diff --git a/Modernize/Modernize/react-version/packages/typescript/main/.eslintrc.cjs b/Modernize/Modernize/react-version/packages/typescript/main/.eslintrc.cjs new file mode 100644 index 0000000..d8df3c1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/.eslintrc.cjs @@ -0,0 +1,19 @@ +module.exports = { + root: true, + env: { browser: true, es2020: true }, + extends: [ + 'eslint:recommended', + 'plugin:@typescript-eslint/recommended', + 'plugin:react-hooks/recommended', + ], + ignorePatterns: ['dist', '.eslintrc.cjs'], + parser: '@typescript-eslint/parser', + plugins: ['react-refresh'], + rules: { + "react/react-in-jsx-scope": "off", + 'react-refresh/only-export-components': [ + 'warn', + { allowConstantExport: true }, + ], + }, +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/.gitignore b/Modernize/Modernize/react-version/packages/typescript/main/.gitignore new file mode 100644 index 0000000..4108b33 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/.gitignore @@ -0,0 +1,24 @@ +# Logs +logs +*.log +npm-debug.log* +yarn-debug.log* +yarn-error.log* +pnpm-debug.log* +lerna-debug.log* + +node_modules +dist +dist-ssr +*.local + +# Editor directories and files +.vscode/* +!.vscode/extensions.json +.idea +.DS_Store +*.suo +*.ntvs* +*.njsproj +*.sln +*.sw? diff --git a/Modernize/Modernize/react-version/packages/typescript/main/.npmrc b/Modernize/Modernize/react-version/packages/typescript/main/.npmrc new file mode 100644 index 0000000..e9ee3cb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/.npmrc @@ -0,0 +1 @@ +legacy-peer-deps=true \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/.prettierrc b/Modernize/Modernize/react-version/packages/typescript/main/.prettierrc new file mode 100644 index 0000000..1387b1c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/.prettierrc @@ -0,0 +1,8 @@ +{ + "bracketSpacing": true, + "printWidth": 100, + "singleQuote": true, + "trailingComma": "all", + "tabWidth": 2, + "useTabs": false +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/README.md b/Modernize/Modernize/react-version/packages/typescript/main/README.md new file mode 100644 index 0000000..e8779f3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/README.md @@ -0,0 +1,27 @@ +# React + TypeScript + Vite + +This template provides a minimal setup to get React working in Vite with HMR and some ESLint rules. + +Currently, two official plugins are available: + +- [@vitejs/plugin-react](https://github.com/vitejs/vite-plugin-react/blob/main/packages/plugin-react/README.md) uses [Babel](https://babeljs.io/) for Fast Refresh +- [@vitejs/plugin-react-swc](https://github.com/vitejs/vite-plugin-react-swc) uses [SWC](https://swc.rs/) for Fast Refresh + +## Expanding the ESLint configuration + +If you are developing a production application, we recommend updating the configuration to enable type aware lint rules: + +- Configure the top-level `parserOptions` property like this: + +```js + parserOptions: { + ecmaVersion: 'latest', + sourceType: 'module', + project: ['./tsconfig.json', './tsconfig.node.json'], + tsconfigRootDir: __dirname, + }, +``` + +- Replace `plugin:@typescript-eslint/recommended` to `plugin:@typescript-eslint/recommended-type-checked` or `plugin:@typescript-eslint/strict-type-checked` +- Optionally add `plugin:@typescript-eslint/stylistic-type-checked` +- Install [eslint-plugin-react](https://github.com/jsx-eslint/eslint-plugin-react) and add `plugin:react/recommended` & `plugin:react/jsx-runtime` to the `extends` list diff --git a/Modernize/Modernize/react-version/packages/typescript/main/index.html b/Modernize/Modernize/react-version/packages/typescript/main/index.html new file mode 100644 index 0000000..508df80 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/index.html @@ -0,0 +1,20 @@ + + + + + + + Modernize Vite + React + TS + + + +
+ + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/package-lock.json b/Modernize/Modernize/react-version/packages/typescript/main/package-lock.json new file mode 100644 index 0000000..c1026d4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/package-lock.json @@ -0,0 +1,13145 @@ +{ + "name": "main-vite-ts", + "version": "5.0.0", + "lockfileVersion": 3, + "requires": true, + "packages": { + "": { + "name": "main-vite-ts", + "version": "5.0.0", + "dependencies": { + "@casl/ability": "^6.3.3", + "@casl/react": "^3.1.0", + "@dnd-kit/core": "^6.1.0", + "@dnd-kit/sortable": "^8.0.0", + "@emotion/cache": "^11.11.0", + "@emotion/react": "^11.13.3", + "@emotion/server": "^11.11.0", + "@emotion/styled": "^11.13.0", + "@hello-pangea/dnd": "^17.0.0", + "@mui/icons-material": "^5.14.13", + "@mui/lab": "6.0.0-beta.10", + "@mui/material": "^6.1.6", + "@mui/system": "^6.1.10", + "@mui/x-charts": "7.23.1", + "@mui/x-date-pickers": "7.18.0", + "@mui/x-tree-view": "^7.18.0", + "@reduxjs/toolkit": "2.2.3", + "@svgr/rollup": "8.1.0", + "@tabler/icons-react": "^2.39.0", + "@tanstack/react-table": "^8.20.1", + "@tiptap/core": "^2.9.1", + "@tiptap/extension-image": "^2.9.1", + "@tiptap/extension-table": "^2.9.1", + "@tiptap/react": "^2.9.1", + "@tiptap/starter-kit": "^2.9.1", + "apexcharts": "3.48.0", + "axios": "1.7.7", + "axios-mock-adapter": "2.0.0", + "chance": "^1.1.11", + "date-fns": "^2.30.0", + "dayjs": "^1.11.13", + "emoji-picker-react": "^4.12.0", + "formik": "^2.4.5", + "formik-mui": "^5.0.0-alpha.0", + "framer-motion": "^10.16.4", + "fslightbox-react": "^1.7.6", + "gray-matter": "^4.0.3", + "i18next": "^23.5.1", + "lodash": "^4.17.21", + "moment": "^2.29.4", + "mui-tiptap": "^1.13.0", + "prop-types": "^15.7.2", + "react": "19.0.0-rc-02c0e824-20241028", + "react-apexcharts": "^1.4.1", + "react-big-calendar": "1.11.3", + "react-dom": "19.0.0-rc-02c0e824-20241028", + "react-dropzone": "^14.2.3", + "react-helmet": "^6.1.0", + "react-i18next": "^13.2.2", + "react-intersection-observer": "^9.5.2", + "react-redux": "9.1.2", + "react-router": "^7.0.2", + "react-slick": "^0.29.0", + "react-spring": "^9.7.3", + "react-syntax-highlighter": "^15.5.0", + "react-top-loading-bar": "^2.3.1", + "redux": "^5.0.1", + "redux-persist": "^6.0.0", + "remark": "^15.0.1", + "remark-html": "^16.0.1", + "sharp": "^0.32.6", + "simplebar": "^6.2.7", + "simplebar-react": "^3.2.4", + "slick-carousel": "^1.8.1", + "stylis-plugin-rtl": "^2.1.1", + "yup": "^0.32.11" + }, + "devDependencies": { + "@types/chance": "^1.1.6", + "@types/fslightbox-react": "^1.7.8", + "@types/node": "22.10.1", + "@types/react": "19.0.1", + "@types/react-big-calendar": "^1.15.0", + "@types/react-dom": "19.0.1", + "@types/react-helmet": "^6.1.11", + "@types/react-slick": "^0.23.13", + "@types/react-syntax-highlighter": "^15.5.13", + "@vitejs/plugin-react": "^4.3.4", + "eslint": "latest", + "eslint-config-next": "latest", + "typescript": "5.7.2", + "vite": "6.0.3" + } + }, + "node_modules/@ampproject/remapping": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@ampproject/remapping/-/remapping-2.3.0.tgz", + "integrity": "sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==", + "license": "Apache-2.0", + "dependencies": { + "@jridgewell/gen-mapping": "^0.3.5", + "@jridgewell/trace-mapping": "^0.3.24" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@babel/code-frame": { + "version": "7.26.2", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.26.2.tgz", + "integrity": "sha512-RJlIHRueQgwWitWgF8OdFYGZX328Ax5BCemNGlqHfplnRT9ESi8JkFlvaVYbS+UubVY6dpv87Fs2u5M29iNFVQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-validator-identifier": "^7.25.9", + "js-tokens": "^4.0.0", + "picocolors": "^1.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/compat-data": { + "version": "7.26.2", + "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.26.2.tgz", + "integrity": "sha512-Z0WgzSEa+aUcdiJuCIqgujCshpMWgUpgOxXotrYPSA53hA3qopNaqcJpyr0hVb1FeWdnqFA35/fUtXgBK8srQg==", + "license": "MIT", + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/core": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.26.0.tgz", + "integrity": "sha512-i1SLeK+DzNnQ3LL/CswPCa/E5u4lh1k6IAEphON8F+cXt0t9euTshDru0q7/IqMa1PMPz5RnHuHscF8/ZJsStg==", + "license": "MIT", + "dependencies": { + "@ampproject/remapping": "^2.2.0", + "@babel/code-frame": "^7.26.0", + "@babel/generator": "^7.26.0", + "@babel/helper-compilation-targets": "^7.25.9", + "@babel/helper-module-transforms": "^7.26.0", + "@babel/helpers": "^7.26.0", + "@babel/parser": "^7.26.0", + "@babel/template": "^7.25.9", + "@babel/traverse": "^7.25.9", + "@babel/types": "^7.26.0", + "convert-source-map": "^2.0.0", + "debug": "^4.1.0", + "gensync": "^1.0.0-beta.2", + "json5": "^2.2.3", + "semver": "^6.3.1" + }, + "engines": { + "node": ">=6.9.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/babel" + } + }, + "node_modules/@babel/core/node_modules/convert-source-map": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz", + "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==", + "license": "MIT" + }, + "node_modules/@babel/generator": { + "version": "7.26.2", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.26.2.tgz", + "integrity": "sha512-zevQbhbau95nkoxSq3f/DC/SC+EEOUZd3DYqfSkMhY2/wfSeaHV1Ew4vk8e+x8lja31IbyuUa2uQ3JONqKbysw==", + "license": "MIT", + "dependencies": { + "@babel/parser": "^7.26.2", + "@babel/types": "^7.26.0", + "@jridgewell/gen-mapping": "^0.3.5", + "@jridgewell/trace-mapping": "^0.3.25", + "jsesc": "^3.0.2" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-annotate-as-pure": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz", + "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==", + "license": "MIT", + "dependencies": { + "@babel/types": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-builder-binary-assignment-operator-visitor": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-builder-binary-assignment-operator-visitor/-/helper-builder-binary-assignment-operator-visitor-7.25.9.tgz", + "integrity": "sha512-C47lC7LIDCnz0h4vai/tpNOI95tCd5ZT3iBt/DBH5lXKHZsyNQv18yf1wIIg2ntiQNgmAvA+DgZ82iW8Qdym8g==", + "license": "MIT", + "dependencies": { + "@babel/traverse": "^7.25.9", + "@babel/types": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-compilation-targets": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.25.9.tgz", + "integrity": "sha512-j9Db8Suy6yV/VHa4qzrj9yZfZxhLWQdVnRlXxmKLYlhWUVB1sB2G5sxuWYXk/whHD9iW76PmNzxZ4UCnTQTVEQ==", + "license": "MIT", + "dependencies": { + "@babel/compat-data": "^7.25.9", + "@babel/helper-validator-option": "^7.25.9", + "browserslist": "^4.24.0", + "lru-cache": "^5.1.1", + "semver": "^6.3.1" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-create-class-features-plugin": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-create-class-features-plugin/-/helper-create-class-features-plugin-7.25.9.tgz", + "integrity": "sha512-UTZQMvt0d/rSz6KI+qdu7GQze5TIajwTS++GUozlw8VBJDEOAqSXwm1WvmYEZwqdqSGQshRocPDqrt4HBZB3fQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.25.9", + "@babel/helper-member-expression-to-functions": "^7.25.9", + "@babel/helper-optimise-call-expression": "^7.25.9", + "@babel/helper-replace-supers": "^7.25.9", + "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9", + "@babel/traverse": "^7.25.9", + "semver": "^6.3.1" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/helper-create-regexp-features-plugin": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-create-regexp-features-plugin/-/helper-create-regexp-features-plugin-7.25.9.tgz", + "integrity": "sha512-ORPNZ3h6ZRkOyAa/SaHU+XsLZr0UQzRwuDQ0cczIA17nAzZ+85G5cVkOJIj7QavLZGSe8QXUmNFxSZzjcZF9bw==", + "license": "MIT", + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.25.9", + "regexpu-core": "^6.1.1", + "semver": "^6.3.1" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/helper-define-polyfill-provider": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.6.3.tgz", + "integrity": "sha512-HK7Bi+Hj6H+VTHA3ZvBis7V/6hu9QuTrnMXNybfUf2iiuU/N97I8VjB+KbhFF8Rld/Lx5MzoCwPCpPjfK+n8Cg==", + "license": "MIT", + "dependencies": { + "@babel/helper-compilation-targets": "^7.22.6", + "@babel/helper-plugin-utils": "^7.22.5", + "debug": "^4.1.1", + "lodash.debounce": "^4.0.8", + "resolve": "^1.14.2" + }, + "peerDependencies": { + "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" + } + }, + "node_modules/@babel/helper-member-expression-to-functions": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.25.9.tgz", + "integrity": "sha512-wbfdZ9w5vk0C0oyHqAJbc62+vet5prjj01jjJ8sKn3j9h3MQQlflEdXYvuqRWjHnM12coDEqiC1IRCi0U/EKwQ==", + "license": "MIT", + "dependencies": { + "@babel/traverse": "^7.25.9", + "@babel/types": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-module-imports": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.25.9.tgz", + "integrity": "sha512-tnUA4RsrmflIM6W6RFTLFSXITtl0wKjgpnLgXyowocVPrbYrLUXSBXDgTs8BlbmIzIdlBySRQjINYs2BAkiLtw==", + "license": "MIT", + "dependencies": { + "@babel/traverse": "^7.25.9", + "@babel/types": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-module-transforms": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.26.0.tgz", + "integrity": "sha512-xO+xu6B5K2czEnQye6BHA7DolFFmS3LB7stHZFaOLb1pAwO1HWLS8fXA+eh0A2yIvltPVmx3eNNDBJA2SLHXFw==", + "license": "MIT", + "dependencies": { + "@babel/helper-module-imports": "^7.25.9", + "@babel/helper-validator-identifier": "^7.25.9", + "@babel/traverse": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/helper-optimise-call-expression": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-optimise-call-expression/-/helper-optimise-call-expression-7.25.9.tgz", + "integrity": "sha512-FIpuNaz5ow8VyrYcnXQTDRGvV6tTjkNtCK/RYNDXGSLlUD6cBuQTSw43CShGxjvfBTfcUA/r6UhUCbtYqkhcuQ==", + "license": "MIT", + "dependencies": { + "@babel/types": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-plugin-utils": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-plugin-utils/-/helper-plugin-utils-7.25.9.tgz", + "integrity": "sha512-kSMlyUVdWe25rEsRGviIgOWnoT/nfABVWlqt9N19/dIPWViAOW2s9wznP5tURbs/IDuNk4gPy3YdYRgH3uxhBw==", + "license": "MIT", + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-remap-async-to-generator": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-remap-async-to-generator/-/helper-remap-async-to-generator-7.25.9.tgz", + "integrity": "sha512-IZtukuUeBbhgOcaW2s06OXTzVNJR0ybm4W5xC1opWFFJMZbwRj5LCk+ByYH7WdZPZTt8KnFwA8pvjN2yqcPlgw==", + "license": "MIT", + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.25.9", + "@babel/helper-wrap-function": "^7.25.9", + "@babel/traverse": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/helper-replace-supers": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-replace-supers/-/helper-replace-supers-7.25.9.tgz", + "integrity": "sha512-IiDqTOTBQy0sWyeXyGSC5TBJpGFXBkRynjBeXsvbhQFKj2viwJC76Epz35YLU1fpe/Am6Vppb7W7zM4fPQzLsQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-member-expression-to-functions": "^7.25.9", + "@babel/helper-optimise-call-expression": "^7.25.9", + "@babel/traverse": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/helper-simple-access": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-simple-access/-/helper-simple-access-7.25.9.tgz", + "integrity": "sha512-c6WHXuiaRsJTyHYLJV75t9IqsmTbItYfdj99PnzYGQZkYKvan5/2jKJ7gu31J3/BJ/A18grImSPModuyG/Eo0Q==", + "license": "MIT", + "dependencies": { + "@babel/traverse": "^7.25.9", + "@babel/types": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-skip-transparent-expression-wrappers": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-skip-transparent-expression-wrappers/-/helper-skip-transparent-expression-wrappers-7.25.9.tgz", + "integrity": "sha512-K4Du3BFa3gvyhzgPcntrkDgZzQaq6uozzcpGbOO1OEJaI+EJdqWIMTLgFgQf6lrfiDFo5FU+BxKepI9RmZqahA==", + "license": "MIT", + "dependencies": { + "@babel/traverse": "^7.25.9", + "@babel/types": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-string-parser": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-string-parser/-/helper-string-parser-7.25.9.tgz", + "integrity": "sha512-4A/SCr/2KLd5jrtOMFzaKjVtAei3+2r/NChoBNoZ3EyP/+GlhoaEGoWOZUmFmoITP7zOJyHIMm+DYRd8o3PvHA==", + "license": "MIT", + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-validator-identifier": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.25.9.tgz", + "integrity": "sha512-Ed61U6XJc3CVRfkERJWDz4dJwKe7iLmmJsbOGu9wSloNSFttHV0I8g6UAgb7qnK5ly5bGLPd4oXZlxCdANBOWQ==", + "license": "MIT", + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-validator-option": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-option/-/helper-validator-option-7.25.9.tgz", + "integrity": "sha512-e/zv1co8pp55dNdEcCynfj9X7nyUKUXoUEwfXqaZt0omVOmDe9oOTdKStH4GmAw6zxMFs50ZayuMfHDKlO7Tfw==", + "license": "MIT", + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-wrap-function": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/helper-wrap-function/-/helper-wrap-function-7.25.9.tgz", + "integrity": "sha512-ETzz9UTjQSTmw39GboatdymDq4XIQbR8ySgVrylRhPOFpsd+JrKHIuF0de7GCWmem+T4uC5z7EZguod7Wj4A4g==", + "license": "MIT", + "dependencies": { + "@babel/template": "^7.25.9", + "@babel/traverse": "^7.25.9", + "@babel/types": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helpers": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.26.0.tgz", + "integrity": "sha512-tbhNuIxNcVb21pInl3ZSjksLCvgdZy9KwJ8brv993QtIVKJBBkYXz4q4ZbAv31GdnC+R90np23L5FbEBlthAEw==", + "license": "MIT", + "dependencies": { + "@babel/template": "^7.25.9", + "@babel/types": "^7.26.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/parser": { + "version": "7.26.2", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.26.2.tgz", + "integrity": "sha512-DWMCZH9WA4Maitz2q21SRKHo9QXZxkDsbNZoVD62gusNtNBBqDg9i7uOhASfTfIGNzW+O+r7+jAlM8dwphcJKQ==", + "license": "MIT", + "dependencies": { + "@babel/types": "^7.26.0" + }, + "bin": { + "parser": "bin/babel-parser.js" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@babel/plugin-bugfix-firefox-class-in-computed-class-key": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-firefox-class-in-computed-class-key/-/plugin-bugfix-firefox-class-in-computed-class-key-7.25.9.tgz", + "integrity": "sha512-ZkRyVkThtxQ/J6nv3JFYv1RYY+JT5BvU0y3k5bWrmuG4woXypRa4PXmm9RhOwodRkYFWqC0C0cqcJ4OqR7kW+g==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/traverse": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/plugin-bugfix-safari-class-field-initializer-scope": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-class-field-initializer-scope/-/plugin-bugfix-safari-class-field-initializer-scope-7.25.9.tgz", + "integrity": "sha512-MrGRLZxLD/Zjj0gdU15dfs+HH/OXvnw/U4jJD8vpcP2CJQapPEv1IWwjc/qMg7ItBlPwSv1hRBbb7LeuANdcnw==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression/-/plugin-bugfix-safari-id-destructuring-collision-in-function-expression-7.25.9.tgz", + "integrity": "sha512-2qUwwfAFpJLZqxd02YW9btUCZHl+RFvdDkNfZwaIJrvB8Tesjsk8pEQkTvGwZXLqXUx/2oyY3ySRhm6HOXuCug==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining/-/plugin-bugfix-v8-spread-parameters-in-optional-chaining-7.25.9.tgz", + "integrity": "sha512-6xWgLZTJXwilVjlnV7ospI3xi+sl8lN8rXXbBD6vYn3UYDlGsag8wrZkKcSI8G6KgqKP7vNFaDgeDnfAABq61g==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9", + "@babel/plugin-transform-optional-chaining": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.13.0" + } + }, + "node_modules/@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly/-/plugin-bugfix-v8-static-class-fields-redefine-readonly-7.25.9.tgz", + "integrity": "sha512-aLnMXYPnzwwqhYSCyXfKkIkYgJ8zv9RK+roo9DkTXz38ynIhd9XCbN08s3MGvqL2MYGVUGdRQLL/JqBIeJhJBg==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/traverse": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/plugin-proposal-private-property-in-object": { + "version": "7.21.0-placeholder-for-preset-env.2", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-property-in-object/-/plugin-proposal-private-property-in-object-7.21.0-placeholder-for-preset-env.2.tgz", + "integrity": "sha512-SOSkfJDddaM7mak6cPEpswyTRnuRltl429hMraQEglW+OkovnCzsiszTmsrlY//qLFjCpQDFRvjdm2wA5pPm9w==", + "license": "MIT", + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-import-assertions": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-assertions/-/plugin-syntax-import-assertions-7.26.0.tgz", + "integrity": "sha512-QCWT5Hh830hK5EQa7XzuqIkQU9tT/whqbDz7kuaZMHFl1inRRg7JnuAEOQ0Ur0QUl0NufCk1msK2BeY79Aj/eg==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-import-attributes": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-attributes/-/plugin-syntax-import-attributes-7.26.0.tgz", + "integrity": "sha512-e2dttdsJ1ZTpi3B9UYGLw41hifAubg19AtCu/2I/F1QNVclOBr1dYpTdmdyZ84Xiz43BS/tCUkMAZNLv12Pi+A==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-jsx": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-jsx/-/plugin-syntax-jsx-7.25.9.tgz", + "integrity": "sha512-ld6oezHQMZsZfp6pWtbjaNDF2tiiCYYDqQszHt5VV437lewP9aSi2Of99CK0D0XB21k7FLgnLcmQKyKzynfeAA==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-typescript": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-typescript/-/plugin-syntax-typescript-7.25.9.tgz", + "integrity": "sha512-hjMgRy5hb8uJJjUcdWunWVcoi9bGpJp8p5Ol1229PoN6aytsLwNMgmdftO23wnCLMfVmTwZDWMPNq/D1SY60JQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-unicode-sets-regex": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-unicode-sets-regex/-/plugin-syntax-unicode-sets-regex-7.18.6.tgz", + "integrity": "sha512-727YkEAPwSIQTv5im8QHz3upqp92JTWhidIC81Tdx4VJYIte/VndKf1qKrfnnhPLiPghStWfvC/iFaMCQu7Nqg==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.18.6", + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/plugin-transform-arrow-functions": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-arrow-functions/-/plugin-transform-arrow-functions-7.25.9.tgz", + "integrity": "sha512-6jmooXYIwn9ca5/RylZADJ+EnSxVUS5sjeJ9UPk6RWRzXCmOJCy6dqItPJFpw2cuCangPK4OYr5uhGKcmrm5Qg==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-async-generator-functions": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-generator-functions/-/plugin-transform-async-generator-functions-7.25.9.tgz", + "integrity": "sha512-RXV6QAzTBbhDMO9fWwOmwwTuYaiPbggWQ9INdZqAYeSHyG7FzQ+nOZaUUjNwKv9pV3aE4WFqFm1Hnbci5tBCAw==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-remap-async-to-generator": "^7.25.9", + "@babel/traverse": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-async-to-generator": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.25.9.tgz", + "integrity": "sha512-NT7Ejn7Z/LjUH0Gv5KsBCxh7BH3fbLTV0ptHvpeMvrt3cPThHfJfst9Wrb7S8EvJ7vRTFI7z+VAvFVEQn/m5zQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-module-imports": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-remap-async-to-generator": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-block-scoped-functions": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoped-functions/-/plugin-transform-block-scoped-functions-7.25.9.tgz", + "integrity": "sha512-toHc9fzab0ZfenFpsyYinOX0J/5dgJVA2fm64xPewu7CoYHWEivIWKxkK2rMi4r3yQqLnVmheMXRdG+k239CgA==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-block-scoping": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoping/-/plugin-transform-block-scoping-7.25.9.tgz", + "integrity": "sha512-1F05O7AYjymAtqbsFETboN1NvBdcnzMerO+zlMyJBEz6WkMdejvGWw9p05iTSjC85RLlBseHHQpYaM4gzJkBGg==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-class-properties": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-class-properties/-/plugin-transform-class-properties-7.25.9.tgz", + "integrity": "sha512-bbMAII8GRSkcd0h0b4X+36GksxuheLFjP65ul9w6C3KgAamI3JqErNgSrosX6ZPj+Mpim5VvEbawXxJCyEUV3Q==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-class-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-class-static-block": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-class-static-block/-/plugin-transform-class-static-block-7.26.0.tgz", + "integrity": "sha512-6J2APTs7BDDm+UMqP1useWqhcRAXo0WIoVj26N7kPFB6S73Lgvyka4KTZYIxtgYXiN5HTyRObA72N2iu628iTQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-class-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.12.0" + } + }, + "node_modules/@babel/plugin-transform-classes": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-classes/-/plugin-transform-classes-7.25.9.tgz", + "integrity": "sha512-mD8APIXmseE7oZvZgGABDyM34GUmK45Um2TXiBUt7PnuAxrgoSVf123qUzPxEr/+/BHrRn5NMZCdE2m/1F8DGg==", + "license": "MIT", + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.25.9", + "@babel/helper-compilation-targets": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-replace-supers": "^7.25.9", + "@babel/traverse": "^7.25.9", + "globals": "^11.1.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-computed-properties": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-computed-properties/-/plugin-transform-computed-properties-7.25.9.tgz", + "integrity": "sha512-HnBegGqXZR12xbcTHlJ9HGxw1OniltT26J5YpfruGqtUHlz/xKf/G2ak9e+t0rVqrjXa9WOhvYPz1ERfMj23AA==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/template": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-destructuring": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.25.9.tgz", + "integrity": "sha512-WkCGb/3ZxXepmMiX101nnGiU+1CAdut8oHyEOHxkKuS1qKpU2SMXE2uSvfz8PBuLd49V6LEsbtyPhWC7fnkgvQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-dotall-regex": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dotall-regex/-/plugin-transform-dotall-regex-7.25.9.tgz", + "integrity": "sha512-t7ZQ7g5trIgSRYhI9pIJtRl64KHotutUJsh4Eze5l7olJv+mRSg4/MmbZ0tv1eeqRbdvo/+trvJD/Oc5DmW2cA==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-duplicate-keys": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-keys/-/plugin-transform-duplicate-keys-7.25.9.tgz", + "integrity": "sha512-LZxhJ6dvBb/f3x8xwWIuyiAHy56nrRG3PeYTpBkkzkYRRQ6tJLu68lEF5VIqMUZiAV7a8+Tb78nEoMCMcqjXBw==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-duplicate-named-capturing-groups-regex": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-named-capturing-groups-regex/-/plugin-transform-duplicate-named-capturing-groups-regex-7.25.9.tgz", + "integrity": "sha512-0UfuJS0EsXbRvKnwcLjFtJy/Sxc5J5jhLHnFhy7u4zih97Hz6tJkLU+O+FMMrNZrosUPxDi6sYxJ/EA8jDiAog==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/plugin-transform-dynamic-import": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dynamic-import/-/plugin-transform-dynamic-import-7.25.9.tgz", + "integrity": "sha512-GCggjexbmSLaFhqsojeugBpeaRIgWNTcgKVq/0qIteFEqY2A+b9QidYadrWlnbWQUrW5fn+mCvf3tr7OeBFTyg==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-exponentiation-operator": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-exponentiation-operator/-/plugin-transform-exponentiation-operator-7.25.9.tgz", + "integrity": "sha512-KRhdhlVk2nObA5AYa7QMgTMTVJdfHprfpAk4DjZVtllqRg9qarilstTKEhpVjyt+Npi8ThRyiV8176Am3CodPA==", + "license": "MIT", + "dependencies": { + "@babel/helper-builder-binary-assignment-operator-visitor": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-export-namespace-from": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-export-namespace-from/-/plugin-transform-export-namespace-from-7.25.9.tgz", + "integrity": "sha512-2NsEz+CxzJIVOPx2o9UsW1rXLqtChtLoVnwYHHiB04wS5sgn7mrV45fWMBX0Kk+ub9uXytVYfNP2HjbVbCB3Ww==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-for-of": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.25.9.tgz", + "integrity": "sha512-LqHxduHoaGELJl2uhImHwRQudhCM50pT46rIBNvtT/Oql3nqiS3wOwP+5ten7NpYSXrrVLgtZU3DZmPtWZo16A==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-function-name": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-function-name/-/plugin-transform-function-name-7.25.9.tgz", + "integrity": "sha512-8lP+Yxjv14Vc5MuWBpJsoUCd3hD6V9DgBon2FVYL4jJgbnVQ9fTgYmonchzZJOVNgzEgbxp4OwAf6xz6M/14XA==", + "license": "MIT", + "dependencies": { + "@babel/helper-compilation-targets": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/traverse": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-json-strings": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-json-strings/-/plugin-transform-json-strings-7.25.9.tgz", + "integrity": "sha512-xoTMk0WXceiiIvsaquQQUaLLXSW1KJ159KP87VilruQm0LNNGxWzahxSS6T6i4Zg3ezp4vA4zuwiNUR53qmQAw==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-literals": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-literals/-/plugin-transform-literals-7.25.9.tgz", + "integrity": "sha512-9N7+2lFziW8W9pBl2TzaNht3+pgMIRP74zizeCSrtnSKVdUl8mAjjOP2OOVQAfZ881P2cNjDj1uAMEdeD50nuQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-logical-assignment-operators": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-logical-assignment-operators/-/plugin-transform-logical-assignment-operators-7.25.9.tgz", + "integrity": "sha512-wI4wRAzGko551Y8eVf6iOY9EouIDTtPb0ByZx+ktDGHwv6bHFimrgJM/2T021txPZ2s4c7bqvHbd+vXG6K948Q==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-member-expression-literals": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-member-expression-literals/-/plugin-transform-member-expression-literals-7.25.9.tgz", + "integrity": "sha512-PYazBVfofCQkkMzh2P6IdIUaCEWni3iYEerAsRWuVd8+jlM1S9S9cz1dF9hIzyoZ8IA3+OwVYIp9v9e+GbgZhA==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-modules-amd": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.25.9.tgz", + "integrity": "sha512-g5T11tnI36jVClQlMlt4qKDLlWnG5pP9CSM4GhdRciTNMRgkfpo5cR6b4rGIOYPgRRuFAvwjPQ/Yk+ql4dyhbw==", + "license": "MIT", + "dependencies": { + "@babel/helper-module-transforms": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-modules-commonjs": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.25.9.tgz", + "integrity": "sha512-dwh2Ol1jWwL2MgkCzUSOvfmKElqQcuswAZypBSUsScMXvgdT8Ekq5YA6TtqpTVWH+4903NmboMuH1o9i8Rxlyg==", + "license": "MIT", + "dependencies": { + "@babel/helper-module-transforms": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-simple-access": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-modules-systemjs": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.25.9.tgz", + "integrity": "sha512-hyss7iIlH/zLHaehT+xwiymtPOpsiwIIRlCAOwBB04ta5Tt+lNItADdlXw3jAWZ96VJ2jlhl/c+PNIQPKNfvcA==", + "license": "MIT", + "dependencies": { + "@babel/helper-module-transforms": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-validator-identifier": "^7.25.9", + "@babel/traverse": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-modules-umd": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-umd/-/plugin-transform-modules-umd-7.25.9.tgz", + "integrity": "sha512-bS9MVObUgE7ww36HEfwe6g9WakQ0KF07mQF74uuXdkoziUPfKyu/nIm663kz//e5O1nPInPFx36z7WJmJ4yNEw==", + "license": "MIT", + "dependencies": { + "@babel/helper-module-transforms": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-named-capturing-groups-regex": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-named-capturing-groups-regex/-/plugin-transform-named-capturing-groups-regex-7.25.9.tgz", + "integrity": "sha512-oqB6WHdKTGl3q/ItQhpLSnWWOpjUJLsOCLVyeFgeTktkBSCiurvPOsyt93gibI9CmuKvTUEtWmG5VhZD+5T/KA==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/plugin-transform-new-target": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-new-target/-/plugin-transform-new-target-7.25.9.tgz", + "integrity": "sha512-U/3p8X1yCSoKyUj2eOBIx3FOn6pElFOKvAAGf8HTtItuPyB+ZeOqfn+mvTtg9ZlOAjsPdK3ayQEjqHjU/yLeVQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-nullish-coalescing-operator": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-nullish-coalescing-operator/-/plugin-transform-nullish-coalescing-operator-7.25.9.tgz", + "integrity": "sha512-ENfftpLZw5EItALAD4WsY/KUWvhUlZndm5GC7G3evUsVeSJB6p0pBeLQUnRnBCBx7zV0RKQjR9kCuwrsIrjWog==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-numeric-separator": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-numeric-separator/-/plugin-transform-numeric-separator-7.25.9.tgz", + "integrity": "sha512-TlprrJ1GBZ3r6s96Yq8gEQv82s8/5HnCVHtEJScUj90thHQbwe+E5MLhi2bbNHBEJuzrvltXSru+BUxHDoog7Q==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-object-rest-spread": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-rest-spread/-/plugin-transform-object-rest-spread-7.25.9.tgz", + "integrity": "sha512-fSaXafEE9CVHPweLYw4J0emp1t8zYTXyzN3UuG+lylqkvYd7RMrsOQ8TYx5RF231be0vqtFC6jnx3UmpJmKBYg==", + "license": "MIT", + "dependencies": { + "@babel/helper-compilation-targets": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/plugin-transform-parameters": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-object-super": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-super/-/plugin-transform-object-super-7.25.9.tgz", + "integrity": "sha512-Kj/Gh+Rw2RNLbCK1VAWj2U48yxxqL2x0k10nPtSdRa0O2xnHXalD0s+o1A6a0W43gJ00ANo38jxkQreckOzv5A==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-replace-supers": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-optional-catch-binding": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-optional-catch-binding/-/plugin-transform-optional-catch-binding-7.25.9.tgz", + "integrity": "sha512-qM/6m6hQZzDcZF3onzIhZeDHDO43bkNNlOX0i8n3lR6zLbu0GN2d8qfM/IERJZYauhAHSLHy39NF0Ctdvcid7g==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-optional-chaining": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-optional-chaining/-/plugin-transform-optional-chaining-7.25.9.tgz", + "integrity": "sha512-6AvV0FsLULbpnXeBjrY4dmWF8F7gf8QnvTEoO/wX/5xm/xE1Xo8oPuD3MPS+KS9f9XBEAWN7X1aWr4z9HdOr7A==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-parameters": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-parameters/-/plugin-transform-parameters-7.25.9.tgz", + "integrity": "sha512-wzz6MKwpnshBAiRmn4jR8LYz/g8Ksg0o80XmwZDlordjwEk9SxBzTWC7F5ef1jhbrbOW2DJ5J6ayRukrJmnr0g==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-private-methods": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-private-methods/-/plugin-transform-private-methods-7.25.9.tgz", + "integrity": "sha512-D/JUozNpQLAPUVusvqMxyvjzllRaF8/nSrP1s2YGQT/W4LHK4xxsMcHjhOGTS01mp9Hda8nswb+FblLdJornQw==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-class-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-private-property-in-object": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-private-property-in-object/-/plugin-transform-private-property-in-object-7.25.9.tgz", + "integrity": "sha512-Evf3kcMqzXA3xfYJmZ9Pg1OvKdtqsDMSWBDzZOPLvHiTt36E75jLDQo5w1gtRU95Q4E5PDttrTf25Fw8d/uWLw==", + "license": "MIT", + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.25.9", + "@babel/helper-create-class-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-property-literals": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-property-literals/-/plugin-transform-property-literals-7.25.9.tgz", + "integrity": "sha512-IvIUeV5KrS/VPavfSM/Iu+RE6llrHrYIKY1yfCzyO/lMXHQ+p7uGhonmGVisv6tSBSVgWzMBohTcvkC9vQcQFA==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-react-constant-elements": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-constant-elements/-/plugin-transform-react-constant-elements-7.25.9.tgz", + "integrity": "sha512-Ncw2JFsJVuvfRsa2lSHiC55kETQVLSnsYGQ1JDDwkUeWGTL/8Tom8aLTnlqgoeuopWrbbGndrc9AlLYrIosrow==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-react-display-name": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-display-name/-/plugin-transform-react-display-name-7.25.9.tgz", + "integrity": "sha512-KJfMlYIUxQB1CJfO3e0+h0ZHWOTLCPP115Awhaz8U0Zpq36Gl/cXlpoyMRnUWlhNUBAzldnCiAZNvCDj7CrKxQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-react-jsx": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-jsx/-/plugin-transform-react-jsx-7.25.9.tgz", + "integrity": "sha512-s5XwpQYCqGerXl+Pu6VDL3x0j2d82eiV77UJ8a2mDHAW7j9SWRqQ2y1fNo1Z74CdcYipl5Z41zvjj4Nfzq36rw==", + "license": "MIT", + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.25.9", + "@babel/helper-module-imports": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/plugin-syntax-jsx": "^7.25.9", + "@babel/types": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-react-jsx-development": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-jsx-development/-/plugin-transform-react-jsx-development-7.25.9.tgz", + "integrity": "sha512-9mj6rm7XVYs4mdLIpbZnHOYdpW42uoiBCTVowg7sP1thUOiANgMb4UtpRivR0pp5iL+ocvUv7X4mZgFRpJEzGw==", + "license": "MIT", + "dependencies": { + "@babel/plugin-transform-react-jsx": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-react-jsx-self": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-jsx-self/-/plugin-transform-react-jsx-self-7.25.9.tgz", + "integrity": "sha512-y8quW6p0WHkEhmErnfe58r7x0A70uKphQm8Sp8cV7tjNQwK56sNVK0M73LK3WuYmsuyrftut4xAkjjgU0twaMg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-react-jsx-source": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-jsx-source/-/plugin-transform-react-jsx-source-7.25.9.tgz", + "integrity": "sha512-+iqjT8xmXhhYv4/uiYd8FNQsraMFZIfxVSqxxVSZP0WbbSAWvBXAul0m/zu+7Vv4O/3WtApy9pmaTMiumEZgfg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-react-pure-annotations": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-pure-annotations/-/plugin-transform-react-pure-annotations-7.25.9.tgz", + "integrity": "sha512-KQ/Takk3T8Qzj5TppkS1be588lkbTp5uj7w6a0LeQaTMSckU/wK0oJ/pih+T690tkgI5jfmg2TqDJvd41Sj1Cg==", + "license": "MIT", + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-regenerator": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regenerator/-/plugin-transform-regenerator-7.25.9.tgz", + "integrity": "sha512-vwDcDNsgMPDGP0nMqzahDWE5/MLcX8sv96+wfX7as7LoF/kr97Bo/7fI00lXY4wUXYfVmwIIyG80fGZ1uvt2qg==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "regenerator-transform": "^0.15.2" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-regexp-modifiers": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regexp-modifiers/-/plugin-transform-regexp-modifiers-7.26.0.tgz", + "integrity": "sha512-vN6saax7lrA2yA/Pak3sCxuD6F5InBjn9IcrIKQPjpsLvuHYLVroTxjdlVRHjjBWxKOqIwpTXDkOssYT4BFdRw==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/plugin-transform-reserved-words": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-reserved-words/-/plugin-transform-reserved-words-7.25.9.tgz", + "integrity": "sha512-7DL7DKYjn5Su++4RXu8puKZm2XBPHyjWLUidaPEkCUBbE7IPcsrkRHggAOOKydH1dASWdcUBxrkOGNxUv5P3Jg==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-shorthand-properties": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-shorthand-properties/-/plugin-transform-shorthand-properties-7.25.9.tgz", + "integrity": "sha512-MUv6t0FhO5qHnS/W8XCbHmiRWOphNufpE1IVxhK5kuN3Td9FT1x4rx4K42s3RYdMXCXpfWkGSbCSd0Z64xA7Ng==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-spread": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-spread/-/plugin-transform-spread-7.25.9.tgz", + "integrity": "sha512-oNknIB0TbURU5pqJFVbOOFspVlrpVwo2H1+HUIsVDvp5VauGGDP1ZEvO8Nn5xyMEs3dakajOxlmkNW7kNgSm6A==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-sticky-regex": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-sticky-regex/-/plugin-transform-sticky-regex-7.25.9.tgz", + "integrity": "sha512-WqBUSgeVwucYDP9U/xNRQam7xV8W5Zf+6Eo7T2SRVUFlhRiMNFdFz58u0KZmCVVqs2i7SHgpRnAhzRNmKfi2uA==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-template-literals": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.25.9.tgz", + "integrity": "sha512-o97AE4syN71M/lxrCtQByzphAdlYluKPDBzDVzMmfCobUjjhAryZV0AIpRPrxN0eAkxXO6ZLEScmt+PNhj2OTw==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-typeof-symbol": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.25.9.tgz", + "integrity": "sha512-v61XqUMiueJROUv66BVIOi0Fv/CUuZuZMl5NkRoCVxLAnMexZ0A3kMe7vvZ0nulxMuMp0Mk6S5hNh48yki08ZA==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-typescript": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typescript/-/plugin-transform-typescript-7.25.9.tgz", + "integrity": "sha512-7PbZQZP50tzv2KGGnhh82GSyMB01yKY9scIjf1a+GfZCtInOWqUH5+1EBU4t9fyR5Oykkkc9vFTs4OHrhHXljQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.25.9", + "@babel/helper-create-class-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9", + "@babel/plugin-syntax-typescript": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-unicode-escapes": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-escapes/-/plugin-transform-unicode-escapes-7.25.9.tgz", + "integrity": "sha512-s5EDrE6bW97LtxOcGj1Khcx5AaXwiMmi4toFWRDP9/y0Woo6pXC+iyPu/KuhKtfSrNFd7jJB+/fkOtZy6aIC6Q==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-unicode-property-regex": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-property-regex/-/plugin-transform-unicode-property-regex-7.25.9.tgz", + "integrity": "sha512-Jt2d8Ga+QwRluxRQ307Vlxa6dMrYEMZCgGxoPR8V52rxPyldHu3hdlHspxaqYmE7oID5+kB+UKUB/eWS+DkkWg==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-unicode-regex": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-regex/-/plugin-transform-unicode-regex-7.25.9.tgz", + "integrity": "sha512-yoxstj7Rg9dlNn9UQxzk4fcNivwv4nUYz7fYXBaKxvw/lnmPuOm/ikoELygbYq68Bls3D/D+NBPHiLwZdZZ4HA==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-unicode-sets-regex": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-sets-regex/-/plugin-transform-unicode-sets-regex-7.25.9.tgz", + "integrity": "sha512-8BYqO3GeVNHtx69fdPshN3fnzUNLrWdHhk/icSwigksJGczKSizZ+Z6SBCxTs723Fr5VSNorTIK7a+R2tISvwQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/preset-env": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.26.0.tgz", + "integrity": "sha512-H84Fxq0CQJNdPFT2DrfnylZ3cf5K43rGfWK4LJGPpjKHiZlk0/RzwEus3PDDZZg+/Er7lCA03MVacueUuXdzfw==", + "license": "MIT", + "dependencies": { + "@babel/compat-data": "^7.26.0", + "@babel/helper-compilation-targets": "^7.25.9", + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-validator-option": "^7.25.9", + "@babel/plugin-bugfix-firefox-class-in-computed-class-key": "^7.25.9", + "@babel/plugin-bugfix-safari-class-field-initializer-scope": "^7.25.9", + "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.25.9", + "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.25.9", + "@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": "^7.25.9", + "@babel/plugin-proposal-private-property-in-object": "7.21.0-placeholder-for-preset-env.2", + "@babel/plugin-syntax-import-assertions": "^7.26.0", + "@babel/plugin-syntax-import-attributes": "^7.26.0", + "@babel/plugin-syntax-unicode-sets-regex": "^7.18.6", + "@babel/plugin-transform-arrow-functions": "^7.25.9", + "@babel/plugin-transform-async-generator-functions": "^7.25.9", + "@babel/plugin-transform-async-to-generator": "^7.25.9", + "@babel/plugin-transform-block-scoped-functions": "^7.25.9", + "@babel/plugin-transform-block-scoping": "^7.25.9", + "@babel/plugin-transform-class-properties": "^7.25.9", + "@babel/plugin-transform-class-static-block": "^7.26.0", + "@babel/plugin-transform-classes": "^7.25.9", + "@babel/plugin-transform-computed-properties": "^7.25.9", + "@babel/plugin-transform-destructuring": "^7.25.9", + "@babel/plugin-transform-dotall-regex": "^7.25.9", + "@babel/plugin-transform-duplicate-keys": "^7.25.9", + "@babel/plugin-transform-duplicate-named-capturing-groups-regex": "^7.25.9", + "@babel/plugin-transform-dynamic-import": "^7.25.9", + "@babel/plugin-transform-exponentiation-operator": "^7.25.9", + "@babel/plugin-transform-export-namespace-from": "^7.25.9", + "@babel/plugin-transform-for-of": "^7.25.9", + "@babel/plugin-transform-function-name": "^7.25.9", + "@babel/plugin-transform-json-strings": "^7.25.9", + "@babel/plugin-transform-literals": "^7.25.9", + "@babel/plugin-transform-logical-assignment-operators": "^7.25.9", + "@babel/plugin-transform-member-expression-literals": "^7.25.9", + "@babel/plugin-transform-modules-amd": "^7.25.9", + "@babel/plugin-transform-modules-commonjs": "^7.25.9", + "@babel/plugin-transform-modules-systemjs": "^7.25.9", + "@babel/plugin-transform-modules-umd": "^7.25.9", + "@babel/plugin-transform-named-capturing-groups-regex": "^7.25.9", + "@babel/plugin-transform-new-target": "^7.25.9", + "@babel/plugin-transform-nullish-coalescing-operator": "^7.25.9", + "@babel/plugin-transform-numeric-separator": "^7.25.9", + "@babel/plugin-transform-object-rest-spread": "^7.25.9", + "@babel/plugin-transform-object-super": "^7.25.9", + "@babel/plugin-transform-optional-catch-binding": "^7.25.9", + "@babel/plugin-transform-optional-chaining": "^7.25.9", + "@babel/plugin-transform-parameters": "^7.25.9", + "@babel/plugin-transform-private-methods": "^7.25.9", + "@babel/plugin-transform-private-property-in-object": "^7.25.9", + "@babel/plugin-transform-property-literals": "^7.25.9", + "@babel/plugin-transform-regenerator": "^7.25.9", + "@babel/plugin-transform-regexp-modifiers": "^7.26.0", + "@babel/plugin-transform-reserved-words": "^7.25.9", + "@babel/plugin-transform-shorthand-properties": "^7.25.9", + "@babel/plugin-transform-spread": "^7.25.9", + "@babel/plugin-transform-sticky-regex": "^7.25.9", + "@babel/plugin-transform-template-literals": "^7.25.9", + "@babel/plugin-transform-typeof-symbol": "^7.25.9", + "@babel/plugin-transform-unicode-escapes": "^7.25.9", + "@babel/plugin-transform-unicode-property-regex": "^7.25.9", + "@babel/plugin-transform-unicode-regex": "^7.25.9", + "@babel/plugin-transform-unicode-sets-regex": "^7.25.9", + "@babel/preset-modules": "0.1.6-no-external-plugins", + "babel-plugin-polyfill-corejs2": "^0.4.10", + "babel-plugin-polyfill-corejs3": "^0.10.6", + "babel-plugin-polyfill-regenerator": "^0.6.1", + "core-js-compat": "^3.38.1", + "semver": "^6.3.1" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/preset-modules": { + "version": "0.1.6-no-external-plugins", + "resolved": "https://registry.npmjs.org/@babel/preset-modules/-/preset-modules-0.1.6-no-external-plugins.tgz", + "integrity": "sha512-HrcgcIESLm9aIR842yhJ5RWan/gebQUJ6E/E5+rf0y9o6oj7w0Br+sWuL6kEQ/o/AdfvR1Je9jG18/gnpwjEyA==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.0.0", + "@babel/types": "^7.4.4", + "esutils": "^2.0.2" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0 || ^8.0.0-0 <8.0.0" + } + }, + "node_modules/@babel/preset-react": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/preset-react/-/preset-react-7.25.9.tgz", + "integrity": "sha512-D3to0uSPiWE7rBrdIICCd0tJSIGpLaaGptna2+w7Pft5xMqLpA1sz99DK5TZ1TjGbdQ/VI1eCSZ06dv3lT4JOw==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-validator-option": "^7.25.9", + "@babel/plugin-transform-react-display-name": "^7.25.9", + "@babel/plugin-transform-react-jsx": "^7.25.9", + "@babel/plugin-transform-react-jsx-development": "^7.25.9", + "@babel/plugin-transform-react-pure-annotations": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/preset-typescript": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/preset-typescript/-/preset-typescript-7.26.0.tgz", + "integrity": "sha512-NMk1IGZ5I/oHhoXEElcm+xUnL/szL6xflkFZmoEU9xj1qSJXpiS7rsspYo92B4DRCDvZn2erT5LdsCeXAKNCkg==", + "license": "MIT", + "dependencies": { + "@babel/helper-plugin-utils": "^7.25.9", + "@babel/helper-validator-option": "^7.25.9", + "@babel/plugin-syntax-jsx": "^7.25.9", + "@babel/plugin-transform-modules-commonjs": "^7.25.9", + "@babel/plugin-transform-typescript": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/runtime": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.26.0.tgz", + "integrity": "sha512-FDSOghenHTiToteC/QRlv2q3DhPZ/oOXTBoirfWNx1Cx3TMVcGWQtMMmQcSvb/JjpNeGzx8Pq/b4fKEJuWm1sw==", + "license": "MIT", + "dependencies": { + "regenerator-runtime": "^0.14.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/template": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.25.9.tgz", + "integrity": "sha512-9DGttpmPvIxBb/2uwpVo3dqJ+O6RooAFOS+lB+xDqoE2PVCE8nfoHMdZLpfCQRLwvohzXISPZcgxt80xLfsuwg==", + "license": "MIT", + "dependencies": { + "@babel/code-frame": "^7.25.9", + "@babel/parser": "^7.25.9", + "@babel/types": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/traverse": { + "version": "7.25.9", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.25.9.tgz", + "integrity": "sha512-ZCuvfwOwlz/bawvAuvcj8rrithP2/N55Tzz342AkTvq4qaWbGfmCk/tKhNaV2cthijKrPAA8SRJV5WWe7IBMJw==", + "license": "MIT", + "dependencies": { + "@babel/code-frame": "^7.25.9", + "@babel/generator": "^7.25.9", + "@babel/parser": "^7.25.9", + "@babel/template": "^7.25.9", + "@babel/types": "^7.25.9", + "debug": "^4.3.1", + "globals": "^11.1.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/types": { + "version": "7.26.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.26.0.tgz", + "integrity": "sha512-Z/yiTPj+lDVnF7lWeKCIJzaIkI0vYO87dMpZ4bg4TDrFe4XXLFWL1TbXU27gBP3QccxV9mZICCrnjnYlJjXHOA==", + "license": "MIT", + "dependencies": { + "@babel/helper-string-parser": "^7.25.9", + "@babel/helper-validator-identifier": "^7.25.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@casl/ability": { + "version": "6.3.3", + "resolved": "https://registry.npmjs.org/@casl/ability/-/ability-6.3.3.tgz", + "integrity": "sha512-UzbqsE9etu6QzZrRmqIyVun2kztAzJ46Tz7lC/2P2buCE6B6Ll7Vptz7JTQtGwapLbeKo2jS7dL966TVOQ7x4g==", + "dependencies": { + "@ucast/mongo2js": "^1.3.0" + }, + "funding": { + "url": "https://github.com/stalniy/casl/blob/master/BACKERS.md" + } + }, + "node_modules/@casl/react": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@casl/react/-/react-3.1.0.tgz", + "integrity": "sha512-p4Xmex1Slxz/G0cBtZik+xyOkeOynBUe0UrMFTai6aYkYOb4NyUy3w+9rtnedjcuKijiow2HKJQjnSurLxdc/g==", + "peerDependencies": { + "@casl/ability": "^3.0.0 || ^4.0.0 || ^5.1.0 || ^6.0.0", + "react": "^16.0.0 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/@dnd-kit/accessibility": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@dnd-kit/accessibility/-/accessibility-3.1.0.tgz", + "integrity": "sha512-ea7IkhKvlJUv9iSHJOnxinBcoOI3ppGnnL+VDJ75O45Nss6HtZd8IdN8touXPDtASfeI2T2LImb8VOZcL47wjQ==", + "dependencies": { + "tslib": "^2.0.0" + }, + "peerDependencies": { + "react": ">=16.8.0" + } + }, + "node_modules/@dnd-kit/core": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/@dnd-kit/core/-/core-6.1.0.tgz", + "integrity": "sha512-J3cQBClB4TVxwGo3KEjssGEXNJqGVWx17aRTZ1ob0FliR5IjYgTxl5YJbKTzA6IzrtelotH19v6y7uoIRUZPSg==", + "dependencies": { + "@dnd-kit/accessibility": "^3.1.0", + "@dnd-kit/utilities": "^3.2.2", + "tslib": "^2.0.0" + }, + "peerDependencies": { + "react": ">=16.8.0", + "react-dom": ">=16.8.0" + } + }, + "node_modules/@dnd-kit/sortable": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/@dnd-kit/sortable/-/sortable-8.0.0.tgz", + "integrity": "sha512-U3jk5ebVXe1Lr7c2wU7SBZjcWdQP+j7peHJfCspnA81enlu88Mgd7CC8Q+pub9ubP7eKVETzJW+IBAhsqbSu/g==", + "dependencies": { + "@dnd-kit/utilities": "^3.2.2", + "tslib": "^2.0.0" + }, + "peerDependencies": { + "@dnd-kit/core": "^6.1.0", + "react": ">=16.8.0" + } + }, + "node_modules/@dnd-kit/utilities": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/@dnd-kit/utilities/-/utilities-3.2.2.tgz", + "integrity": "sha512-+MKAJEOfaBe5SmV6t34p80MMKhjvUz0vRrvVJbPT0WElzaOJ/1xs+D+KDv+tD/NE5ujfrChEcshd4fLn0wpiqg==", + "dependencies": { + "tslib": "^2.0.0" + }, + "peerDependencies": { + "react": ">=16.8.0" + } + }, + "node_modules/@emotion/babel-plugin": { + "version": "11.13.5", + "resolved": "https://registry.npmjs.org/@emotion/babel-plugin/-/babel-plugin-11.13.5.tgz", + "integrity": "sha512-pxHCpT2ex+0q+HH91/zsdHkw/lXd468DIN2zvfvLtPKLLMo6gQj7oLObq8PhkrxOZb/gGCq03S3Z7PDhS8pduQ==", + "license": "MIT", + "dependencies": { + "@babel/helper-module-imports": "^7.16.7", + "@babel/runtime": "^7.18.3", + "@emotion/hash": "^0.9.2", + "@emotion/memoize": "^0.9.0", + "@emotion/serialize": "^1.3.3", + "babel-plugin-macros": "^3.1.0", + "convert-source-map": "^1.5.0", + "escape-string-regexp": "^4.0.0", + "find-root": "^1.1.0", + "source-map": "^0.5.7", + "stylis": "4.2.0" + } + }, + "node_modules/@emotion/cache": { + "version": "11.13.5", + "resolved": "https://registry.npmjs.org/@emotion/cache/-/cache-11.13.5.tgz", + "integrity": "sha512-Z3xbtJ+UcK76eWkagZ1onvn/wAVb1GOMuR15s30Fm2wrMgC7jzpnO2JZXr4eujTTqoQFUrZIw/rT0c6Zzjca1g==", + "license": "MIT", + "dependencies": { + "@emotion/memoize": "^0.9.0", + "@emotion/sheet": "^1.4.0", + "@emotion/utils": "^1.4.2", + "@emotion/weak-memoize": "^0.4.0", + "stylis": "4.2.0" + } + }, + "node_modules/@emotion/hash": { + "version": "0.9.2", + "resolved": "https://registry.npmjs.org/@emotion/hash/-/hash-0.9.2.tgz", + "integrity": "sha512-MyqliTZGuOm3+5ZRSaaBGP3USLw6+EGykkwZns2EPC5g8jJ4z9OrdZY9apkl3+UP9+sdz76YYkwCKP5gh8iY3g==", + "license": "MIT" + }, + "node_modules/@emotion/is-prop-valid": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/@emotion/is-prop-valid/-/is-prop-valid-1.3.0.tgz", + "integrity": "sha512-SHetuSLvJDzuNbOdtPVbq6yMMMlLoW5Q94uDqJZqy50gcmAjxFkVqmzqSGEFq9gT2iMuIeKV1PXVWmvUhuZLlQ==", + "dependencies": { + "@emotion/memoize": "^0.9.0" + } + }, + "node_modules/@emotion/memoize": { + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/@emotion/memoize/-/memoize-0.9.0.tgz", + "integrity": "sha512-30FAj7/EoJ5mwVPOWhAyCX+FPfMDrVecJAM+Iw9NRoSl4BBAQeqj4cApHHUXOVvIPgLVDsCFoz/hGD+5QQD1GQ==" + }, + "node_modules/@emotion/react": { + "version": "11.13.5", + "resolved": "https://registry.npmjs.org/@emotion/react/-/react-11.13.5.tgz", + "integrity": "sha512-6zeCUxUH+EPF1s+YF/2hPVODeV/7V07YU5x+2tfuRL8MdW6rv5vb2+CBEGTGwBdux0OIERcOS+RzxeK80k2DsQ==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.18.3", + "@emotion/babel-plugin": "^11.13.5", + "@emotion/cache": "^11.13.5", + "@emotion/serialize": "^1.3.3", + "@emotion/use-insertion-effect-with-fallbacks": "^1.1.0", + "@emotion/utils": "^1.4.2", + "@emotion/weak-memoize": "^0.4.0", + "hoist-non-react-statics": "^3.3.1" + }, + "peerDependencies": { + "react": ">=16.8.0" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@emotion/serialize": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/@emotion/serialize/-/serialize-1.3.3.tgz", + "integrity": "sha512-EISGqt7sSNWHGI76hC7x1CksiXPahbxEOrC5RjmFRJTqLyEK9/9hZvBbiYn70dw4wuwMKiEMCUlR6ZXTSWQqxA==", + "license": "MIT", + "dependencies": { + "@emotion/hash": "^0.9.2", + "@emotion/memoize": "^0.9.0", + "@emotion/unitless": "^0.10.0", + "@emotion/utils": "^1.4.2", + "csstype": "^3.0.2" + } + }, + "node_modules/@emotion/server": { + "version": "11.11.0", + "resolved": "https://registry.npmjs.org/@emotion/server/-/server-11.11.0.tgz", + "integrity": "sha512-6q89fj2z8VBTx9w93kJ5n51hsmtYuFPtZgnc1L8VzRx9ti4EU6EyvF6Nn1H1x3vcCQCF7u2dB2lY4AYJwUW4PA==", + "license": "MIT", + "dependencies": { + "@emotion/utils": "^1.2.1", + "html-tokenize": "^2.0.0", + "multipipe": "^1.0.2", + "through": "^2.3.8" + }, + "peerDependencies": { + "@emotion/css": "^11.0.0-rc.0" + }, + "peerDependenciesMeta": { + "@emotion/css": { + "optional": true + } + } + }, + "node_modules/@emotion/sheet": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/@emotion/sheet/-/sheet-1.4.0.tgz", + "integrity": "sha512-fTBW9/8r2w3dXWYM4HCB1Rdp8NLibOw2+XELH5m5+AkWiL/KqYX6dc0kKYlaYyKjrQ6ds33MCdMPEwgs2z1rqg==" + }, + "node_modules/@emotion/styled": { + "version": "11.13.5", + "resolved": "https://registry.npmjs.org/@emotion/styled/-/styled-11.13.5.tgz", + "integrity": "sha512-gnOQ+nGLPvDXgIx119JqGalys64lhMdnNQA9TMxhDA4K0Hq5+++OE20Zs5GxiCV9r814xQ2K5WmtofSpHVW6BQ==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.18.3", + "@emotion/babel-plugin": "^11.13.5", + "@emotion/is-prop-valid": "^1.3.0", + "@emotion/serialize": "^1.3.3", + "@emotion/use-insertion-effect-with-fallbacks": "^1.1.0", + "@emotion/utils": "^1.4.2" + }, + "peerDependencies": { + "@emotion/react": "^11.0.0-rc.0", + "react": ">=16.8.0" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@emotion/unitless": { + "version": "0.10.0", + "resolved": "https://registry.npmjs.org/@emotion/unitless/-/unitless-0.10.0.tgz", + "integrity": "sha512-dFoMUuQA20zvtVTuxZww6OHoJYgrzfKM1t52mVySDJnMSEa08ruEvdYQbhvyu6soU+NeLVd3yKfTfT0NeV6qGg==", + "license": "MIT" + }, + "node_modules/@emotion/use-insertion-effect-with-fallbacks": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@emotion/use-insertion-effect-with-fallbacks/-/use-insertion-effect-with-fallbacks-1.1.0.tgz", + "integrity": "sha512-+wBOcIV5snwGgI2ya3u99D7/FJquOIniQT1IKyDsBmEgwvpxMNeS65Oib7OnE2d2aY+3BU4OiH+0Wchf8yk3Hw==", + "license": "MIT", + "peerDependencies": { + "react": ">=16.8.0" + } + }, + "node_modules/@emotion/utils": { + "version": "1.4.2", + "resolved": "https://registry.npmjs.org/@emotion/utils/-/utils-1.4.2.tgz", + "integrity": "sha512-3vLclRofFziIa3J2wDh9jjbkUz9qk5Vi3IZ/FSTKViB0k+ef0fPV7dYrUIugbgupYDx7v9ud/SjrtEP8Y4xLoA==", + "license": "MIT" + }, + "node_modules/@emotion/weak-memoize": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/@emotion/weak-memoize/-/weak-memoize-0.4.0.tgz", + "integrity": "sha512-snKqtPW01tN0ui7yu9rGv69aJXr/a/Ywvl11sUjNtEcRc+ng/mQriFL0wLXMef74iHa/EkftbDzU9F8iFbH+zg==", + "license": "MIT" + }, + "node_modules/@esbuild/aix-ppc64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.24.0.tgz", + "integrity": "sha512-WtKdFM7ls47zkKHFVzMz8opM7LkcsIp9amDUBIAWirg70RM71WRSjdILPsY5Uv1D42ZpUfaPILDlfactHgsRkw==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "aix" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/android-arm": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.24.0.tgz", + "integrity": "sha512-arAtTPo76fJ/ICkXWetLCc9EwEHKaeya4vMrReVlEIUCAUncH7M4bhMQ+M9Vf+FFOZJdTNMXNBrWwW+OXWpSew==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/android-arm64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.24.0.tgz", + "integrity": "sha512-Vsm497xFM7tTIPYK9bNTYJyF/lsP590Qc1WxJdlB6ljCbdZKU9SY8i7+Iin4kyhV/KV5J2rOKsBQbB77Ab7L/w==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/android-x64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.24.0.tgz", + "integrity": "sha512-t8GrvnFkiIY7pa7mMgJd7p8p8qqYIz1NYiAoKc75Zyv73L3DZW++oYMSHPRarcotTKuSs6m3hTOa5CKHaS02TQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/darwin-arm64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.24.0.tgz", + "integrity": "sha512-CKyDpRbK1hXwv79soeTJNHb5EiG6ct3efd/FTPdzOWdbZZfGhpbcqIpiD0+vwmpu0wTIL97ZRPZu8vUt46nBSw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/darwin-x64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.24.0.tgz", + "integrity": "sha512-rgtz6flkVkh58od4PwTRqxbKH9cOjaXCMZgWD905JOzjFKW+7EiUObfd/Kav+A6Gyud6WZk9w+xu6QLytdi2OA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/freebsd-arm64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.24.0.tgz", + "integrity": "sha512-6Mtdq5nHggwfDNLAHkPlyLBpE5L6hwsuXZX8XNmHno9JuL2+bg2BX5tRkwjyfn6sKbxZTq68suOjgWqCicvPXA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/freebsd-x64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.24.0.tgz", + "integrity": "sha512-D3H+xh3/zphoX8ck4S2RxKR6gHlHDXXzOf6f/9dbFt/NRBDIE33+cVa49Kil4WUjxMGW0ZIYBYtaGCa2+OsQwQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-arm": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.24.0.tgz", + "integrity": "sha512-gJKIi2IjRo5G6Glxb8d3DzYXlxdEj2NlkixPsqePSZMhLudqPhtZ4BUrpIuTjJYXxvF9njql+vRjB2oaC9XpBw==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-arm64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.24.0.tgz", + "integrity": "sha512-TDijPXTOeE3eaMkRYpcy3LarIg13dS9wWHRdwYRnzlwlA370rNdZqbcp0WTyyV/k2zSxfko52+C7jU5F9Tfj1g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-ia32": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.24.0.tgz", + "integrity": "sha512-K40ip1LAcA0byL05TbCQ4yJ4swvnbzHscRmUilrmP9Am7//0UjPreh4lpYzvThT2Quw66MhjG//20mrufm40mA==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-loong64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.24.0.tgz", + "integrity": "sha512-0mswrYP/9ai+CU0BzBfPMZ8RVm3RGAN/lmOMgW4aFUSOQBjA31UP8Mr6DDhWSuMwj7jaWOT0p0WoZ6jeHhrD7g==", + "cpu": [ + "loong64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-mips64el": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.24.0.tgz", + "integrity": "sha512-hIKvXm0/3w/5+RDtCJeXqMZGkI2s4oMUGj3/jM0QzhgIASWrGO5/RlzAzm5nNh/awHE0A19h/CvHQe6FaBNrRA==", + "cpu": [ + "mips64el" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-ppc64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.24.0.tgz", + "integrity": "sha512-HcZh5BNq0aC52UoocJxaKORfFODWXZxtBaaZNuN3PUX3MoDsChsZqopzi5UupRhPHSEHotoiptqikjN/B77mYQ==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-riscv64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.24.0.tgz", + "integrity": "sha512-bEh7dMn/h3QxeR2KTy1DUszQjUrIHPZKyO6aN1X4BCnhfYhuQqedHaa5MxSQA/06j3GpiIlFGSsy1c7Gf9padw==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-s390x": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.24.0.tgz", + "integrity": "sha512-ZcQ6+qRkw1UcZGPyrCiHHkmBaj9SiCD8Oqd556HldP+QlpUIe2Wgn3ehQGVoPOvZvtHm8HPx+bH20c9pvbkX3g==", + "cpu": [ + "s390x" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-x64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.24.0.tgz", + "integrity": "sha512-vbutsFqQ+foy3wSSbmjBXXIJ6PL3scghJoM8zCL142cGaZKAdCZHyf+Bpu/MmX9zT9Q0zFBVKb36Ma5Fzfa8xA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/netbsd-x64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.24.0.tgz", + "integrity": "sha512-hjQ0R/ulkO8fCYFsG0FZoH+pWgTTDreqpqY7UnQntnaKv95uP5iW3+dChxnx7C3trQQU40S+OgWhUVwCjVFLvg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/openbsd-arm64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-arm64/-/openbsd-arm64-0.24.0.tgz", + "integrity": "sha512-MD9uzzkPQbYehwcN583yx3Tu5M8EIoTD+tUgKF982WYL9Pf5rKy9ltgD0eUgs8pvKnmizxjXZyLt0z6DC3rRXg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/openbsd-x64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.24.0.tgz", + "integrity": "sha512-4ir0aY1NGUhIC1hdoCzr1+5b43mw99uNwVzhIq1OY3QcEwPDO3B7WNXBzaKY5Nsf1+N11i1eOfFcq+D/gOS15Q==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/sunos-x64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.24.0.tgz", + "integrity": "sha512-jVzdzsbM5xrotH+W5f1s+JtUy1UWgjU0Cf4wMvffTB8m6wP5/kx0KiaLHlbJO+dMgtxKV8RQ/JvtlFcdZ1zCPA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "sunos" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/win32-arm64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.24.0.tgz", + "integrity": "sha512-iKc8GAslzRpBytO2/aN3d2yb2z8XTVfNV0PjGlCxKo5SgWmNXx82I/Q3aG1tFfS+A2igVCY97TJ8tnYwpUWLCA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/win32-ia32": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.24.0.tgz", + "integrity": "sha512-vQW36KZolfIudCcTnaTpmLQ24Ha1RjygBo39/aLkM2kmjkWmZGEJ5Gn9l5/7tzXA42QGIoWbICfg6KLLkIw6yw==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/win32-x64": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.24.0.tgz", + "integrity": "sha512-7IAFPrjSQIJrGsK6flwg7NFmwBoSTyF3rl7If0hNUFQU4ilTsEPL6GuMuU9BfIWVVGuRnuIidkSMC+c0Otu8IA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@eslint-community/eslint-utils": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.4.0.tgz", + "integrity": "sha512-1/sA4dwrzBAyeUoQ6oxahHKmrZvsnLCg4RfxW3ZFGGmQkSNQPFNLV9CUEFQP1x9EYXHTo5p6xdhZM1Ne9p/AfA==", + "dev": true, + "dependencies": { + "eslint-visitor-keys": "^3.3.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "peerDependencies": { + "eslint": "^6.0.0 || ^7.0.0 || >=8.0.0" + } + }, + "node_modules/@eslint-community/regexpp": { + "version": "4.11.1", + "resolved": "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.11.1.tgz", + "integrity": "sha512-m4DVN9ZqskZoLU5GlWZadwDnYo3vAEydiUayB9widCl9ffWx2IvPnp6n3on5rJmziJSw9Bv+Z3ChDVdMwXCY8Q==", + "dev": true, + "engines": { + "node": "^12.0.0 || ^14.0.0 || >=16.0.0" + } + }, + "node_modules/@eslint/eslintrc": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-2.1.4.tgz", + "integrity": "sha512-269Z39MS6wVJtsoUl10L60WdkhJVdPG24Q4eZTH3nnF6lpvSShEK3wQjDX9JRWAUPvPh7COouPpU9IrqaZFvtQ==", + "dev": true, + "dependencies": { + "ajv": "^6.12.4", + "debug": "^4.3.2", + "espree": "^9.6.0", + "globals": "^13.19.0", + "ignore": "^5.2.0", + "import-fresh": "^3.2.1", + "js-yaml": "^4.1.0", + "minimatch": "^3.1.2", + "strip-json-comments": "^3.1.1" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/@eslint/eslintrc/node_modules/globals": { + "version": "13.24.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-13.24.0.tgz", + "integrity": "sha512-AhO5QUcj8llrbG09iWhPU2B204J1xnPeL8kQmVorSsy+Sjj1sk8gIyh6cUocGmH4L0UuhAJy+hJMRA4mgA4mFQ==", + "dev": true, + "dependencies": { + "type-fest": "^0.20.2" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/@eslint/js": { + "version": "8.44.0", + "resolved": "https://registry.npmjs.org/@eslint/js/-/js-8.44.0.tgz", + "integrity": "sha512-Ag+9YM4ocKQx9AarydN0KY2j0ErMHNIocPDrVo8zAE44xLTjEtz81OdR68/cydGtk6m6jDb5Za3r2useMzYmSw==", + "dev": true, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + } + }, + "node_modules/@floating-ui/core": { + "version": "1.6.8", + "resolved": "https://registry.npmjs.org/@floating-ui/core/-/core-1.6.8.tgz", + "integrity": "sha512-7XJ9cPU+yI2QeLS+FCSlqNFZJq8arvswefkZrYI1yQBbftw6FyrZOxYSh+9S7z7TpeWlRt9zJ5IhM1WIL334jA==", + "license": "MIT", + "dependencies": { + "@floating-ui/utils": "^0.2.8" + } + }, + "node_modules/@floating-ui/dom": { + "version": "1.6.12", + "resolved": "https://registry.npmjs.org/@floating-ui/dom/-/dom-1.6.12.tgz", + "integrity": "sha512-NP83c0HjokcGVEMeoStg317VD9W7eDlGK7457dMBANbKA6GJZdc7rjujdgqzTaz93jkGgc5P/jeWbaCHnMNc+w==", + "license": "MIT", + "dependencies": { + "@floating-ui/core": "^1.6.0", + "@floating-ui/utils": "^0.2.8" + } + }, + "node_modules/@floating-ui/react-dom": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.1.2.tgz", + "integrity": "sha512-06okr5cgPzMNBy+Ycse2A6udMi4bqwW/zgBF/rwjcNqWkyr82Mcg8b0vjX8OJpZFy/FKjJmw6wV7t44kK6kW7A==", + "license": "MIT", + "dependencies": { + "@floating-ui/dom": "^1.0.0" + }, + "peerDependencies": { + "react": ">=16.8.0", + "react-dom": ">=16.8.0" + } + }, + "node_modules/@floating-ui/utils": { + "version": "0.2.8", + "resolved": "https://registry.npmjs.org/@floating-ui/utils/-/utils-0.2.8.tgz", + "integrity": "sha512-kym7SodPp8/wloecOpcmSnWJsK7M0E5Wg8UcFA+uO4B9s5d0ywXOEro/8HM9x0rW+TljRzul/14UYz3TleT3ig==", + "license": "MIT" + }, + "node_modules/@hello-pangea/dnd": { + "version": "17.0.0", + "resolved": "https://registry.npmjs.org/@hello-pangea/dnd/-/dnd-17.0.0.tgz", + "integrity": "sha512-LDDPOix/5N0j5QZxubiW9T0M0+1PR0rTDWeZF5pu1Tz91UQnuVK4qQ/EjY83Qm2QeX0eM8qDXANfDh3VVqtR4Q==", + "license": "Apache-2.0", + "dependencies": { + "@babel/runtime": "^7.25.6", + "css-box-model": "^1.2.1", + "memoize-one": "^6.0.0", + "raf-schd": "^4.0.3", + "react-redux": "^9.1.2", + "redux": "^5.0.1", + "use-memo-one": "^1.1.3" + }, + "peerDependencies": { + "react": "^18.0.0", + "react-dom": "^18.0.0" + } + }, + "node_modules/@hello-pangea/dnd/node_modules/memoize-one": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/memoize-one/-/memoize-one-6.0.0.tgz", + "integrity": "sha512-rkpe71W0N0c0Xz6QD0eJETuWAJGnJ9afsl1srmwPrI+yBCkge5EycXXbYRyvL29zZVUWQCY7InPRCv3GDXuZNw==", + "license": "MIT" + }, + "node_modules/@humanwhocodes/config-array": { + "version": "0.11.14", + "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.11.14.tgz", + "integrity": "sha512-3T8LkOmg45BV5FICb15QQMsyUSWrQ8AygVfC7ZG32zOalnqrilm018ZVCw0eapXux8FtA33q8PSRSstjee3jSg==", + "deprecated": "Use @eslint/config-array instead", + "dev": true, + "dependencies": { + "@humanwhocodes/object-schema": "^2.0.2", + "debug": "^4.3.1", + "minimatch": "^3.0.5" + }, + "engines": { + "node": ">=10.10.0" + } + }, + "node_modules/@humanwhocodes/module-importer": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz", + "integrity": "sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==", + "dev": true, + "engines": { + "node": ">=12.22" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/nzakas" + } + }, + "node_modules/@humanwhocodes/object-schema": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/@humanwhocodes/object-schema/-/object-schema-2.0.3.tgz", + "integrity": "sha512-93zYdMES/c1D69yZiKDBj0V24vqNzB/koF26KPaagAfd3P/4gUlh3Dys5ogAK+Exi9QyzlD8x/08Zt7wIKcDcA==", + "deprecated": "Use @eslint/object-schema instead", + "dev": true + }, + "node_modules/@jridgewell/gen-mapping": { + "version": "0.3.5", + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.5.tgz", + "integrity": "sha512-IzL8ZoEDIBRWEzlCcRhOaCupYyN5gdIK+Q6fbFdPDg6HqX6jpkItn7DFIpW9LQzXG6Df9sA7+OKnq0qlz/GaQg==", + "dependencies": { + "@jridgewell/set-array": "^1.2.1", + "@jridgewell/sourcemap-codec": "^1.4.10", + "@jridgewell/trace-mapping": "^0.3.24" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/resolve-uri": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", + "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/set-array": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.2.1.tgz", + "integrity": "sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==", + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/sourcemap-codec": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.0.tgz", + "integrity": "sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==" + }, + "node_modules/@jridgewell/trace-mapping": { + "version": "0.3.25", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.25.tgz", + "integrity": "sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==", + "dependencies": { + "@jridgewell/resolve-uri": "^3.1.0", + "@jridgewell/sourcemap-codec": "^1.4.14" + } + }, + "node_modules/@mui/base": { + "version": "5.0.0-beta.58", + "resolved": "https://registry.npmjs.org/@mui/base/-/base-5.0.0-beta.58.tgz", + "integrity": "sha512-P0E7ZrxOuyYqBvVv9w8k7wm+Xzx/KRu+BGgFcR2htTsGCpJNQJCSUXNUZ50MUmSU9hzqhwbQWNXhV1MBTl6F7A==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.25.0", + "@floating-ui/react-dom": "^2.1.1", + "@mui/types": "^7.2.15", + "@mui/utils": "6.0.0-rc.0", + "@popperjs/core": "^2.11.8", + "clsx": "^2.1.1", + "prop-types": "^15.8.1" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@types/react": "^17.0.0 || ^18.0.0", + "react": "^17.0.0 || ^18.0.0", + "react-dom": "^17.0.0 || ^18.0.0" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@mui/base/node_modules/@mui/utils": { + "version": "6.0.0-rc.0", + "resolved": "https://registry.npmjs.org/@mui/utils/-/utils-6.0.0-rc.0.tgz", + "integrity": "sha512-tBp0ILEXDL0bbDDT8PnZOjCqSm5Dfk2N0Z45uzRw+wVl6fVvloC9zw8avl+OdX1Bg3ubs/ttKn8nRNv17bpM5A==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.25.0", + "@mui/types": "^7.2.15", + "@types/prop-types": "^15.7.12", + "clsx": "^2.1.1", + "prop-types": "^15.8.1", + "react-is": "^18.3.1" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@types/react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react": "^17.0.0 || ^18.0.0 || ^19.0.0" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@mui/core-downloads-tracker": { + "version": "6.1.8", + "resolved": "https://registry.npmjs.org/@mui/core-downloads-tracker/-/core-downloads-tracker-6.1.8.tgz", + "integrity": "sha512-TGAvzwUg9hybDacwfIGFjI2bXYXrIqky+vMfaeay8rvT56/PNAlvIDUJ54kpT5KRc9AWAihOvtDI7/LJOThOmQ==", + "license": "MIT", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + } + }, + "node_modules/@mui/icons-material": { + "version": "5.14.13", + "resolved": "https://registry.npmjs.org/@mui/icons-material/-/icons-material-5.14.13.tgz", + "integrity": "sha512-fxKE1UrjI4xVxHe9IAGuVQZrc18dSBJg0P+Sqi2SZmcDUCShmgRq6Jq7l7GduvuMIkOSqAJdNgLtXmtmZkjtLg==", + "dependencies": { + "@babel/runtime": "^7.23.1" + }, + "engines": { + "node": ">=12.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui" + }, + "peerDependencies": { + "@mui/material": "^5.0.0", + "@types/react": "^17.0.0 || ^18.0.0", + "react": "^17.0.0 || ^18.0.0" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@mui/lab": { + "version": "6.0.0-beta.10", + "resolved": "https://registry.npmjs.org/@mui/lab/-/lab-6.0.0-beta.10.tgz", + "integrity": "sha512-eqCBz5SZS8Un9To3UcjH01AxkOOgvme/g0ZstFC8Nz1Kg5/EJMA0ByhKS5AvUMzUKrv0FXMdbuPqbBvF3bVrXg==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.25.6", + "@mui/base": "5.0.0-beta.58", + "@mui/system": "^6.1.1", + "@mui/types": "^7.2.17", + "@mui/utils": "^6.1.1", + "clsx": "^2.1.1", + "prop-types": "^15.8.1" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@emotion/react": "^11.5.0", + "@emotion/styled": "^11.3.0", + "@mui/material": "^6.1.1", + "@mui/material-pigment-css": "^6.1.1", + "@types/react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react-dom": "^17.0.0 || ^18.0.0 || ^19.0.0" + }, + "peerDependenciesMeta": { + "@emotion/react": { + "optional": true + }, + "@emotion/styled": { + "optional": true + }, + "@mui/material-pigment-css": { + "optional": true + }, + "@types/react": { + "optional": true + } + } + }, + "node_modules/@mui/material": { + "version": "6.1.8", + "resolved": "https://registry.npmjs.org/@mui/material/-/material-6.1.8.tgz", + "integrity": "sha512-QZdQFnXct+7NXIzHgT3qt+sQiO7HYGZU2vymP9Xl9tUMXEOA/S1mZMMb7+WGZrk5TzNlU/kP/85K0da5V1jXoQ==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.26.0", + "@mui/core-downloads-tracker": "^6.1.8", + "@mui/system": "^6.1.8", + "@mui/types": "^7.2.19", + "@mui/utils": "^6.1.8", + "@popperjs/core": "^2.11.8", + "@types/react-transition-group": "^4.4.11", + "clsx": "^2.1.1", + "csstype": "^3.1.3", + "prop-types": "^15.8.1", + "react-is": "^18.3.1", + "react-transition-group": "^4.4.5" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@emotion/react": "^11.5.0", + "@emotion/styled": "^11.3.0", + "@mui/material-pigment-css": "^6.1.8", + "@types/react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react-dom": "^17.0.0 || ^18.0.0 || ^19.0.0" + }, + "peerDependenciesMeta": { + "@emotion/react": { + "optional": true + }, + "@emotion/styled": { + "optional": true + }, + "@mui/material-pigment-css": { + "optional": true + }, + "@types/react": { + "optional": true + } + } + }, + "node_modules/@mui/private-theming": { + "version": "6.1.10", + "resolved": "https://registry.npmjs.org/@mui/private-theming/-/private-theming-6.1.10.tgz", + "integrity": "sha512-DqgsH0XFEweeG3rQfVkqTkeXcj/E76PGYWag8flbPdV8IYdMo+DfVdFlZK8JEjsaIVD2Eu1kJg972XnH5pfnBQ==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.26.0", + "@mui/utils": "^6.1.10", + "prop-types": "^15.8.1" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@types/react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react": "^17.0.0 || ^18.0.0 || ^19.0.0" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@mui/styled-engine": { + "version": "6.1.10", + "resolved": "https://registry.npmjs.org/@mui/styled-engine/-/styled-engine-6.1.10.tgz", + "integrity": "sha512-+NV9adKZYhslJ270iPjf2yzdVJwav7CIaXcMlPSi1Xy1S/zRe5xFgZ6BEoMdmGRpr34lIahE8H1acXP2myrvRw==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.26.0", + "@emotion/cache": "^11.13.5", + "@emotion/serialize": "^1.3.3", + "@emotion/sheet": "^1.4.0", + "csstype": "^3.1.3", + "prop-types": "^15.8.1" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@emotion/react": "^11.4.1", + "@emotion/styled": "^11.3.0", + "react": "^17.0.0 || ^18.0.0 || ^19.0.0" + }, + "peerDependenciesMeta": { + "@emotion/react": { + "optional": true + }, + "@emotion/styled": { + "optional": true + } + } + }, + "node_modules/@mui/system": { + "version": "6.1.10", + "resolved": "https://registry.npmjs.org/@mui/system/-/system-6.1.10.tgz", + "integrity": "sha512-5YNIqxETR23SIkyP7MY2fFnXmplX/M4wNi2R+10AVRd3Ub+NLctWY/Vs5vq1oAMF0eSDLhRTGUjaUe+IGSfWqg==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.26.0", + "@mui/private-theming": "^6.1.10", + "@mui/styled-engine": "^6.1.10", + "@mui/types": "^7.2.19", + "@mui/utils": "^6.1.10", + "clsx": "^2.1.1", + "csstype": "^3.1.3", + "prop-types": "^15.8.1" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@emotion/react": "^11.5.0", + "@emotion/styled": "^11.3.0", + "@types/react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react": "^17.0.0 || ^18.0.0 || ^19.0.0" + }, + "peerDependenciesMeta": { + "@emotion/react": { + "optional": true + }, + "@emotion/styled": { + "optional": true + }, + "@types/react": { + "optional": true + } + } + }, + "node_modules/@mui/types": { + "version": "7.2.19", + "resolved": "https://registry.npmjs.org/@mui/types/-/types-7.2.19.tgz", + "integrity": "sha512-6XpZEM/Q3epK9RN8ENoXuygnqUQxE+siN/6rGRi2iwJPgBUR25mphYQ9ZI87plGh58YoZ5pp40bFvKYOCDJ3tA==", + "license": "MIT", + "peerDependencies": { + "@types/react": "^17.0.0 || ^18.0.0 || ^19.0.0" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@mui/utils": { + "version": "6.1.10", + "resolved": "https://registry.npmjs.org/@mui/utils/-/utils-6.1.10.tgz", + "integrity": "sha512-1ETuwswGjUiAf2dP9TkBy8p49qrw2wXa+RuAjNTRE5+91vtXJ1HKrs7H9s8CZd1zDlQVzUcUAPm9lpQwF5ogTw==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.26.0", + "@mui/types": "^7.2.19", + "@types/prop-types": "^15.7.13", + "clsx": "^2.1.1", + "prop-types": "^15.8.1", + "react-is": "^18.3.1" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@types/react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react": "^17.0.0 || ^18.0.0 || ^19.0.0" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@mui/x-charts": { + "version": "7.23.1", + "resolved": "https://registry.npmjs.org/@mui/x-charts/-/x-charts-7.23.1.tgz", + "integrity": "sha512-hIVRitRSFxf60BHDr+T7Tarj4lLwOV8flebeIsyEPJJHvSlaFNFwr6rqYFb8SGULYU7ppKMhiESD1+YqgJSU1Q==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.25.7", + "@mui/utils": "^5.16.6 || ^6.0.0", + "@mui/x-charts-vendor": "7.20.0", + "@mui/x-internals": "7.23.0", + "@react-spring/rafz": "^9.7.5", + "@react-spring/web": "^9.7.5", + "clsx": "^2.1.1", + "prop-types": "^15.8.1" + }, + "engines": { + "node": ">=14.0.0" + }, + "peerDependencies": { + "@emotion/react": "^11.9.0", + "@emotion/styled": "^11.8.1", + "@mui/material": "^5.15.14 || ^6.0.0", + "@mui/system": "^5.15.14 || ^6.0.0", + "react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react-dom": "^17.0.0 || ^18.0.0 || ^19.0.0" + }, + "peerDependenciesMeta": { + "@emotion/react": { + "optional": true + }, + "@emotion/styled": { + "optional": true + } + } + }, + "node_modules/@mui/x-charts-vendor": { + "version": "7.20.0", + "resolved": "https://registry.npmjs.org/@mui/x-charts-vendor/-/x-charts-vendor-7.20.0.tgz", + "integrity": "sha512-pzlh7z/7KKs5o0Kk0oPcB+sY0+Dg7Q7RzqQowDQjpy5Slz6qqGsgOB5YUzn0L+2yRmvASc4Pe0914Ao3tMBogg==", + "license": "MIT AND ISC", + "dependencies": { + "@babel/runtime": "^7.25.7", + "@types/d3-color": "^3.1.3", + "@types/d3-delaunay": "^6.0.4", + "@types/d3-interpolate": "^3.0.4", + "@types/d3-scale": "^4.0.8", + "@types/d3-shape": "^3.1.6", + "@types/d3-time": "^3.0.3", + "d3-color": "^3.1.0", + "d3-delaunay": "^6.0.4", + "d3-interpolate": "^3.0.1", + "d3-scale": "^4.0.2", + "d3-shape": "^3.2.0", + "d3-time": "^3.1.0", + "delaunator": "^5.0.1", + "robust-predicates": "^3.0.2" + } + }, + "node_modules/@mui/x-charts/node_modules/@mui/x-internals": { + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@mui/x-internals/-/x-internals-7.23.0.tgz", + "integrity": "sha512-bPclKpqUiJYIHqmTxSzMVZi6MH51cQsn5U+8jskaTlo3J4QiMeCYJn/gn7YbeR9GOZFp8hetyHjoQoVHKRXCig==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.25.7", + "@mui/utils": "^5.16.6 || ^6.0.0" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "react": "^17.0.0 || ^18.0.0 || ^19.0.0" + } + }, + "node_modules/@mui/x-date-pickers": { + "version": "7.18.0", + "resolved": "https://registry.npmjs.org/@mui/x-date-pickers/-/x-date-pickers-7.18.0.tgz", + "integrity": "sha512-12tXIoMj9vpS8fS/bS3kWPCoVrH38vNGCxgplI0vOnUrN9rJuYJz3agLPJe1S0xciTw+9W8ZSe3soaW+owoz1Q==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.25.6", + "@mui/utils": "^5.16.6", + "@mui/x-internals": "7.18.0", + "@types/react-transition-group": "^4.4.11", + "clsx": "^2.1.1", + "prop-types": "^15.8.1", + "react-transition-group": "^4.4.5" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@emotion/react": "^11.9.0", + "@emotion/styled": "^11.8.1", + "@mui/material": "^5.15.14 || ^6.0.0", + "@mui/system": "^5.15.14 || ^6.0.0", + "date-fns": "^2.25.0 || ^3.2.0 || ^4.0.0", + "date-fns-jalali": "^2.13.0-0 || ^3.2.0-0", + "dayjs": "^1.10.7", + "luxon": "^3.0.2", + "moment": "^2.29.4", + "moment-hijri": "^2.1.2", + "moment-jalaali": "^0.7.4 || ^0.8.0 || ^0.9.0 || ^0.10.0", + "react": "^17.0.0 || ^18.0.0", + "react-dom": "^17.0.0 || ^18.0.0" + }, + "peerDependenciesMeta": { + "@emotion/react": { + "optional": true + }, + "@emotion/styled": { + "optional": true + }, + "date-fns": { + "optional": true + }, + "date-fns-jalali": { + "optional": true + }, + "dayjs": { + "optional": true + }, + "luxon": { + "optional": true + }, + "moment": { + "optional": true + }, + "moment-hijri": { + "optional": true + }, + "moment-jalaali": { + "optional": true + } + } + }, + "node_modules/@mui/x-date-pickers/node_modules/@mui/utils": { + "version": "5.16.6", + "resolved": "https://registry.npmjs.org/@mui/utils/-/utils-5.16.6.tgz", + "integrity": "sha512-tWiQqlhxAt3KENNiSRL+DIn9H5xNVK6Jjf70x3PnfQPz1MPBdh7yyIcAyVBT9xiw7hP3SomRhPR7hzBMBCjqEA==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.23.9", + "@mui/types": "^7.2.15", + "@types/prop-types": "^15.7.12", + "clsx": "^2.1.1", + "prop-types": "^15.8.1", + "react-is": "^18.3.1" + }, + "engines": { + "node": ">=12.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@types/react": "^17.0.0 || ^18.0.0", + "react": "^17.0.0 || ^18.0.0" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@mui/x-date-pickers/node_modules/@mui/x-internals": { + "version": "7.18.0", + "resolved": "https://registry.npmjs.org/@mui/x-internals/-/x-internals-7.18.0.tgz", + "integrity": "sha512-lzCHOWIR0cAIY1bGrWSprYerahbnH5C31ql/2OWCEjcngL2NAV1M6oKI2Vp4HheqzJ822c60UyWyapvyjSzY/A==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.25.6", + "@mui/utils": "^5.16.6" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "react": "^17.0.0 || ^18.0.0" + } + }, + "node_modules/@mui/x-internals": { + "version": "7.21.0", + "resolved": "https://registry.npmjs.org/@mui/x-internals/-/x-internals-7.21.0.tgz", + "integrity": "sha512-94YNyZ0BhK5Z+Tkr90RKf47IVCW8R/1MvdUhh6MCQg6sZa74jsX+x+gEZ4kzuCqOsuyTyxikeQ8vVuCIQiP7UQ==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.25.7", + "@mui/utils": "^5.16.6 || ^6.0.0" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "react": "^17.0.0 || ^18.0.0" + } + }, + "node_modules/@mui/x-tree-view": { + "version": "7.22.1", + "resolved": "https://registry.npmjs.org/@mui/x-tree-view/-/x-tree-view-7.22.1.tgz", + "integrity": "sha512-EdFuzAgHn+/b++oNbm8JuXiF4MbRW+Dg70+MNbp2fQi8U1J38kg1hwvIFQ6Wi2AEt3Dv9euaPMFJM+a/4pk5Ng==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.25.7", + "@mui/utils": "^5.16.6 || ^6.0.0", + "@mui/x-internals": "7.21.0", + "@types/react-transition-group": "^4.4.11", + "clsx": "^2.1.1", + "prop-types": "^15.8.1", + "react-transition-group": "^4.4.5" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mui-org" + }, + "peerDependencies": { + "@emotion/react": "^11.9.0", + "@emotion/styled": "^11.8.1", + "@mui/material": "^5.15.14 || ^6.0.0", + "@mui/system": "^5.15.14 || ^6.0.0", + "react": "^17.0.0 || ^18.0.0", + "react-dom": "^17.0.0 || ^18.0.0" + }, + "peerDependenciesMeta": { + "@emotion/react": { + "optional": true + }, + "@emotion/styled": { + "optional": true + } + } + }, + "node_modules/@next/eslint-plugin-next": { + "version": "15.0.3", + "resolved": "https://registry.npmjs.org/@next/eslint-plugin-next/-/eslint-plugin-next-15.0.3.tgz", + "integrity": "sha512-3Ln/nHq2V+v8uIaxCR6YfYo7ceRgZNXfTd3yW1ukTaFbO+/I8jNakrjYWODvG9BuR2v5kgVtH/C8r0i11quOgw==", + "dev": true, + "license": "MIT", + "dependencies": { + "fast-glob": "3.3.1" + } + }, + "node_modules/@next/eslint-plugin-next/node_modules/fast-glob": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.3.1.tgz", + "integrity": "sha512-kNFPyjhh5cKjrUltxs+wFx+ZkbRaxxmZ+X0ZU31SOsxCEtP9VPgtq2teZw1DebupL5GmDaNQ6yKMMVcM41iqDg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@nodelib/fs.stat": "^2.0.2", + "@nodelib/fs.walk": "^1.2.3", + "glob-parent": "^5.1.2", + "merge2": "^1.3.0", + "micromatch": "^4.0.4" + }, + "engines": { + "node": ">=8.6.0" + } + }, + "node_modules/@next/eslint-plugin-next/node_modules/glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "dev": true, + "license": "ISC", + "dependencies": { + "is-glob": "^4.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/@nodelib/fs.scandir": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", + "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", + "dev": true, + "dependencies": { + "@nodelib/fs.stat": "2.0.5", + "run-parallel": "^1.1.9" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nodelib/fs.stat": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", + "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", + "dev": true, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nodelib/fs.walk": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", + "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", + "dev": true, + "dependencies": { + "@nodelib/fs.scandir": "2.1.5", + "fastq": "^1.6.0" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nolyfill/is-core-module": { + "version": "1.0.39", + "resolved": "https://registry.npmjs.org/@nolyfill/is-core-module/-/is-core-module-1.0.39.tgz", + "integrity": "sha512-nn5ozdjYQpUCZlWGuxcJY/KpxkWQs4DcbMCmKojjyrYDEAGy4Ce19NN4v5MduafTwJlbKc99UA8YhSVqq9yPZA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12.4.0" + } + }, + "node_modules/@popperjs/core": { + "version": "2.11.8", + "resolved": "https://registry.npmjs.org/@popperjs/core/-/core-2.11.8.tgz", + "integrity": "sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A==", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/popperjs" + } + }, + "node_modules/@react-spring/animated": { + "version": "9.7.5", + "resolved": "https://registry.npmjs.org/@react-spring/animated/-/animated-9.7.5.tgz", + "integrity": "sha512-Tqrwz7pIlsSDITzxoLS3n/v/YCUHQdOIKtOJf4yL6kYVSDTSmVK1LI1Q3M/uu2Sx4X3pIWF3xLUhlsA6SPNTNg==", + "license": "MIT", + "dependencies": { + "@react-spring/shared": "~9.7.5", + "@react-spring/types": "~9.7.5" + }, + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/@react-spring/core": { + "version": "9.7.5", + "resolved": "https://registry.npmjs.org/@react-spring/core/-/core-9.7.5.tgz", + "integrity": "sha512-rmEqcxRcu7dWh7MnCcMXLvrf6/SDlSokLaLTxiPlAYi11nN3B5oiCUAblO72o+9z/87j2uzxa2Inm8UbLjXA+w==", + "license": "MIT", + "dependencies": { + "@react-spring/animated": "~9.7.5", + "@react-spring/shared": "~9.7.5", + "@react-spring/types": "~9.7.5" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/react-spring/donate" + }, + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/@react-spring/konva": { + "version": "9.7.5", + "resolved": "https://registry.npmjs.org/@react-spring/konva/-/konva-9.7.5.tgz", + "integrity": "sha512-BelrmyY6w0FGoNSEfSJltjQDUoW0Prxf+FzGjyLuLs+V9M9OM/aHnYqOlvQEfQsZx6C/ZiDOn5BZl8iH8SDf+Q==", + "license": "MIT", + "dependencies": { + "@react-spring/animated": "~9.7.5", + "@react-spring/core": "~9.7.5", + "@react-spring/shared": "~9.7.5", + "@react-spring/types": "~9.7.5" + }, + "peerDependencies": { + "konva": ">=2.6", + "react": "^16.8.0 || ^17.0.0 || ^18.0.0", + "react-konva": "^16.8.0 || ^16.8.7-0 || ^16.9.0-0 || ^16.10.1-0 || ^16.12.0-0 || ^16.13.0-0 || ^17.0.0-0 || ^17.0.1-0 || ^17.0.2-0 || ^18.0.0-0" + } + }, + "node_modules/@react-spring/native": { + "version": "9.7.5", + "resolved": "https://registry.npmjs.org/@react-spring/native/-/native-9.7.5.tgz", + "integrity": "sha512-C1S500BNP1I05MftElyLv2nIqaWQ0MAByOAK/p4vuXcUK3XcjFaAJ385gVLgV2rgKfvkqRoz97PSwbh+ZCETEg==", + "license": "MIT", + "dependencies": { + "@react-spring/animated": "~9.7.5", + "@react-spring/core": "~9.7.5", + "@react-spring/shared": "~9.7.5", + "@react-spring/types": "~9.7.5" + }, + "peerDependencies": { + "react": "16.8.0 || >=17.0.0 || >=18.0.0", + "react-native": ">=0.58" + } + }, + "node_modules/@react-spring/rafz": { + "version": "9.7.5", + "resolved": "https://registry.npmjs.org/@react-spring/rafz/-/rafz-9.7.5.tgz", + "integrity": "sha512-5ZenDQMC48wjUzPAm1EtwQ5Ot3bLIAwwqP2w2owG5KoNdNHpEJV263nGhCeKKmuA3vG2zLLOdu3or6kuDjA6Aw==", + "license": "MIT" + }, + "node_modules/@react-spring/shared": { + "version": "9.7.5", + "resolved": "https://registry.npmjs.org/@react-spring/shared/-/shared-9.7.5.tgz", + "integrity": "sha512-wdtoJrhUeeyD/PP/zo+np2s1Z820Ohr/BbuVYv+3dVLW7WctoiN7std8rISoYoHpUXtbkpesSKuPIw/6U1w1Pw==", + "license": "MIT", + "dependencies": { + "@react-spring/rafz": "~9.7.5", + "@react-spring/types": "~9.7.5" + }, + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/@react-spring/three": { + "version": "9.7.5", + "resolved": "https://registry.npmjs.org/@react-spring/three/-/three-9.7.5.tgz", + "integrity": "sha512-RxIsCoQfUqOS3POmhVHa1wdWS0wyHAUway73uRLp3GAL5U2iYVNdnzQsep6M2NZ994BlW8TcKuMtQHUqOsy6WA==", + "license": "MIT", + "dependencies": { + "@react-spring/animated": "~9.7.5", + "@react-spring/core": "~9.7.5", + "@react-spring/shared": "~9.7.5", + "@react-spring/types": "~9.7.5" + }, + "peerDependencies": { + "@react-three/fiber": ">=6.0", + "react": "^16.8.0 || ^17.0.0 || ^18.0.0", + "three": ">=0.126" + } + }, + "node_modules/@react-spring/types": { + "version": "9.7.5", + "resolved": "https://registry.npmjs.org/@react-spring/types/-/types-9.7.5.tgz", + "integrity": "sha512-HVj7LrZ4ReHWBimBvu2SKND3cDVUPWKLqRTmWe/fNY6o1owGOX0cAHbdPDTMelgBlVbrTKrre6lFkhqGZErK/g==", + "license": "MIT" + }, + "node_modules/@react-spring/web": { + "version": "9.7.5", + "resolved": "https://registry.npmjs.org/@react-spring/web/-/web-9.7.5.tgz", + "integrity": "sha512-lmvqGwpe+CSttsWNZVr+Dg62adtKhauGwLyGE/RRyZ8AAMLgb9x3NDMA5RMElXo+IMyTkPp7nxTB8ZQlmhb6JQ==", + "license": "MIT", + "dependencies": { + "@react-spring/animated": "~9.7.5", + "@react-spring/core": "~9.7.5", + "@react-spring/shared": "~9.7.5", + "@react-spring/types": "~9.7.5" + }, + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0", + "react-dom": "^16.8.0 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/@react-spring/zdog": { + "version": "9.7.5", + "resolved": "https://registry.npmjs.org/@react-spring/zdog/-/zdog-9.7.5.tgz", + "integrity": "sha512-VV7vmb52wGHgDA1ry6hv+QgxTs78fqjKEQnj+M8hiBg+dwOsTtqqM24ADtc4cMAhPW+eZhVps8ZNKtjt8ouHFA==", + "license": "MIT", + "dependencies": { + "@react-spring/animated": "~9.7.5", + "@react-spring/core": "~9.7.5", + "@react-spring/shared": "~9.7.5", + "@react-spring/types": "~9.7.5" + }, + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0", + "react-dom": "^16.8.0 || ^17.0.0 || ^18.0.0", + "react-zdog": ">=1.0", + "zdog": ">=1.0" + } + }, + "node_modules/@reduxjs/toolkit": { + "version": "2.2.3", + "resolved": "https://registry.npmjs.org/@reduxjs/toolkit/-/toolkit-2.2.3.tgz", + "integrity": "sha512-76dll9EnJXg4EVcI5YNxZA/9hSAmZsFqzMmNRHvIlzw2WS/twfcVX3ysYrWGJMClwEmChQFC4yRq74tn6fdzRA==", + "license": "MIT", + "dependencies": { + "immer": "^10.0.3", + "redux": "^5.0.1", + "redux-thunk": "^3.1.0", + "reselect": "^5.0.1" + }, + "peerDependencies": { + "react": "^16.9.0 || ^17.0.0 || ^18", + "react-redux": "^7.2.1 || ^8.1.3 || ^9.0.0" + }, + "peerDependenciesMeta": { + "react": { + "optional": true + }, + "react-redux": { + "optional": true + } + } + }, + "node_modules/@remirror/core-constants": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@remirror/core-constants/-/core-constants-3.0.0.tgz", + "integrity": "sha512-42aWfPrimMfDKDi4YegyS7x+/0tlzaqwPQCULLanv3DMIlu96KTJR0fM5isWX2UViOqlGnX6YFgqWepcX+XMNg==", + "license": "MIT" + }, + "node_modules/@restart/hooks": { + "version": "0.4.16", + "resolved": "https://registry.npmjs.org/@restart/hooks/-/hooks-0.4.16.tgz", + "integrity": "sha512-f7aCv7c+nU/3mF7NWLtVVr0Ra80RqsO89hO72r+Y/nvQr5+q0UFGkocElTH6MJApvReVh6JHUFYn2cw1WdHF3w==", + "dependencies": { + "dequal": "^2.0.3" + }, + "peerDependencies": { + "react": ">=16.8.0" + } + }, + "node_modules/@rollup/pluginutils": { + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/@rollup/pluginutils/-/pluginutils-5.1.3.tgz", + "integrity": "sha512-Pnsb6f32CD2W3uCaLZIzDmeFyQ2b8UWMFI7xtwUezpcGBDVDW6y9XgAWIlARiGAo6eNF5FK5aQTr0LFyNyqq5A==", + "license": "MIT", + "dependencies": { + "@types/estree": "^1.0.0", + "estree-walker": "^2.0.2", + "picomatch": "^4.0.2" + }, + "engines": { + "node": ">=14.0.0" + }, + "peerDependencies": { + "rollup": "^1.20.0||^2.0.0||^3.0.0||^4.0.0" + }, + "peerDependenciesMeta": { + "rollup": { + "optional": true + } + } + }, + "node_modules/@rollup/pluginutils/node_modules/picomatch": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.2.tgz", + "integrity": "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==", + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, + "node_modules/@rollup/rollup-android-arm-eabi": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.27.4.tgz", + "integrity": "sha512-2Y3JT6f5MrQkICUyRVCw4oa0sutfAsgaSsb0Lmmy1Wi2y7X5vT9Euqw4gOsCyy0YfKURBg35nhUKZS4mDcfULw==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@rollup/rollup-android-arm64": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.27.4.tgz", + "integrity": "sha512-wzKRQXISyi9UdCVRqEd0H4cMpzvHYt1f/C3CoIjES6cG++RHKhrBj2+29nPF0IB5kpy9MS71vs07fvrNGAl/iA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@rollup/rollup-darwin-arm64": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.27.4.tgz", + "integrity": "sha512-PlNiRQapift4LNS8DPUHuDX/IdXiLjf8mc5vdEmUR0fF/pyy2qWwzdLjB+iZquGr8LuN4LnUoSEvKRwjSVYz3Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@rollup/rollup-darwin-x64": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.27.4.tgz", + "integrity": "sha512-o9bH2dbdgBDJaXWJCDTNDYa171ACUdzpxSZt+u/AAeQ20Nk5x+IhA+zsGmrQtpkLiumRJEYef68gcpn2ooXhSQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@rollup/rollup-freebsd-arm64": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.27.4.tgz", + "integrity": "sha512-NBI2/i2hT9Q+HySSHTBh52da7isru4aAAo6qC3I7QFVsuhxi2gM8t/EI9EVcILiHLj1vfi+VGGPaLOUENn7pmw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ] + }, + "node_modules/@rollup/rollup-freebsd-x64": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.27.4.tgz", + "integrity": "sha512-wYcC5ycW2zvqtDYrE7deary2P2UFmSh85PUpAx+dwTCO9uw3sgzD6Gv9n5X4vLaQKsrfTSZZ7Z7uynQozPVvWA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ] + }, + "node_modules/@rollup/rollup-linux-arm-gnueabihf": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.27.4.tgz", + "integrity": "sha512-9OwUnK/xKw6DyRlgx8UizeqRFOfi9mf5TYCw1uolDaJSbUmBxP85DE6T4ouCMoN6pXw8ZoTeZCSEfSaYo+/s1w==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm-musleabihf": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.27.4.tgz", + "integrity": "sha512-Vgdo4fpuphS9V24WOV+KwkCVJ72u7idTgQaBoLRD0UxBAWTF9GWurJO9YD9yh00BzbkhpeXtm6na+MvJU7Z73A==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm64-gnu": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.27.4.tgz", + "integrity": "sha512-pleyNgyd1kkBkw2kOqlBx+0atfIIkkExOTiifoODo6qKDSpnc6WzUY5RhHdmTdIJXBdSnh6JknnYTtmQyobrVg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm64-musl": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.27.4.tgz", + "integrity": "sha512-caluiUXvUuVyCHr5DxL8ohaaFFzPGmgmMvwmqAITMpV/Q+tPoaHZ/PWa3t8B2WyoRcIIuu1hkaW5KkeTDNSnMA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-powerpc64le-gnu": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-powerpc64le-gnu/-/rollup-linux-powerpc64le-gnu-4.27.4.tgz", + "integrity": "sha512-FScrpHrO60hARyHh7s1zHE97u0KlT/RECzCKAdmI+LEoC1eDh/RDji9JgFqyO+wPDb86Oa/sXkily1+oi4FzJQ==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-riscv64-gnu": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.27.4.tgz", + "integrity": "sha512-qyyprhyGb7+RBfMPeww9FlHwKkCXdKHeGgSqmIXw9VSUtvyFZ6WZRtnxgbuz76FK7LyoN8t/eINRbPUcvXB5fw==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-s390x-gnu": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.27.4.tgz", + "integrity": "sha512-PFz+y2kb6tbh7m3A7nA9++eInGcDVZUACulf/KzDtovvdTizHpZaJty7Gp0lFwSQcrnebHOqxF1MaKZd7psVRg==", + "cpu": [ + "s390x" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-x64-gnu": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.27.4.tgz", + "integrity": "sha512-Ni8mMtfo+o/G7DVtweXXV/Ol2TFf63KYjTtoZ5f078AUgJTmaIJnj4JFU7TK/9SVWTaSJGxPi5zMDgK4w+Ez7Q==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-x64-musl": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.27.4.tgz", + "integrity": "sha512-5AeeAF1PB9TUzD+3cROzFTnAJAcVUGLuR8ng0E0WXGkYhp6RD6L+6szYVX+64Rs0r72019KHZS1ka1q+zU/wUw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-win32-arm64-msvc": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.27.4.tgz", + "integrity": "sha512-yOpVsA4K5qVwu2CaS3hHxluWIK5HQTjNV4tWjQXluMiiiu4pJj4BN98CvxohNCpcjMeTXk/ZMJBRbgRg8HBB6A==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-ia32-msvc": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.27.4.tgz", + "integrity": "sha512-KtwEJOaHAVJlxV92rNYiG9JQwQAdhBlrjNRp7P9L8Cb4Rer3in+0A+IPhJC9y68WAi9H0sX4AiG2NTsVlmqJeQ==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-x64-msvc": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.27.4.tgz", + "integrity": "sha512-3j4jx1TppORdTAoBJRd+/wJRGCPC0ETWkXOecJ6PPZLj6SptXkrXcNqdj0oclbKML6FkQltdz7bBA3rUSirZug==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rtsao/scc": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@rtsao/scc/-/scc-1.1.0.tgz", + "integrity": "sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==", + "dev": true, + "license": "MIT" + }, + "node_modules/@rushstack/eslint-patch": { + "version": "1.10.4", + "resolved": "https://registry.npmjs.org/@rushstack/eslint-patch/-/eslint-patch-1.10.4.tgz", + "integrity": "sha512-WJgX9nzTqknM393q1QJDJmoW28kUfEnybeTfVNcNAPnIx210RXm2DiXiHzfNPJNIUUb1tJnz/l4QGtJ30PgWmA==", + "dev": true, + "license": "MIT" + }, + "node_modules/@svgr/babel-plugin-add-jsx-attribute": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-add-jsx-attribute/-/babel-plugin-add-jsx-attribute-8.0.0.tgz", + "integrity": "sha512-b9MIk7yhdS1pMCZM8VeNfUlSKVRhsHZNMl5O9SfaX0l0t5wjdgu4IDzGB8bpnGBBOjGST3rRFVsaaEtI4W6f7g==", + "license": "MIT", + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@svgr/babel-plugin-remove-jsx-attribute": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-remove-jsx-attribute/-/babel-plugin-remove-jsx-attribute-8.0.0.tgz", + "integrity": "sha512-BcCkm/STipKvbCl6b7QFrMh/vx00vIP63k2eM66MfHJzPr6O2U0jYEViXkHJWqXqQYjdeA9cuCl5KWmlwjDvbA==", + "license": "MIT", + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@svgr/babel-plugin-remove-jsx-empty-expression": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-remove-jsx-empty-expression/-/babel-plugin-remove-jsx-empty-expression-8.0.0.tgz", + "integrity": "sha512-5BcGCBfBxB5+XSDSWnhTThfI9jcO5f0Ai2V24gZpG+wXF14BzwxxdDb4g6trdOux0rhibGs385BeFMSmxtS3uA==", + "license": "MIT", + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@svgr/babel-plugin-replace-jsx-attribute-value": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-replace-jsx-attribute-value/-/babel-plugin-replace-jsx-attribute-value-8.0.0.tgz", + "integrity": "sha512-KVQ+PtIjb1BuYT3ht8M5KbzWBhdAjjUPdlMtpuw/VjT8coTrItWX6Qafl9+ji831JaJcu6PJNKCV0bp01lBNzQ==", + "license": "MIT", + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@svgr/babel-plugin-svg-dynamic-title": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-svg-dynamic-title/-/babel-plugin-svg-dynamic-title-8.0.0.tgz", + "integrity": "sha512-omNiKqwjNmOQJ2v6ge4SErBbkooV2aAWwaPFs2vUY7p7GhVkzRkJ00kILXQvRhA6miHnNpXv7MRnnSjdRjK8og==", + "license": "MIT", + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@svgr/babel-plugin-svg-em-dimensions": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-svg-em-dimensions/-/babel-plugin-svg-em-dimensions-8.0.0.tgz", + "integrity": "sha512-mURHYnu6Iw3UBTbhGwE/vsngtCIbHE43xCRK7kCw4t01xyGqb2Pd+WXekRRoFOBIY29ZoOhUCTEweDMdrjfi9g==", + "license": "MIT", + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@svgr/babel-plugin-transform-react-native-svg": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-transform-react-native-svg/-/babel-plugin-transform-react-native-svg-8.1.0.tgz", + "integrity": "sha512-Tx8T58CHo+7nwJ+EhUwx3LfdNSG9R2OKfaIXXs5soiy5HtgoAEkDay9LIimLOcG8dJQH1wPZp/cnAv6S9CrR1Q==", + "license": "MIT", + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@svgr/babel-plugin-transform-svg-component": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-transform-svg-component/-/babel-plugin-transform-svg-component-8.0.0.tgz", + "integrity": "sha512-DFx8xa3cZXTdb/k3kfPeaixecQLgKh5NVBMwD0AQxOzcZawK4oo1Jh9LbrcACUivsCA7TLG8eeWgrDXjTMhRmw==", + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@svgr/babel-preset": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/@svgr/babel-preset/-/babel-preset-8.1.0.tgz", + "integrity": "sha512-7EYDbHE7MxHpv4sxvnVPngw5fuR6pw79SkcrILHJ/iMpuKySNCl5W1qcwPEpU+LgyRXOaAFgH0KhwD18wwg6ug==", + "license": "MIT", + "dependencies": { + "@svgr/babel-plugin-add-jsx-attribute": "8.0.0", + "@svgr/babel-plugin-remove-jsx-attribute": "8.0.0", + "@svgr/babel-plugin-remove-jsx-empty-expression": "8.0.0", + "@svgr/babel-plugin-replace-jsx-attribute-value": "8.0.0", + "@svgr/babel-plugin-svg-dynamic-title": "8.0.0", + "@svgr/babel-plugin-svg-em-dimensions": "8.0.0", + "@svgr/babel-plugin-transform-react-native-svg": "8.1.0", + "@svgr/babel-plugin-transform-svg-component": "8.0.0" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@svgr/core": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/@svgr/core/-/core-8.1.0.tgz", + "integrity": "sha512-8QqtOQT5ACVlmsvKOJNEaWmRPmcojMOzCz4Hs2BGG/toAp/K38LcsMRyLp349glq5AzJbCEeimEoxaX6v/fLrA==", + "license": "MIT", + "dependencies": { + "@babel/core": "^7.21.3", + "@svgr/babel-preset": "8.1.0", + "camelcase": "^6.2.0", + "cosmiconfig": "^8.1.3", + "snake-case": "^3.0.4" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + } + }, + "node_modules/@svgr/hast-util-to-babel-ast": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/@svgr/hast-util-to-babel-ast/-/hast-util-to-babel-ast-8.0.0.tgz", + "integrity": "sha512-EbDKwO9GpfWP4jN9sGdYwPBU0kdomaPIL2Eu4YwmgP+sJeXT+L7bMwJUBnhzfH8Q2qMBqZ4fJwpCyYsAN3mt2Q==", + "license": "MIT", + "dependencies": { + "@babel/types": "^7.21.3", + "entities": "^4.4.0" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + } + }, + "node_modules/@svgr/plugin-jsx": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/@svgr/plugin-jsx/-/plugin-jsx-8.1.0.tgz", + "integrity": "sha512-0xiIyBsLlr8quN+WyuxooNW9RJ0Dpr8uOnH/xrCVO8GLUcwHISwj1AG0k+LFzteTkAA0GbX0kj9q6Dk70PTiPA==", + "license": "MIT", + "dependencies": { + "@babel/core": "^7.21.3", + "@svgr/babel-preset": "8.1.0", + "@svgr/hast-util-to-babel-ast": "8.0.0", + "svg-parser": "^2.0.4" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@svgr/core": "*" + } + }, + "node_modules/@svgr/plugin-svgo": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/@svgr/plugin-svgo/-/plugin-svgo-8.1.0.tgz", + "integrity": "sha512-Ywtl837OGO9pTLIN/onoWLmDQ4zFUycI1g76vuKGEz6evR/ZTJlJuz3G/fIkb6OVBJ2g0o6CGJzaEjfmEo3AHA==", + "license": "MIT", + "dependencies": { + "cosmiconfig": "^8.1.3", + "deepmerge": "^4.3.1", + "svgo": "^3.0.2" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + }, + "peerDependencies": { + "@svgr/core": "*" + } + }, + "node_modules/@svgr/rollup": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/@svgr/rollup/-/rollup-8.1.0.tgz", + "integrity": "sha512-0XR1poYvPQoPpmfDYLEqUGu5ePAQ4pdgN3VFsZBNAeze7qubVpsIY1o1R6PZpKep/DKu33GSm2NhwpCLkMs2Cw==", + "license": "MIT", + "dependencies": { + "@babel/core": "^7.21.3", + "@babel/plugin-transform-react-constant-elements": "^7.21.3", + "@babel/preset-env": "^7.20.2", + "@babel/preset-react": "^7.18.6", + "@babel/preset-typescript": "^7.21.0", + "@rollup/pluginutils": "^5.0.2", + "@svgr/core": "8.1.0", + "@svgr/plugin-jsx": "8.1.0", + "@svgr/plugin-svgo": "8.1.0" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/gregberge" + } + }, + "node_modules/@tabler/icons": { + "version": "2.47.0", + "resolved": "https://registry.npmjs.org/@tabler/icons/-/icons-2.47.0.tgz", + "integrity": "sha512-4w5evLh+7FUUiA1GucvGj2ReX2TvOjEr4ejXdwL/bsjoSkof6r1gQmzqI+VHrE2CpJpB3al7bCTulOkFa/RcyA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/codecalm" + } + }, + "node_modules/@tabler/icons-react": { + "version": "2.47.0", + "resolved": "https://registry.npmjs.org/@tabler/icons-react/-/icons-react-2.47.0.tgz", + "integrity": "sha512-iqly2FvCF/qUbgmvS8E40rVeYY7laltc5GUjRxQj59DuX0x/6CpKHTXt86YlI2whg4czvd/c8Ce8YR08uEku0g==", + "license": "MIT", + "dependencies": { + "@tabler/icons": "2.47.0", + "prop-types": "^15.7.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/codecalm" + }, + "peerDependencies": { + "react": "^16.5.1 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/@tanstack/react-table": { + "version": "8.20.5", + "resolved": "https://registry.npmjs.org/@tanstack/react-table/-/react-table-8.20.5.tgz", + "integrity": "sha512-WEHopKw3znbUZ61s9i0+i9g8drmDo6asTWbrQh8Us63DAk/M0FkmIqERew6P71HI75ksZ2Pxyuf4vvKh9rAkiA==", + "dependencies": { + "@tanstack/table-core": "8.20.5" + }, + "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.20.5", + "resolved": "https://registry.npmjs.org/@tanstack/table-core/-/table-core-8.20.5.tgz", + "integrity": "sha512-P9dF7XbibHph2PFRz8gfBKEXEY/HJPOhym8CHmjF8y3q5mWpKx9xtZapXQUWCgkqvsK0R46Azuz+VaxD4Xl+Tg==", + "engines": { + "node": ">=12" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/tannerlinsley" + } + }, + "node_modules/@tiptap/core": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/core/-/core-2.10.2.tgz", + "integrity": "sha512-jYLXbYHTi1stLla/74J8NJizDtcJ/uokhG+1gN4DMWHDujaZOrRZhW98o9gN5BYAp4zv//TVX8H+afLZwKGCKQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/pm": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-blockquote": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-blockquote/-/extension-blockquote-2.10.2.tgz", + "integrity": "sha512-whmep+v0VvBI9Kg5TJ4sKIj7Z+MOjBKAndP0qn1bMoqPNNVRxt92iIud72wfXwfBNcrYiGNlssvsAnPwXfbG9w==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-bold": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-bold/-/extension-bold-2.10.2.tgz", + "integrity": "sha512-1KNTXA8HDkhXblkfeRYDdqAu/Xz2fygyaSrvabrfzg5QVYyVYPNJwjrtfTQNyzWOejBVGE3mOyqnjlLUzPmyYA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-bubble-menu": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-bubble-menu/-/extension-bubble-menu-2.10.2.tgz", + "integrity": "sha512-KAh2bvYcixJ3RFv2P05kPNLAJ4uW6BDj1AfEMn0YguBWWTgZg8Kot1AzBRgTjBBFCInQS6b49db1ff4M07DGsg==", + "license": "MIT", + "dependencies": { + "tippy.js": "^6.3.7" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0", + "@tiptap/pm": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-bullet-list": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-bullet-list/-/extension-bullet-list-2.10.2.tgz", + "integrity": "sha512-jXtTQXZ3j2cyG2dNyVnGauIbsX8CmDY56MJfDg1p+1UZ3zW2GVbKHfvyuulsjobxEd0DNLxduGqbkDY7x3I+HA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-code": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-code/-/extension-code-2.10.2.tgz", + "integrity": "sha512-VV14oeOsJ3VqUEjuUl+lzSW/IBLhurmcj9IiN2sq/Voin04dwvtchqP5fNXgmM3+rFM88zNOsbX0e4uSG4R10w==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-code-block": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-code-block/-/extension-code-block-2.10.2.tgz", + "integrity": "sha512-Y/wkK9Ni4ALGqiGezov62p6cpPcJauBfn2wF1lgJVr6XJ4na5KTCUEbiyBZNbo3aD52vZKgWt8LpLvJ2/5STSw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0", + "@tiptap/pm": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-document": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-document/-/extension-document-2.10.2.tgz", + "integrity": "sha512-Xodp6rMg6vtKZkyX3I6gVd6OZ9PNz9udhDLdCG6JscVJQPO8viV++39UOH416FCvRT46BdHWNCRu/xjUG1C0rA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-dropcursor": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-dropcursor/-/extension-dropcursor-2.10.2.tgz", + "integrity": "sha512-pzkD6Y9r3x4Mb6KqpuPraGNNfxIkQD6dJNtZ9PpU9jVtJDjsGIGdyzCbVJq984UAPBamXiF/5DLwlON7buLd6A==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0", + "@tiptap/pm": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-floating-menu": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-floating-menu/-/extension-floating-menu-2.10.2.tgz", + "integrity": "sha512-s/KfW5YQY13BwhSQRlgomYmHuBT0k6FBxn8mgJLHcA9sTqgy/BriOhmNkMrredNzd4UOd5JVpcT6b+eckG4nkQ==", + "license": "MIT", + "dependencies": { + "tippy.js": "^6.3.7" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0", + "@tiptap/pm": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-gapcursor": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-gapcursor/-/extension-gapcursor-2.10.2.tgz", + "integrity": "sha512-Uj2hIYC5zRPGI9xBYFwtld8JrZ8YZXEqO7sN5VcOwt12cnSmvzga86jUKpj3WOMP/8KamLWW8m8UKHd7Qg1kMA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0", + "@tiptap/pm": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-hard-break": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-hard-break/-/extension-hard-break-2.10.2.tgz", + "integrity": "sha512-jEVKEe8I+Ai/qYjVf6Idg2Gpp1Cxn4O4twJ0MnlEdzoaEHgt/OTU5NO0PBZMpoe/4BkOvkETZmqRbrcGsapeYQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-heading": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-heading/-/extension-heading-2.10.2.tgz", + "integrity": "sha512-OfvE+epZSyB0TbV5/4GdvRPMT1kd0fbgLUEaldWMZOLw/4eOGWZ8yXAtrWkoRMLZfOclgnDfwXvXJLnWXrDdDw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-history": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-history/-/extension-history-2.10.2.tgz", + "integrity": "sha512-Hr5cvYgOAP7vaRD5vbMjirTATFe/zYqnzePhq1c9TQESOi2o0zKxWpZIcHbFFIXCjHLSnpXOZ4yFwHP4k12rgg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0", + "@tiptap/pm": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-horizontal-rule": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-horizontal-rule/-/extension-horizontal-rule-2.10.2.tgz", + "integrity": "sha512-DqaCUxjXnoVN/yylEjoGIlvKkT1KF8mwFJncJn8oSAukYEaSAK056ETvmyZk+/bzc3aRpfv0Kfn/zmLfHZ3wnA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0", + "@tiptap/pm": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-image": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-image/-/extension-image-2.10.2.tgz", + "integrity": "sha512-xaJOVeR/fWozJMVKjYhskecsbayUUm1tIbjE+SyG7IW3Jp+081/W9z2nyfXG6YNnuVjYq+uLejR2Bt0cnEZvmA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-italic": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-italic/-/extension-italic-2.10.2.tgz", + "integrity": "sha512-6p1YkJEWHuMROzNrK+GFJamujBswpydfR3ZMpIjQTLr4hRhSGrde/B5WODRDS+3JiK1xcN16ZQVPFsRJaHMjfQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-list-item": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-list-item/-/extension-list-item-2.10.2.tgz", + "integrity": "sha512-NE800m/QCk58MUcfeeCqmDjgOuiwHddaZvCCQIpErZdI2Y0io9RsSYU3HHEFPIfbKsv/ykVTYbwSweTPs1Tmxw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-ordered-list": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-ordered-list/-/extension-ordered-list-2.10.2.tgz", + "integrity": "sha512-1WYknf7/feouoBN7jW9Z6fvN9gzS1WRaOrDVkLZQ2ZLgT+Bs8H8/r1pv23q8Un6lg0mApwqnUxNhLOOrVyDkGQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-paragraph": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-paragraph/-/extension-paragraph-2.10.2.tgz", + "integrity": "sha512-EZG9W5rsU4uP585cIOrhbAPOUsgqrFbDrj1tZjTbvv0EWK03Un3FGYoGilkcUIxD9uB/XVHP+v2596Ifyi/dvQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-strike": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-strike/-/extension-strike-2.10.2.tgz", + "integrity": "sha512-TjrBbO6UbXCt55hV9wRE7h5R/jLTB+z2yn2blz1TfR7wKkX3tJOnb+ptvIHEVFGJOjkZP6Xaj+aAkGVg5dKZYA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-table": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-table/-/extension-table-2.10.2.tgz", + "integrity": "sha512-T7hzHEB090KsAy0VS4wogcjwauKHlYorQKrBxxZHzE6n6w6Zi0Cz00qJnAb6oYgKrMCTredcxnWUH8PmWlehYg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0", + "@tiptap/pm": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-text": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-text/-/extension-text-2.10.2.tgz", + "integrity": "sha512-7WaJCmHAnf24gZc+Bl64vZgjAFt0CSEc5Jr+f3GII6XeCkZpTCJX85po2MFUhBRZMJheyctyL+UfsRauo/iP0Q==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/extension-text-style": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/extension-text-style/-/extension-text-style-2.10.2.tgz", + "integrity": "sha512-dWx5Ean7Rb6rdqO6C/i0qIIABKHFsABZj0mTDr0/ZXsw3V2O4d1cP13evvcc7HMLNAXziRTtWCVU6M06vwM/Pw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0" + } + }, + "node_modules/@tiptap/pm": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/pm/-/pm-2.10.2.tgz", + "integrity": "sha512-jEgC79uvuEl51XxulutUJPSlhkoY0xQc9R/G4MQltAi+JxJ+KE/pOxgqziWNxBpgUzQqloupjod0kLhLUL4Cig==", + "license": "MIT", + "dependencies": { + "prosemirror-changeset": "^2.2.1", + "prosemirror-collab": "^1.3.1", + "prosemirror-commands": "^1.6.2", + "prosemirror-dropcursor": "^1.8.1", + "prosemirror-gapcursor": "^1.3.2", + "prosemirror-history": "^1.4.1", + "prosemirror-inputrules": "^1.4.0", + "prosemirror-keymap": "^1.2.2", + "prosemirror-markdown": "^1.13.1", + "prosemirror-menu": "^1.2.4", + "prosemirror-model": "^1.23.0", + "prosemirror-schema-basic": "^1.2.3", + "prosemirror-schema-list": "^1.4.1", + "prosemirror-state": "^1.4.3", + "prosemirror-tables": "^1.6.1", + "prosemirror-trailing-node": "^3.0.0", + "prosemirror-transform": "^1.10.2", + "prosemirror-view": "^1.36.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + } + }, + "node_modules/@tiptap/react": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/react/-/react-2.10.2.tgz", + "integrity": "sha512-xBg0uA/ON9LbC8ojwjgFQgZA1xmaEotXZnZcM3tfGjCboqk0toi59v+2CIN9icDfW+UT/hsget3SBQtRw+SBEw==", + "license": "MIT", + "dependencies": { + "@tiptap/extension-bubble-menu": "^2.10.2", + "@tiptap/extension-floating-menu": "^2.10.2", + "@types/use-sync-external-store": "^0.0.6", + "fast-deep-equal": "^3", + "use-sync-external-store": "^1" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "peerDependencies": { + "@tiptap/core": "^2.7.0", + "@tiptap/pm": "^2.7.0", + "react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react-dom": "^17.0.0 || ^18.0.0 || ^19.0.0" + } + }, + "node_modules/@tiptap/react/node_modules/@types/use-sync-external-store": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/@types/use-sync-external-store/-/use-sync-external-store-0.0.6.tgz", + "integrity": "sha512-zFDAD+tlpf2r4asuHEj0XH6pY6i0g5NeAHPn+15wk3BV6JA69eERFXC1gyGThDkVa1zCyKr5jox1+2LbV/AMLg==", + "license": "MIT" + }, + "node_modules/@tiptap/starter-kit": { + "version": "2.10.2", + "resolved": "https://registry.npmjs.org/@tiptap/starter-kit/-/starter-kit-2.10.2.tgz", + "integrity": "sha512-YbS9P3zvLhfEWnCPMcvCwK/+3XjMgZX73D1qMu9jVRHtQGI2DMk9u42KWAMLQAMBUESMcIeGxJ9G5IWJO0PsyA==", + "license": "MIT", + "dependencies": { + "@tiptap/core": "^2.10.2", + "@tiptap/extension-blockquote": "^2.10.2", + "@tiptap/extension-bold": "^2.10.2", + "@tiptap/extension-bullet-list": "^2.10.2", + "@tiptap/extension-code": "^2.10.2", + "@tiptap/extension-code-block": "^2.10.2", + "@tiptap/extension-document": "^2.10.2", + "@tiptap/extension-dropcursor": "^2.10.2", + "@tiptap/extension-gapcursor": "^2.10.2", + "@tiptap/extension-hard-break": "^2.10.2", + "@tiptap/extension-heading": "^2.10.2", + "@tiptap/extension-history": "^2.10.2", + "@tiptap/extension-horizontal-rule": "^2.10.2", + "@tiptap/extension-italic": "^2.10.2", + "@tiptap/extension-list-item": "^2.10.2", + "@tiptap/extension-ordered-list": "^2.10.2", + "@tiptap/extension-paragraph": "^2.10.2", + "@tiptap/extension-strike": "^2.10.2", + "@tiptap/extension-text": "^2.10.2", + "@tiptap/extension-text-style": "^2.10.2", + "@tiptap/pm": "^2.10.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + } + }, + "node_modules/@trysound/sax": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/@trysound/sax/-/sax-0.2.0.tgz", + "integrity": "sha512-L7z9BgrNEcYyUYtF+HaEfiS5ebkh9jXqbszz7pC0hRBPaatV0XjSD3+eHrpqFemQfgwiFF0QPIarnIihIDn7OA==", + "license": "ISC", + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/@types/babel__core": { + "version": "7.20.5", + "resolved": "https://registry.npmjs.org/@types/babel__core/-/babel__core-7.20.5.tgz", + "integrity": "sha512-qoQprZvz5wQFJwMDqeseRXWv3rqMvhgpbXFfVyWhbx9X47POIA6i/+dXefEmZKoAgOaTdaIgNSMqMIU61yRyzA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@babel/parser": "^7.20.7", + "@babel/types": "^7.20.7", + "@types/babel__generator": "*", + "@types/babel__template": "*", + "@types/babel__traverse": "*" + } + }, + "node_modules/@types/babel__generator": { + "version": "7.6.8", + "resolved": "https://registry.npmjs.org/@types/babel__generator/-/babel__generator-7.6.8.tgz", + "integrity": "sha512-ASsj+tpEDsEiFr1arWrlN6V3mdfjRMZt6LtK/Vp/kreFLnr5QH5+DhvD5nINYZXzwJvXeGq+05iUXcAzVrqWtw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@babel/types": "^7.0.0" + } + }, + "node_modules/@types/babel__template": { + "version": "7.4.4", + "resolved": "https://registry.npmjs.org/@types/babel__template/-/babel__template-7.4.4.tgz", + "integrity": "sha512-h/NUaSyG5EyxBIp8YRxo4RMe2/qQgvyowRwVMzhYhBCONbW8PUsg4lkFMrhgZhUe5z3L3MiLDuvyJ/CaPa2A8A==", + "dev": true, + "license": "MIT", + "dependencies": { + "@babel/parser": "^7.1.0", + "@babel/types": "^7.0.0" + } + }, + "node_modules/@types/babel__traverse": { + "version": "7.20.6", + "resolved": "https://registry.npmjs.org/@types/babel__traverse/-/babel__traverse-7.20.6.tgz", + "integrity": "sha512-r1bzfrm0tomOI8g1SzvCaQHo6Lcv6zu0EA+W2kHrt8dyrHQxGzBBL4kdkzIS+jBMV+EYcMAEAqXqYaLJq5rOZg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@babel/types": "^7.20.7" + } + }, + "node_modules/@types/chance": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/@types/chance/-/chance-1.1.6.tgz", + "integrity": "sha512-V+pm3stv1Mvz8fSKJJod6CglNGVqEQ6OyuqitoDkWywEODM/eJd1eSuIp9xt6DrX8BWZ2eDSIzbw1tPCUTvGbQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/@types/cookie": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/@types/cookie/-/cookie-0.6.0.tgz", + "integrity": "sha512-4Kh9a6B2bQciAhf7FSuMRRkUWecJgJu9nPnx3yzpsfXX/c50REIqpHY4C82bXP90qrLtXtkDxTZosYO3UpOwlA==", + "license": "MIT" + }, + "node_modules/@types/d3-color": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/@types/d3-color/-/d3-color-3.1.3.tgz", + "integrity": "sha512-iO90scth9WAbmgv7ogoq57O9YpKmFBbmoEoCHDB2xMBY0+/KVrqAaCDyCE16dUspeOvIxFFRI+0sEtqDqy2b4A==", + "license": "MIT" + }, + "node_modules/@types/d3-delaunay": { + "version": "6.0.4", + "resolved": "https://registry.npmjs.org/@types/d3-delaunay/-/d3-delaunay-6.0.4.tgz", + "integrity": "sha512-ZMaSKu4THYCU6sV64Lhg6qjf1orxBthaC161plr5KuPHo3CNm8DTHiLw/5Eq2b6TsNP0W0iJrUOFscY6Q450Hw==", + "license": "MIT" + }, + "node_modules/@types/d3-interpolate": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/d3-interpolate/-/d3-interpolate-3.0.4.tgz", + "integrity": "sha512-mgLPETlrpVV1YRJIglr4Ez47g7Yxjl1lj7YKsiMCb27VJH9W8NVM6Bb9d8kkpG/uAQS5AmbA48q2IAolKKo1MA==", + "license": "MIT", + "dependencies": { + "@types/d3-color": "*" + } + }, + "node_modules/@types/d3-path": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@types/d3-path/-/d3-path-3.1.0.tgz", + "integrity": "sha512-P2dlU/q51fkOc/Gfl3Ul9kicV7l+ra934qBFXCFhrZMOL6du1TM0pm1ThYvENukyOn5h9v+yMJ9Fn5JK4QozrQ==", + "license": "MIT" + }, + "node_modules/@types/d3-scale": { + "version": "4.0.8", + "resolved": "https://registry.npmjs.org/@types/d3-scale/-/d3-scale-4.0.8.tgz", + "integrity": "sha512-gkK1VVTr5iNiYJ7vWDI+yUFFlszhNMtVeneJ6lUTKPjprsvLLI9/tgEGiXJOnlINJA8FyA88gfnQsHbybVZrYQ==", + "license": "MIT", + "dependencies": { + "@types/d3-time": "*" + } + }, + "node_modules/@types/d3-shape": { + "version": "3.1.6", + "resolved": "https://registry.npmjs.org/@types/d3-shape/-/d3-shape-3.1.6.tgz", + "integrity": "sha512-5KKk5aKGu2I+O6SONMYSNflgiP0WfZIQvVUMan50wHsLG1G94JlxEVnCpQARfTtzytuY0p/9PXXZb3I7giofIA==", + "license": "MIT", + "dependencies": { + "@types/d3-path": "*" + } + }, + "node_modules/@types/d3-time": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/d3-time/-/d3-time-3.0.4.tgz", + "integrity": "sha512-yuzZug1nkAAaBlBBikKZTgzCeA+k1uy4ZFwWANOfKw5z5LRhV0gNA7gNkKm7HoK+HRN0wX3EkxGk0fpbWhmB7g==", + "license": "MIT" + }, + "node_modules/@types/date-arithmetic": { + "version": "4.1.4", + "resolved": "https://registry.npmjs.org/@types/date-arithmetic/-/date-arithmetic-4.1.4.tgz", + "integrity": "sha512-p9eZ2X9B80iKiTW4ukVj8B4K6q9/+xFtQ5MGYA5HWToY9nL4EkhV9+6ftT2VHpVMEZb5Tv00Iel516bVdO+yRw==", + "dev": true, + "license": "MIT" + }, + "node_modules/@types/debug": { + "version": "4.1.12", + "resolved": "https://registry.npmjs.org/@types/debug/-/debug-4.1.12.tgz", + "integrity": "sha512-vIChWdVG3LG1SMxEvI/AK+FWJthlrqlTu7fbrlywTkkaONwk/UAGaULXRlf8vkzFBLVm0zkMdCquhL5aOjhXPQ==", + "license": "MIT", + "dependencies": { + "@types/ms": "*" + } + }, + "node_modules/@types/estree": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.6.tgz", + "integrity": "sha512-AYnb1nQyY49te+VRAVgmzfcgjYS91mY5P0TKUDCLEM+gNnA+3T6rWITXRLYCpahpqSQbN5cE+gHpnPyXjHWxcw==", + "license": "MIT" + }, + "node_modules/@types/fslightbox-react": { + "version": "1.7.8", + "resolved": "https://registry.npmjs.org/@types/fslightbox-react/-/fslightbox-react-1.7.8.tgz", + "integrity": "sha512-98lYTJS5n2osLdxVqZ0Kwg8TUDzsLqDaY/kNb/1PlxmJ8xbxEK1a3gHQUoz0cFSusDAH8bV40IvqdhndVFtYdw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/react": "*" + } + }, + "node_modules/@types/hast": { + "version": "2.3.10", + "resolved": "https://registry.npmjs.org/@types/hast/-/hast-2.3.10.tgz", + "integrity": "sha512-McWspRw8xx8J9HurkVBfYj0xKoE25tOFlHGdx4MJ5xORQrMGZNqJhVQWaIbm6Oyla5kYOXtDiopzKRJzEOkwJw==", + "dependencies": { + "@types/unist": "^2" + } + }, + "node_modules/@types/hoist-non-react-statics": { + "version": "3.3.5", + "resolved": "https://registry.npmjs.org/@types/hoist-non-react-statics/-/hoist-non-react-statics-3.3.5.tgz", + "integrity": "sha512-SbcrWzkKBw2cdwRTwQAswfpB9g9LJWfjtUeW/jvNwbhC8cpmmNYVePa+ncbUe0rGTQ7G3Ff6mYUN2VMfLVr+Sg==", + "dependencies": { + "@types/react": "*", + "hoist-non-react-statics": "^3.3.0" + } + }, + "node_modules/@types/json-schema": { + "version": "7.0.15", + "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", + "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==", + "dev": true + }, + "node_modules/@types/json5": { + "version": "0.0.29", + "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", + "integrity": "sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/@types/linkify-it": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/@types/linkify-it/-/linkify-it-5.0.0.tgz", + "integrity": "sha512-sVDA58zAw4eWAffKOaQH5/5j3XeayukzDk+ewSsnv3p4yJEZHCCzMDiZM8e0OUrRvmpGZ85jf4yDHkHsgBNr9Q==", + "license": "MIT" + }, + "node_modules/@types/lodash": { + "version": "4.14.182", + "resolved": "https://registry.npmjs.org/@types/lodash/-/lodash-4.14.182.tgz", + "integrity": "sha512-/THyiqyQAP9AfARo4pF+aCGcyiQ94tX/Is2I7HofNRqoYLgN1PBoOWu2/zTA5zMxzP5EFutMtWtGAFRKUe961Q==" + }, + "node_modules/@types/lodash-es": { + "version": "4.17.12", + "resolved": "https://registry.npmjs.org/@types/lodash-es/-/lodash-es-4.17.12.tgz", + "integrity": "sha512-0NgftHUcV4v34VhXm8QBSftKVXtbkBG3ViCjs6+eJ5a6y6Mi/jiFGPc1sC7QK+9BFhWrURE3EOggmWaSxL9OzQ==", + "dependencies": { + "@types/lodash": "*" + } + }, + "node_modules/@types/markdown-it": { + "version": "14.1.2", + "resolved": "https://registry.npmjs.org/@types/markdown-it/-/markdown-it-14.1.2.tgz", + "integrity": "sha512-promo4eFwuiW+TfGxhi+0x3czqTYJkG8qB17ZUJiVF10Xm7NLVRSLUsfRTU/6h1e24VvRnXCx+hG7li58lkzog==", + "license": "MIT", + "dependencies": { + "@types/linkify-it": "^5", + "@types/mdurl": "^2" + } + }, + "node_modules/@types/mdast": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-4.0.4.tgz", + "integrity": "sha512-kGaNbPh1k7AFzgpud/gMdvIm5xuECykRR+JnWKQno9TAXVa6WIVCGTPvYGekIDL4uwCZQSYbUxNBSb1aUo79oA==", + "license": "MIT", + "dependencies": { + "@types/unist": "*" + } + }, + "node_modules/@types/mdurl": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@types/mdurl/-/mdurl-2.0.0.tgz", + "integrity": "sha512-RGdgjQUZba5p6QEFAVx2OGb8rQDL/cPRG7GiedRzMcJ1tYnUANBncjbSB1NRGwbvjcPeikRABz2nshyPk1bhWg==", + "license": "MIT" + }, + "node_modules/@types/ms": { + "version": "0.7.34", + "resolved": "https://registry.npmjs.org/@types/ms/-/ms-0.7.34.tgz", + "integrity": "sha512-nG96G3Wp6acyAgJqGasjODb+acrI7KltPiRxzHPXnP3NgI28bpQDRv53olbqGXbfcgF5aiiHmO3xpwEpS5Ld9g==", + "license": "MIT" + }, + "node_modules/@types/node": { + "version": "22.10.1", + "resolved": "https://registry.npmjs.org/@types/node/-/node-22.10.1.tgz", + "integrity": "sha512-qKgsUwfHZV2WCWLAnVP1JqnpE6Im6h3Y0+fYgMTasNQ7V++CBX5OT1as0g0f+OyubbFqhf6XVNIsmN4IIhEgGQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "undici-types": "~6.20.0" + } + }, + "node_modules/@types/parse-json": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/@types/parse-json/-/parse-json-4.0.2.tgz", + "integrity": "sha512-dISoDXWWQwUquiKsyZ4Ng+HX2KsPL7LyHKHQwgGFEA3IaKac4Obd+h2a/a6waisAoepJlBcx9paWqjA8/HVjCw==", + "license": "MIT" + }, + "node_modules/@types/prop-types": { + "version": "15.7.13", + "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.13.tgz", + "integrity": "sha512-hCZTSvwbzWGvhqxp/RqVqwU999pBf2vp7hzIjiYOsl8wqOmUxkQ6ddw1cV3l8811+kdUFus/q4d1Y3E3SyEifA==" + }, + "node_modules/@types/react": { + "version": "19.0.1", + "resolved": "https://registry.npmjs.org/@types/react/-/react-19.0.1.tgz", + "integrity": "sha512-YW6614BDhqbpR5KtUYzTA+zlA7nayzJRA9ljz9CQoxthR0sDisYZLuvSMsil36t4EH/uAt8T52Xb4sVw17G+SQ==", + "license": "MIT", + "dependencies": { + "csstype": "^3.0.2" + } + }, + "node_modules/@types/react-big-calendar": { + "version": "1.16.0", + "resolved": "https://registry.npmjs.org/@types/react-big-calendar/-/react-big-calendar-1.16.0.tgz", + "integrity": "sha512-1w2GXAJWlGmaPZOd9J9cyWA/XBNOGRZ4MmRNypEQhwEMIIL9cfd1UdcvzSrQsnBm0qYF/scqmsISNbUzPBE1vg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/date-arithmetic": "*", + "@types/prop-types": "*", + "@types/react": "*" + } + }, + "node_modules/@types/react-dom": { + "version": "19.0.1", + "resolved": "https://registry.npmjs.org/@types/react-dom/-/react-dom-19.0.1.tgz", + "integrity": "sha512-hljHij7MpWPKF6u5vojuyfV0YA4YURsQG7KT6SzV0Zs2BXAtgdTxG6A229Ub/xiWV4w/7JL8fi6aAyjshH4meA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/react": "*" + } + }, + "node_modules/@types/react-helmet": { + "version": "6.1.11", + "resolved": "https://registry.npmjs.org/@types/react-helmet/-/react-helmet-6.1.11.tgz", + "integrity": "sha512-0QcdGLddTERotCXo3VFlUSWO3ztraw8nZ6e3zJSgG7apwV5xt+pJUS8ewPBqT4NYB1optGLprNQzFleIY84u/g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/react": "*" + } + }, + "node_modules/@types/react-slick": { + "version": "0.23.13", + "resolved": "https://registry.npmjs.org/@types/react-slick/-/react-slick-0.23.13.tgz", + "integrity": "sha512-bNZfDhe/L8t5OQzIyhrRhBr/61pfBcWaYJoq6UDqFtv5LMwfg4NsVDD2J8N01JqdAdxLjOt66OZEp6PX+dGs/A==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/react": "*" + } + }, + "node_modules/@types/react-syntax-highlighter": { + "version": "15.5.13", + "resolved": "https://registry.npmjs.org/@types/react-syntax-highlighter/-/react-syntax-highlighter-15.5.13.tgz", + "integrity": "sha512-uLGJ87j6Sz8UaBAooU0T6lWJ0dBmjZgN1PZTrj05TNql2/XpC6+4HhMT5syIdFUUt+FASfCeLLv4kBygNU+8qA==", + "dev": true, + "dependencies": { + "@types/react": "*" + } + }, + "node_modules/@types/react-transition-group": { + "version": "4.4.11", + "resolved": "https://registry.npmjs.org/@types/react-transition-group/-/react-transition-group-4.4.11.tgz", + "integrity": "sha512-RM05tAniPZ5DZPzzNFP+DmrcOdD0efDUxMy3145oljWSl3x9ZV5vhme98gTxFrj2lhXvmGNnUiuDyJgY9IKkNA==", + "dependencies": { + "@types/react": "*" + } + }, + "node_modules/@types/semver": { + "version": "7.5.8", + "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.5.8.tgz", + "integrity": "sha512-I8EUhyrgfLrcTkzV3TSsGyl1tSuPrEDzr0yd5m90UgNxQkyDXULk3b6MlQqTCpZpNtWe1K0hzclnZkTcLBe2UQ==", + "dev": true + }, + "node_modules/@types/unist": { + "version": "2.0.11", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.11.tgz", + "integrity": "sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==" + }, + "node_modules/@types/use-sync-external-store": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/@types/use-sync-external-store/-/use-sync-external-store-0.0.3.tgz", + "integrity": "sha512-EwmlvuaxPNej9+T4v5AuBPJa2x2UOJVdjCtDHgcDqitUeOtjnJKJ+apYjVcAoBEMjKW1VVFGZLUb5+qqa09XFA==" + }, + "node_modules/@types/warning": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/warning/-/warning-3.0.3.tgz", + "integrity": "sha512-D1XC7WK8K+zZEveUPY+cf4+kgauk8N4eHr/XIHXGlGYkHLud6hK9lYfZk1ry1TNh798cZUCgb6MqGEG8DkJt6Q==" + }, + "node_modules/@typescript-eslint/eslint-plugin": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-6.0.0.tgz", + "integrity": "sha512-xuv6ghKGoiq856Bww/yVYnXGsKa588kY3M0XK7uUW/3fJNNULKRfZfSBkMTSpqGG/8ZCXCadfh8G/z/B4aqS/A==", + "dev": true, + "dependencies": { + "@eslint-community/regexpp": "^4.5.0", + "@typescript-eslint/scope-manager": "6.0.0", + "@typescript-eslint/type-utils": "6.0.0", + "@typescript-eslint/utils": "6.0.0", + "@typescript-eslint/visitor-keys": "6.0.0", + "debug": "^4.3.4", + "grapheme-splitter": "^1.0.4", + "graphemer": "^1.4.0", + "ignore": "^5.2.4", + "natural-compare": "^1.4.0", + "natural-compare-lite": "^1.4.0", + "semver": "^7.5.0", + "ts-api-utils": "^1.0.1" + }, + "engines": { + "node": "^16.0.0 || >=18.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "@typescript-eslint/parser": "^6.0.0 || ^6.0.0-alpha", + "eslint": "^7.0.0 || ^8.0.0" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/eslint-plugin/node_modules/semver": { + "version": "7.6.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.3.tgz", + "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", + "dev": true, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@typescript-eslint/parser": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-6.0.0.tgz", + "integrity": "sha512-TNaufYSPrr1U8n+3xN+Yp9g31vQDJqhXzzPSHfQDLcaO4tU+mCfODPxCwf4H530zo7aUBE3QIdxCXamEnG04Tg==", + "dev": true, + "dependencies": { + "@typescript-eslint/scope-manager": "6.0.0", + "@typescript-eslint/types": "6.0.0", + "@typescript-eslint/typescript-estree": "6.0.0", + "@typescript-eslint/visitor-keys": "6.0.0", + "debug": "^4.3.4" + }, + "engines": { + "node": "^16.0.0 || >=18.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^7.0.0 || ^8.0.0" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/scope-manager": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-6.0.0.tgz", + "integrity": "sha512-o4q0KHlgCZTqjuaZ25nw5W57NeykZT9LiMEG4do/ovwvOcPnDO1BI5BQdCsUkjxFyrCL0cSzLjvIMfR9uo7cWg==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "6.0.0", + "@typescript-eslint/visitor-keys": "6.0.0" + }, + "engines": { + "node": "^16.0.0 || >=18.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/type-utils": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-6.0.0.tgz", + "integrity": "sha512-ah6LJvLgkoZ/pyJ9GAdFkzeuMZ8goV6BH7eC9FPmojrnX9yNCIsfjB+zYcnex28YO3RFvBkV6rMV6WpIqkPvoQ==", + "dev": true, + "dependencies": { + "@typescript-eslint/typescript-estree": "6.0.0", + "@typescript-eslint/utils": "6.0.0", + "debug": "^4.3.4", + "ts-api-utils": "^1.0.1" + }, + "engines": { + "node": "^16.0.0 || >=18.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^7.0.0 || ^8.0.0" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/types": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-6.0.0.tgz", + "integrity": "sha512-Zk9KDggyZM6tj0AJWYYKgF0yQyrcnievdhG0g5FqyU3Y2DRxJn4yWY21sJC0QKBckbsdKKjYDV2yVrrEvuTgxg==", + "dev": true, + "engines": { + "node": "^16.0.0 || >=18.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/typescript-estree": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-6.0.0.tgz", + "integrity": "sha512-2zq4O7P6YCQADfmJ5OTDQTP3ktajnXIRrYAtHM9ofto/CJZV3QfJ89GEaM2BNGeSr1KgmBuLhEkz5FBkS2RQhQ==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "6.0.0", + "@typescript-eslint/visitor-keys": "6.0.0", + "debug": "^4.3.4", + "globby": "^11.1.0", + "is-glob": "^4.0.3", + "semver": "^7.5.0", + "ts-api-utils": "^1.0.1" + }, + "engines": { + "node": "^16.0.0 || >=18.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/typescript-estree/node_modules/semver": { + "version": "7.6.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.3.tgz", + "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", + "dev": true, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@typescript-eslint/utils": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-6.0.0.tgz", + "integrity": "sha512-SOr6l4NB6HE4H/ktz0JVVWNXqCJTOo/mHnvIte1ZhBQ0Cvd04x5uKZa3zT6tiodL06zf5xxdK8COiDvPnQ27JQ==", + "dev": true, + "dependencies": { + "@eslint-community/eslint-utils": "^4.3.0", + "@types/json-schema": "^7.0.11", + "@types/semver": "^7.3.12", + "@typescript-eslint/scope-manager": "6.0.0", + "@typescript-eslint/types": "6.0.0", + "@typescript-eslint/typescript-estree": "6.0.0", + "eslint-scope": "^5.1.1", + "semver": "^7.5.0" + }, + "engines": { + "node": "^16.0.0 || >=18.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^7.0.0 || ^8.0.0" + } + }, + "node_modules/@typescript-eslint/utils/node_modules/eslint-scope": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", + "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", + "dev": true, + "dependencies": { + "esrecurse": "^4.3.0", + "estraverse": "^4.1.1" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/@typescript-eslint/utils/node_modules/estraverse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", + "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==", + "dev": true, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/@typescript-eslint/utils/node_modules/semver": { + "version": "7.6.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.3.tgz", + "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", + "dev": true, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@typescript-eslint/visitor-keys": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-6.0.0.tgz", + "integrity": "sha512-cvJ63l8c0yXdeT5POHpL0Q1cZoRcmRKFCtSjNGJxPkcP571EfZMcNbzWAc7oK3D1dRzm/V5EwtkANTZxqvuuUA==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "6.0.0", + "eslint-visitor-keys": "^3.4.1" + }, + "engines": { + "node": "^16.0.0 || >=18.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@ucast/core": { + "version": "1.10.2", + "resolved": "https://registry.npmjs.org/@ucast/core/-/core-1.10.2.tgz", + "integrity": "sha512-ons5CwXZ/51wrUPfoduC+cO7AS1/wRb0ybpQJ9RrssossDxVy4t49QxWoWgfBDvVKsz9VXzBk9z0wqTdZ+Cq8g==" + }, + "node_modules/@ucast/js": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@ucast/js/-/js-3.0.4.tgz", + "integrity": "sha512-TgG1aIaCMdcaEyckOZKQozn1hazE0w90SVdlpIJ/er8xVumE11gYAtSbw/LBeUnA4fFnFWTcw3t6reqseeH/4Q==", + "dependencies": { + "@ucast/core": "^1.0.0" + } + }, + "node_modules/@ucast/mongo": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/@ucast/mongo/-/mongo-2.4.3.tgz", + "integrity": "sha512-XcI8LclrHWP83H+7H2anGCEeDq0n+12FU2mXCTz6/Tva9/9ddK/iacvvhCyW6cijAAOILmt0tWplRyRhVyZLsA==", + "dependencies": { + "@ucast/core": "^1.4.1" + } + }, + "node_modules/@ucast/mongo2js": { + "version": "1.3.4", + "resolved": "https://registry.npmjs.org/@ucast/mongo2js/-/mongo2js-1.3.4.tgz", + "integrity": "sha512-ahazOr1HtelA5AC1KZ9x0UwPMqqimvfmtSm/PRRSeKKeE5G2SCqTgwiNzO7i9jS8zA3dzXpKVPpXMkcYLnyItA==", + "dependencies": { + "@ucast/core": "^1.6.1", + "@ucast/js": "^3.0.0", + "@ucast/mongo": "^2.4.0" + } + }, + "node_modules/@ungap/structured-clone": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/@ungap/structured-clone/-/structured-clone-1.2.0.tgz", + "integrity": "sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==", + "license": "ISC" + }, + "node_modules/@vitejs/plugin-react": { + "version": "4.3.4", + "resolved": "https://registry.npmjs.org/@vitejs/plugin-react/-/plugin-react-4.3.4.tgz", + "integrity": "sha512-SCCPBJtYLdE8PX/7ZQAs1QAZ8Jqwih+0VBLum1EGqmCCQal+MIUqLCzj3ZUy8ufbC0cAM4LRlSTm7IQJwWT4ug==", + "dev": true, + "license": "MIT", + "dependencies": { + "@babel/core": "^7.26.0", + "@babel/plugin-transform-react-jsx-self": "^7.25.9", + "@babel/plugin-transform-react-jsx-source": "^7.25.9", + "@types/babel__core": "^7.20.5", + "react-refresh": "^0.14.2" + }, + "engines": { + "node": "^14.18.0 || >=16.0.0" + }, + "peerDependencies": { + "vite": "^4.2.0 || ^5.0.0 || ^6.0.0" + } + }, + "node_modules/@yr/monotone-cubic-spline": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/@yr/monotone-cubic-spline/-/monotone-cubic-spline-1.0.3.tgz", + "integrity": "sha512-FQXkOta0XBSUPHndIKON2Y9JeQz5ZeMqLYZVVK93FliNBFm7LNMIZmY6FrMEB9XPcDbE2bekMbZD6kzDkxwYjA==" + }, + "node_modules/acorn": { + "version": "8.12.1", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.12.1.tgz", + "integrity": "sha512-tcpGyI9zbizT9JbV6oYE477V6mTlXvvi0T0G3SNIYE2apm/G5huBa1+K89VGeovbg+jycCrfhl3ADxErOuO6Jg==", + "dev": true, + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/acorn-jsx": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", + "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", + "dev": true, + "peerDependencies": { + "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" + } + }, + "node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/ansi-regex": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", + "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/apexcharts": { + "version": "3.48.0", + "resolved": "https://registry.npmjs.org/apexcharts/-/apexcharts-3.48.0.tgz", + "integrity": "sha512-Lhpj1Ij6lKlrUke8gf+P+SE6uGUn+Pe1TnCJ+zqrY0YMvbqM3LMb1lY+eybbTczUyk0RmMZomlTa2NgX2EUs4Q==", + "dependencies": { + "@yr/monotone-cubic-spline": "^1.0.3", + "svg.draggable.js": "^2.2.2", + "svg.easing.js": "^2.0.0", + "svg.filter.js": "^2.0.2", + "svg.pathmorphing.js": "^0.1.3", + "svg.resize.js": "^1.4.3", + "svg.select.js": "^3.0.1" + } + }, + "node_modules/argparse": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", + "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==" + }, + "node_modules/aria-query": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.3.2.tgz", + "integrity": "sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/array-buffer-byte-length": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/array-buffer-byte-length/-/array-buffer-byte-length-1.0.1.tgz", + "integrity": "sha512-ahC5W1xgou+KTXix4sAO8Ki12Q+jf4i0+tmk3sC+zgcynshkHxzpXdImBehiUYKKKDwvfFiJl1tZt6ewscS1Mg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.5", + "is-array-buffer": "^3.0.4" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/array-includes": { + "version": "3.1.8", + "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.8.tgz", + "integrity": "sha512-itaWrbYbqpGXkGhZPGUulwnhVf5Hpy1xiCFsGqyIGglbBxmG5vSjxQen3/WGOjPpNEv1RtBLKxbmVXm8HpJStQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.2", + "es-object-atoms": "^1.0.0", + "get-intrinsic": "^1.2.4", + "is-string": "^1.0.7" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/array-union": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz", + "integrity": "sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/array.prototype.findlast": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/array.prototype.findlast/-/array.prototype.findlast-1.2.5.tgz", + "integrity": "sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.2", + "es-errors": "^1.3.0", + "es-object-atoms": "^1.0.0", + "es-shim-unscopables": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/array.prototype.findlastindex": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/array.prototype.findlastindex/-/array.prototype.findlastindex-1.2.5.tgz", + "integrity": "sha512-zfETvRFA8o7EiNn++N5f/kaCw221hrpGsDmcpndVupkPzEc1Wuf3VgC0qby1BbHs7f5DVYjgtEU2LLh5bqeGfQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.2", + "es-errors": "^1.3.0", + "es-object-atoms": "^1.0.0", + "es-shim-unscopables": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/array.prototype.flat": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.3.2.tgz", + "integrity": "sha512-djYB+Zx2vLewY8RWlNCUdHjDXs2XOgm602S9E7P/UpHgfeHL00cRiIF+IN/G/aUJ7kGPb6yO/ErDI5V2s8iycA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.2.0", + "es-abstract": "^1.22.1", + "es-shim-unscopables": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/array.prototype.flatmap": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.2.tgz", + "integrity": "sha512-Ewyx0c9PmpcsByhSW4r+9zDU7sGjFc86qf/kKtuSCRdhfbk0SNLLkaT5qvcHnRGgc5NP/ly/y+qkXkqONX54CQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.2.0", + "es-abstract": "^1.22.1", + "es-shim-unscopables": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/array.prototype.tosorted": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/array.prototype.tosorted/-/array.prototype.tosorted-1.1.4.tgz", + "integrity": "sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.3", + "es-errors": "^1.3.0", + "es-shim-unscopables": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/arraybuffer.prototype.slice": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.3.tgz", + "integrity": "sha512-bMxMKAjg13EBSVscxTaYA4mRc5t1UAXa2kXiGTNfZ079HIWXEkKmkgFrh/nJqamaLSrXO5H4WFFkPEaLJWbs3A==", + "dev": true, + "license": "MIT", + "dependencies": { + "array-buffer-byte-length": "^1.0.1", + "call-bind": "^1.0.5", + "define-properties": "^1.2.1", + "es-abstract": "^1.22.3", + "es-errors": "^1.2.1", + "get-intrinsic": "^1.2.3", + "is-array-buffer": "^3.0.4", + "is-shared-array-buffer": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/ast-types-flow": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/ast-types-flow/-/ast-types-flow-0.0.8.tgz", + "integrity": "sha512-OH/2E5Fg20h2aPrbe+QL8JZQFko0YZaF+j4mnQ7BGhfavO7OpSLa8a0y9sBwomHdSbkhTS8TQNayBfnW5DwbvQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==" + }, + "node_modules/attr-accept": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/attr-accept/-/attr-accept-2.2.2.tgz", + "integrity": "sha512-7prDjvt9HmqiZ0cl5CRjtS84sEyhsHP2coDkaZKRKVfCDo9s7iw7ChVmar78Gu9pC4SoR/28wFu/G5JJhTnqEg==", + "engines": { + "node": ">=4" + } + }, + "node_modules/available-typed-arrays": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.7.tgz", + "integrity": "sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "possible-typed-array-names": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/axe-core": { + "version": "4.10.2", + "resolved": "https://registry.npmjs.org/axe-core/-/axe-core-4.10.2.tgz", + "integrity": "sha512-RE3mdQ7P3FRSe7eqCWoeQ/Z9QXrtniSjp1wUjt5nRC3WIpz5rSCve6o3fsZ2aCpJtrZjSZgjwXAoTO5k4tEI0w==", + "dev": true, + "license": "MPL-2.0", + "engines": { + "node": ">=4" + } + }, + "node_modules/axios": { + "version": "1.7.7", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.7.7.tgz", + "integrity": "sha512-S4kL7XrjgBmvdGut0sN3yJxqYzrDOnivkBiN0OFs6hLiUam3UPvswUo0kqGyhqUZGEOytHyumEdXsAkgCOUf3Q==", + "license": "MIT", + "dependencies": { + "follow-redirects": "^1.15.6", + "form-data": "^4.0.0", + "proxy-from-env": "^1.1.0" + } + }, + "node_modules/axios-mock-adapter": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/axios-mock-adapter/-/axios-mock-adapter-2.0.0.tgz", + "integrity": "sha512-D/K0J5Zm6KvaMTnsWrBQZWLzKN9GxUFZEa0mx2qeEHXDeTugCoplWehy8y36dj5vuSjhe1u/Dol8cZ8lzzmDew==", + "license": "MIT", + "dependencies": { + "fast-deep-equal": "^3.1.3", + "is-buffer": "^2.0.5" + }, + "peerDependencies": { + "axios": ">= 0.17.0" + } + }, + "node_modules/axobject-query": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/axobject-query/-/axobject-query-4.1.0.tgz", + "integrity": "sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/b4a": { + "version": "1.6.7", + "resolved": "https://registry.npmjs.org/b4a/-/b4a-1.6.7.tgz", + "integrity": "sha512-OnAYlL5b7LEkALw87fUVafQw5rVR9RjwGd4KUwNQ6DrrNmaVaUCgLipfVlzrPQ4tWOR9P0IXGNOx50jYCCdSJg==", + "license": "Apache-2.0" + }, + "node_modules/babel-plugin-macros": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/babel-plugin-macros/-/babel-plugin-macros-3.1.0.tgz", + "integrity": "sha512-Cg7TFGpIr01vOQNODXOOaGz2NpCU5gl8x1qJFbb6hbZxR7XrcE2vtbAsTAbJ7/xwJtUuJEw8K8Zr/AE0LHlesg==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.12.5", + "cosmiconfig": "^7.0.0", + "resolve": "^1.19.0" + }, + "engines": { + "node": ">=10", + "npm": ">=6" + } + }, + "node_modules/babel-plugin-macros/node_modules/cosmiconfig": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.1.0.tgz", + "integrity": "sha512-AdmX6xUzdNASswsFtmwSt7Vj8po9IuqXm0UXz7QKPuEUmPB4XyjGfaAr2PSuELMwkRMVH1EpIkX5bTZGRB3eCA==", + "license": "MIT", + "dependencies": { + "@types/parse-json": "^4.0.0", + "import-fresh": "^3.2.1", + "parse-json": "^5.0.0", + "path-type": "^4.0.0", + "yaml": "^1.10.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/babel-plugin-polyfill-corejs2": { + "version": "0.4.12", + "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs2/-/babel-plugin-polyfill-corejs2-0.4.12.tgz", + "integrity": "sha512-CPWT6BwvhrTO2d8QVorhTCQw9Y43zOu7G9HigcfxvepOU6b8o3tcWad6oVgZIsZCTt42FFv97aA7ZJsbM4+8og==", + "license": "MIT", + "dependencies": { + "@babel/compat-data": "^7.22.6", + "@babel/helper-define-polyfill-provider": "^0.6.3", + "semver": "^6.3.1" + }, + "peerDependencies": { + "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" + } + }, + "node_modules/babel-plugin-polyfill-corejs3": { + "version": "0.10.6", + "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.10.6.tgz", + "integrity": "sha512-b37+KR2i/khY5sKmWNVQAnitvquQbNdWy6lJdsr0kmquCKEEUgMKK4SboVM3HtfnZilfjr4MMQ7vY58FVWDtIA==", + "license": "MIT", + "dependencies": { + "@babel/helper-define-polyfill-provider": "^0.6.2", + "core-js-compat": "^3.38.0" + }, + "peerDependencies": { + "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" + } + }, + "node_modules/babel-plugin-polyfill-regenerator": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.6.3.tgz", + "integrity": "sha512-LiWSbl4CRSIa5x/JAU6jZiG9eit9w6mz+yVMFwDE83LAWvt0AfGBoZ7HS/mkhrKuh2ZlzfVZYKoLjXdqw6Yt7Q==", + "license": "MIT", + "dependencies": { + "@babel/helper-define-polyfill-provider": "^0.6.3" + }, + "peerDependencies": { + "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" + } + }, + "node_modules/bail": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/bail/-/bail-2.0.2.tgz", + "integrity": "sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "dev": true + }, + "node_modules/bare-events": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/bare-events/-/bare-events-2.5.0.tgz", + "integrity": "sha512-/E8dDe9dsbLyh2qrZ64PEPadOQ0F4gbl1sUJOrmph7xOiIxfY8vwab/4bFLh4Y88/Hk/ujKcrQKc+ps0mv873A==", + "license": "Apache-2.0", + "optional": true + }, + "node_modules/bare-fs": { + "version": "2.3.5", + "resolved": "https://registry.npmjs.org/bare-fs/-/bare-fs-2.3.5.tgz", + "integrity": "sha512-SlE9eTxifPDJrT6YgemQ1WGFleevzwY+XAP1Xqgl56HtcrisC2CHCZ2tq6dBpcH2TnNxwUEUGhweo+lrQtYuiw==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "bare-events": "^2.0.0", + "bare-path": "^2.0.0", + "bare-stream": "^2.0.0" + } + }, + "node_modules/bare-os": { + "version": "2.4.4", + "resolved": "https://registry.npmjs.org/bare-os/-/bare-os-2.4.4.tgz", + "integrity": "sha512-z3UiI2yi1mK0sXeRdc4O1Kk8aOa/e+FNWZcTiPB/dfTWyLypuE99LibgRaQki914Jq//yAWylcAt+mknKdixRQ==", + "license": "Apache-2.0", + "optional": true + }, + "node_modules/bare-path": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/bare-path/-/bare-path-2.1.3.tgz", + "integrity": "sha512-lh/eITfU8hrj9Ru5quUp0Io1kJWIk1bTjzo7JH1P5dWmQ2EL4hFUlfI8FonAhSlgIfhn63p84CDY/x+PisgcXA==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "bare-os": "^2.1.0" + } + }, + "node_modules/bare-stream": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/bare-stream/-/bare-stream-2.4.2.tgz", + "integrity": "sha512-XZ4ln/KV4KT+PXdIWTKjsLY+quqCaEtqqtgGJVPw9AoM73By03ij64YjepK0aQvHSWDb6AfAZwqKaFu68qkrdA==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "streamx": "^2.20.0" + } + }, + "node_modules/base64-js": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", + "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT" + }, + "node_modules/bl": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz", + "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==", + "license": "MIT", + "dependencies": { + "buffer": "^5.5.0", + "inherits": "^2.0.4", + "readable-stream": "^3.4.0" + } + }, + "node_modules/bl/node_modules/readable-stream": { + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", + "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", + "license": "MIT", + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/bl/node_modules/string_decoder": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", + "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", + "license": "MIT", + "dependencies": { + "safe-buffer": "~5.2.0" + } + }, + "node_modules/boolbase": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/boolbase/-/boolbase-1.0.0.tgz", + "integrity": "sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww==", + "license": "ISC" + }, + "node_modules/brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, + "dependencies": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "node_modules/braces": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz", + "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", + "dev": true, + "dependencies": { + "fill-range": "^7.1.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/browserslist": { + "version": "4.24.2", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.24.2.tgz", + "integrity": "sha512-ZIc+Q62revdMcqC6aChtW4jz3My3klmCO1fEmINZY/8J3EpBg5/A/D0AKmBveUh6pgoeycoMkVMko84tuYS+Gg==", + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/browserslist" + }, + { + "type": "github", + "url": "https://github.com/sponsors/ai" + } + ], + "license": "MIT", + "dependencies": { + "caniuse-lite": "^1.0.30001669", + "electron-to-chromium": "^1.5.41", + "node-releases": "^2.0.18", + "update-browserslist-db": "^1.1.1" + }, + "bin": { + "browserslist": "cli.js" + }, + "engines": { + "node": "^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7" + } + }, + "node_modules/buffer": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", + "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT", + "dependencies": { + "base64-js": "^1.3.1", + "ieee754": "^1.1.13" + } + }, + "node_modules/buffer-from": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-0.1.2.tgz", + "integrity": "sha512-RiWIenusJsmI2KcvqQABB83tLxCByE3upSP8QU3rJDMVFGPWLvPQJt/O1Su9moRWeH7d+Q2HYb68f6+v+tw2vg==", + "license": "MIT" + }, + "node_modules/call-bind": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz", + "integrity": "sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==", + "dev": true, + "dependencies": { + "es-define-property": "^1.0.0", + "es-errors": "^1.3.0", + "function-bind": "^1.1.2", + "get-intrinsic": "^1.2.4", + "set-function-length": "^1.2.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/callsites": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", + "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", + "engines": { + "node": ">=6" + } + }, + "node_modules/camelcase": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", + "integrity": "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==", + "license": "MIT", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/can-use-dom": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/can-use-dom/-/can-use-dom-0.1.0.tgz", + "integrity": "sha512-ceOhN1DL7Y4O6M0j9ICgmTYziV89WMd96SvSl0REd8PMgrY0B/WBOPoed5S1KUmJqXgUXh8gzSe6E3ae27upsQ==", + "license": "MIT" + }, + "node_modules/caniuse-lite": { + "version": "1.0.30001684", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001684.tgz", + "integrity": "sha512-G1LRwLIQjBQoyq0ZJGqGIJUXzJ8irpbjHLpVRXDvBEScFJ9b17sgK6vlx0GAJFE21okD7zXl08rRRUfq6HdoEQ==", + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/caniuse-lite" + }, + { + "type": "github", + "url": "https://github.com/sponsors/ai" + } + ], + "license": "CC-BY-4.0" + }, + "node_modules/ccount": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/ccount/-/ccount-2.0.1.tgz", + "integrity": "sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/chance": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/chance/-/chance-1.1.11.tgz", + "integrity": "sha512-kqTg3WWywappJPqtgrdvbA380VoXO2eu9VCV895JgbyHsaErXdyHK9LOZ911OvAk6L0obK7kDk9CGs8+oBawVA==" + }, + "node_modules/character-entities": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-1.2.4.tgz", + "integrity": "sha512-iBMyeEHxfVnIakwOuDXpVkc54HijNgCyQB2w0VfGQThle6NXn50zU6V/u+LDhxHcDUPojn6Kpga3PTAD8W1bQw==", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-entities-html4": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/character-entities-html4/-/character-entities-html4-2.1.0.tgz", + "integrity": "sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-entities-legacy": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-1.1.4.tgz", + "integrity": "sha512-3Xnr+7ZFS1uxeiUDvV02wQ+QDbc55o97tIV5zHScSPJpcLm/r0DFPcoY3tYRp+VZukxuMeKgXYmsXQHO05zQeA==", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-reference-invalid": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-1.1.4.tgz", + "integrity": "sha512-mKKUkUbhPpQlCOfIuZkvSEgktjPFIsZKRRbC6KWVEMvlzblj3i3asQv5ODsrwt0N3pHAEvjP8KTQPHkp0+6jOg==", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/chownr": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.4.tgz", + "integrity": "sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==", + "license": "ISC" + }, + "node_modules/classnames": { + "version": "2.5.1", + "resolved": "https://registry.npmjs.org/classnames/-/classnames-2.5.1.tgz", + "integrity": "sha512-saHYOzhIQs6wy2sVxTM6bUDsQO4F50V9RQ22qBpEdCW+I+/Wmke2HOl6lS6dTpdxVhb88/I6+Hs+438c3lfUow==" + }, + "node_modules/clsx": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/clsx/-/clsx-2.1.1.tgz", + "integrity": "sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA==", + "engines": { + "node": ">=6" + } + }, + "node_modules/color": { + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/color/-/color-4.2.3.tgz", + "integrity": "sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A==", + "license": "MIT", + "dependencies": { + "color-convert": "^2.0.1", + "color-string": "^1.9.0" + }, + "engines": { + "node": ">=12.5.0" + } + }, + "node_modules/color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==" + }, + "node_modules/color-string": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/color-string/-/color-string-1.9.1.tgz", + "integrity": "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg==", + "license": "MIT", + "dependencies": { + "color-name": "^1.0.0", + "simple-swizzle": "^0.2.2" + } + }, + "node_modules/color/node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "license": "MIT", + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/color/node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "license": "MIT" + }, + "node_modules/combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/comma-separated-tokens": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-1.0.8.tgz", + "integrity": "sha512-GHuDRO12Sypu2cV70d1dkA2EUmXHgntrzbpvOB+Qy+49ypNfGgFQIC2fhhXbnyrJRynDCAARsT7Ou0M6hirpfw==", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/commander": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz", + "integrity": "sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==", + "license": "MIT", + "engines": { + "node": ">= 10" + } + }, + "node_modules/concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", + "dev": true + }, + "node_modules/convert-source-map": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz", + "integrity": "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A==", + "license": "MIT" + }, + "node_modules/cookie": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-1.0.2.tgz", + "integrity": "sha512-9Kr/j4O16ISv8zBBhJoi4bXOYNTkFLOqSL3UDB0njXxCXNezjeyVrJyGOWtgfs/q2km1gwBcfH8q1yEGoMYunA==", + "license": "MIT", + "engines": { + "node": ">=18" + } + }, + "node_modules/core-js-compat": { + "version": "3.39.0", + "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.39.0.tgz", + "integrity": "sha512-VgEUx3VwlExr5no0tXlBt+silBvhTryPwCXRI2Id1PN8WTKu7MreethvddqOubrYxkFdv/RnYrqlv1sFNAUelw==", + "license": "MIT", + "dependencies": { + "browserslist": "^4.24.2" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/core-js" + } + }, + "node_modules/core-util-is": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz", + "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", + "license": "MIT" + }, + "node_modules/cosmiconfig": { + "version": "8.3.6", + "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-8.3.6.tgz", + "integrity": "sha512-kcZ6+W5QzcJ3P1Mt+83OUv/oHFqZHIx8DuxG6eZ5RGMERoLqp4BuGjhHLYGK+Kf5XVkQvqBSmAy/nGWN3qDgEA==", + "license": "MIT", + "dependencies": { + "import-fresh": "^3.3.0", + "js-yaml": "^4.1.0", + "parse-json": "^5.2.0", + "path-type": "^4.0.0" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "url": "https://github.com/sponsors/d-fischer" + }, + "peerDependencies": { + "typescript": ">=4.9.5" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/crelt": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/crelt/-/crelt-1.0.6.tgz", + "integrity": "sha512-VQ2MBenTq1fWZUH9DJNGti7kKv6EeAuYr3cLwxUWhIu1baTaXh4Ib5W2CqHVqib4/MqbYGJqiL3Zb8GJZr3l4g==", + "license": "MIT" + }, + "node_modules/cross-spawn": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", + "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==", + "dev": true, + "dependencies": { + "path-key": "^3.1.0", + "shebang-command": "^2.0.0", + "which": "^2.0.1" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/css-box-model": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/css-box-model/-/css-box-model-1.2.1.tgz", + "integrity": "sha512-a7Vr4Q/kd/aw96bnJG332W9V9LkJO69JRcaCYDUqjp6/z0w6VcZjgAcTbgFxEPfBgdnAwlh3iwu+hLopa+flJw==", + "dependencies": { + "tiny-invariant": "^1.0.6" + } + }, + "node_modules/css-select": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/css-select/-/css-select-5.1.0.tgz", + "integrity": "sha512-nwoRF1rvRRnnCqqY7updORDsuqKzqYJ28+oSMaJMMgOauh3fvwHqMS7EZpIPqK8GL+g9mKxF1vP/ZjSeNjEVHg==", + "license": "BSD-2-Clause", + "dependencies": { + "boolbase": "^1.0.0", + "css-what": "^6.1.0", + "domhandler": "^5.0.2", + "domutils": "^3.0.1", + "nth-check": "^2.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, + "node_modules/css-tree": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/css-tree/-/css-tree-2.3.1.tgz", + "integrity": "sha512-6Fv1DV/TYw//QF5IzQdqsNDjx/wc8TrMBZsqjL9eW01tWb7R7k/mq+/VXfJCl7SoD5emsJop9cOByJZfs8hYIw==", + "license": "MIT", + "dependencies": { + "mdn-data": "2.0.30", + "source-map-js": "^1.0.1" + }, + "engines": { + "node": "^10 || ^12.20.0 || ^14.13.0 || >=15.0.0" + } + }, + "node_modules/css-what": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/css-what/-/css-what-6.1.0.tgz", + "integrity": "sha512-HTUrgRJ7r4dsZKU6GjmpfRK1O76h97Z8MfS1G0FozR+oF2kG6Vfe8JE6zwrkbxigziPHinCJ+gCPjA9EaBDtRw==", + "license": "BSD-2-Clause", + "engines": { + "node": ">= 6" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, + "node_modules/cssjanus": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/cssjanus/-/cssjanus-2.3.0.tgz", + "integrity": "sha512-ZZXXn51SnxRxAZ6fdY7mBDPmA4OZd83q/J9Gdqz3YmE9TUq+9tZl+tdOnCi7PpNygI6PEkehj9rgifv5+W8a5A==", + "engines": { + "node": ">=10.0.0" + } + }, + "node_modules/csso": { + "version": "5.0.5", + "resolved": "https://registry.npmjs.org/csso/-/csso-5.0.5.tgz", + "integrity": "sha512-0LrrStPOdJj+SPCCrGhzryycLjwcgUSHBtxNA8aIDxf0GLsRh1cKYhB00Gd1lDOS4yGH69+SNn13+TWbVHETFQ==", + "license": "MIT", + "dependencies": { + "css-tree": "~2.2.0" + }, + "engines": { + "node": "^10 || ^12.20.0 || ^14.13.0 || >=15.0.0", + "npm": ">=7.0.0" + } + }, + "node_modules/csso/node_modules/css-tree": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/css-tree/-/css-tree-2.2.1.tgz", + "integrity": "sha512-OA0mILzGc1kCOCSJerOeqDxDQ4HOh+G8NbOJFOTgOCzpw7fCBubk0fEyxp8AgOL/jvLgYA/uV0cMbe43ElF1JA==", + "license": "MIT", + "dependencies": { + "mdn-data": "2.0.28", + "source-map-js": "^1.0.1" + }, + "engines": { + "node": "^10 || ^12.20.0 || ^14.13.0 || >=15.0.0", + "npm": ">=7.0.0" + } + }, + "node_modules/csso/node_modules/mdn-data": { + "version": "2.0.28", + "resolved": "https://registry.npmjs.org/mdn-data/-/mdn-data-2.0.28.tgz", + "integrity": "sha512-aylIc7Z9y4yzHYAJNuESG3hfhC+0Ibp/MAMiaOZgNv4pmEdFyfZhhhny4MNiAfWdBQ1RQ2mfDWmM1x8SvGyp8g==", + "license": "CC0-1.0" + }, + "node_modules/csstype": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz", + "integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==" + }, + "node_modules/d3-array": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/d3-array/-/d3-array-3.2.4.tgz", + "integrity": "sha512-tdQAmyA18i4J7wprpYq8ClcxZy3SC31QMeByyCFyRt7BVHdREQZ5lpzoe5mFEYZUWe+oq8HBvk9JjpibyEV4Jg==", + "license": "ISC", + "dependencies": { + "internmap": "1 - 2" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-color": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-color/-/d3-color-3.1.0.tgz", + "integrity": "sha512-zg/chbXyeBtMQ1LbD/WSoW2DpC3I0mpmPdW+ynRTj/x2DAWYrIY7qeZIHidozwV24m4iavr15lNwIwLxRmOxhA==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-delaunay": { + "version": "6.0.4", + "resolved": "https://registry.npmjs.org/d3-delaunay/-/d3-delaunay-6.0.4.tgz", + "integrity": "sha512-mdjtIZ1XLAM8bm/hx3WwjfHt6Sggek7qH043O8KEjDXN40xi3vx/6pYSVTwLjEgiXQTbvaouWKynLBiUZ6SK6A==", + "license": "ISC", + "dependencies": { + "delaunator": "5" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-format": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-format/-/d3-format-3.1.0.tgz", + "integrity": "sha512-YyUI6AEuY/Wpt8KWLgZHsIU86atmikuoOmCfommt0LYHiQSPjvX2AcFc38PX0CBpr2RCyZhjex+NS/LPOv6YqA==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-interpolate": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-interpolate/-/d3-interpolate-3.0.1.tgz", + "integrity": "sha512-3bYs1rOD33uo8aqJfKP3JWPAibgw8Zm2+L9vBKEHJ2Rg+viTR7o5Mmv5mZcieN+FRYaAOWX5SJATX6k1PWz72g==", + "license": "ISC", + "dependencies": { + "d3-color": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-path": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-path/-/d3-path-3.1.0.tgz", + "integrity": "sha512-p3KP5HCf/bvjBSSKuXid6Zqijx7wIfNW+J/maPs+iwR35at5JCbLUT0LzF1cnjbCHWhqzQTIN2Jpe8pRebIEFQ==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-scale": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/d3-scale/-/d3-scale-4.0.2.tgz", + "integrity": "sha512-GZW464g1SH7ag3Y7hXjf8RoUuAFIqklOAq3MRl4OaWabTFJY9PN/E1YklhXLh+OQ3fM9yS2nOkCoS+WLZ6kvxQ==", + "license": "ISC", + "dependencies": { + "d3-array": "2.10.0 - 3", + "d3-format": "1 - 3", + "d3-interpolate": "1.2.0 - 3", + "d3-time": "2.1.1 - 3", + "d3-time-format": "2 - 4" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-shape": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/d3-shape/-/d3-shape-3.2.0.tgz", + "integrity": "sha512-SaLBuwGm3MOViRq2ABk3eLoxwZELpH6zhl3FbAoJ7Vm1gofKx6El1Ib5z23NUEhF9AsGl7y+dzLe5Cw2AArGTA==", + "license": "ISC", + "dependencies": { + "d3-path": "^3.1.0" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-time": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-time/-/d3-time-3.1.0.tgz", + "integrity": "sha512-VqKjzBLejbSMT4IgbmVgDjpkYrNWUYJnbCGo874u7MMKIWsILRX+OpX/gTk8MqjpT1A/c6HY2dCA77ZN0lkQ2Q==", + "license": "ISC", + "dependencies": { + "d3-array": "2 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-time-format": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/d3-time-format/-/d3-time-format-4.1.0.tgz", + "integrity": "sha512-dJxPBlzC7NugB2PDLwo9Q8JiTR3M3e4/XANkreKSUxF8vvXKqm1Yfq4Q5dl8budlunRVlUUaDUgFt7eA8D6NLg==", + "license": "ISC", + "dependencies": { + "d3-time": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/damerau-levenshtein": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/damerau-levenshtein/-/damerau-levenshtein-1.0.8.tgz", + "integrity": "sha512-sdQSFB7+llfUcQHUQO3+B8ERRj0Oa4w9POWMI/puGtuf7gFywGmkaLCElnudfTiKZV+NvHqL0ifzdrI8Ro7ESA==", + "dev": true, + "license": "BSD-2-Clause" + }, + "node_modules/data-view-buffer": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/data-view-buffer/-/data-view-buffer-1.0.1.tgz", + "integrity": "sha512-0lht7OugA5x3iJLOWFhWK/5ehONdprk0ISXqVFn/NFrDu+cuc8iADFrGQz5BnRK7LLU3JmkbXSxaqX+/mXYtUA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.6", + "es-errors": "^1.3.0", + "is-data-view": "^1.0.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/data-view-byte-length": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/data-view-byte-length/-/data-view-byte-length-1.0.1.tgz", + "integrity": "sha512-4J7wRJD3ABAzr8wP+OcIcqq2dlUKp4DVflx++hs5h5ZKydWMI6/D/fAot+yh6g2tHh8fLFTvNOaVN357NvSrOQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "es-errors": "^1.3.0", + "is-data-view": "^1.0.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/data-view-byte-offset": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/data-view-byte-offset/-/data-view-byte-offset-1.0.0.tgz", + "integrity": "sha512-t/Ygsytq+R995EJ5PZlD4Cu56sWa8InXySaViRzw9apusqsOO2bQP+SbYzAhR0pFKoB+43lYy8rWban9JSuXnA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.6", + "es-errors": "^1.3.0", + "is-data-view": "^1.0.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/date-arithmetic": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/date-arithmetic/-/date-arithmetic-4.1.0.tgz", + "integrity": "sha512-QWxYLR5P/6GStZcdem+V1xoto6DMadYWpMXU82ES3/RfR3Wdwr3D0+be7mgOJ+Ov0G9D5Dmb9T17sNLQYj9XOg==" + }, + "node_modules/date-fns": { + "version": "2.30.0", + "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-2.30.0.tgz", + "integrity": "sha512-fnULvOpxnC5/Vg3NCiWelDsLiUc9bRwAPs/+LfTLNvetFCtCTN+yQz15C/fs4AwX1R9K5GLtLfn8QW+dWisaAw==", + "dependencies": { + "@babel/runtime": "^7.21.0" + }, + "engines": { + "node": ">=0.11" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/date-fns" + } + }, + "node_modules/dayjs": { + "version": "1.11.13", + "resolved": "https://registry.npmjs.org/dayjs/-/dayjs-1.11.13.tgz", + "integrity": "sha512-oaMBel6gjolK862uaPQOVTA7q3TZhuSvuMQAAglQDOWYO9A91IrAOUJEyKVlqJlHE0vq5p5UXxzdPfMH/x6xNg==", + "license": "MIT" + }, + "node_modules/debug": { + "version": "4.3.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.7.tgz", + "integrity": "sha512-Er2nc/H7RrMXZBFCEim6TCmMk02Z8vLC2Rbi1KEBggpo0fS6l0S1nnapwmIi3yW/+GOJap1Krg4w0Hg80oCqgQ==", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/decode-named-character-reference": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/decode-named-character-reference/-/decode-named-character-reference-1.0.2.tgz", + "integrity": "sha512-O8x12RzrUF8xyVcY0KJowWsmaJxQbmy0/EtnNtHRpsOcT7dFk5W598coHqBVpmWo1oQQfsCqfCmkZN5DJrZVdg==", + "license": "MIT", + "dependencies": { + "character-entities": "^2.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/decode-named-character-reference/node_modules/character-entities": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-2.0.2.tgz", + "integrity": "sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/decompress-response": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz", + "integrity": "sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==", + "license": "MIT", + "dependencies": { + "mimic-response": "^3.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "license": "MIT", + "engines": { + "node": ">=4.0.0" + } + }, + "node_modules/deep-is": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", + "integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==", + "dev": true + }, + "node_modules/deepmerge": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.3.1.tgz", + "integrity": "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/define-data-property": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", + "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", + "dev": true, + "dependencies": { + "es-define-property": "^1.0.0", + "es-errors": "^1.3.0", + "gopd": "^1.0.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/define-properties": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.2.1.tgz", + "integrity": "sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==", + "dev": true, + "dependencies": { + "define-data-property": "^1.0.1", + "has-property-descriptors": "^1.0.0", + "object-keys": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/delaunator": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/delaunator/-/delaunator-5.0.1.tgz", + "integrity": "sha512-8nvh+XBe96aCESrGOqMp/84b13H9cdKbG5P2ejQCh4d4sK9RL4371qou9drQjMhvnPmhWl5hnmqbEE0fXr9Xnw==", + "license": "ISC", + "dependencies": { + "robust-predicates": "^3.0.2" + } + }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/dequal": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", + "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", + "engines": { + "node": ">=6" + } + }, + "node_modules/detect-libc": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.0.3.tgz", + "integrity": "sha512-bwy0MGW55bG41VqxxypOsdSdGqLwXPI/focwgTYCFMbdUiBAxLg9CFzG08sz2aqzknwiX7Hkl0bQENjg8iLByw==", + "license": "Apache-2.0", + "engines": { + "node": ">=8" + } + }, + "node_modules/devlop": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/devlop/-/devlop-1.1.0.tgz", + "integrity": "sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==", + "license": "MIT", + "dependencies": { + "dequal": "^2.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/dir-glob": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", + "integrity": "sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==", + "dev": true, + "dependencies": { + "path-type": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/doctrine": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", + "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", + "dev": true, + "dependencies": { + "esutils": "^2.0.2" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/dom-helpers": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/dom-helpers/-/dom-helpers-5.2.1.tgz", + "integrity": "sha512-nRCa7CK3VTrM2NmGkIy4cbK7IZlgBE/PYMn55rrXefr5xXDP0LdtfPnblFDoVdcAfslJ7or6iqAUnx0CCGIWQA==", + "dependencies": { + "@babel/runtime": "^7.8.7", + "csstype": "^3.0.2" + } + }, + "node_modules/dom-serializer": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-2.0.0.tgz", + "integrity": "sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg==", + "license": "MIT", + "dependencies": { + "domelementtype": "^2.3.0", + "domhandler": "^5.0.2", + "entities": "^4.2.0" + }, + "funding": { + "url": "https://github.com/cheeriojs/dom-serializer?sponsor=1" + } + }, + "node_modules/domelementtype": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.3.0.tgz", + "integrity": "sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/fb55" + } + ], + "license": "BSD-2-Clause" + }, + "node_modules/domhandler": { + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-5.0.3.tgz", + "integrity": "sha512-cgwlv/1iFQiFnU96XXgROh8xTeetsnJiDsTc7TYCLFd9+/WNkIqPTxiM/8pSd8VIrhXGTf1Ny1q1hquVqDJB5w==", + "license": "BSD-2-Clause", + "dependencies": { + "domelementtype": "^2.3.0" + }, + "engines": { + "node": ">= 4" + }, + "funding": { + "url": "https://github.com/fb55/domhandler?sponsor=1" + } + }, + "node_modules/domutils": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/domutils/-/domutils-3.1.0.tgz", + "integrity": "sha512-H78uMmQtI2AhgDJjWeQmHwJJ2bLPD3GMmO7Zja/ZZh84wkm+4ut+IUnUdRa8uCGX88DiVx1j6FRe1XfxEgjEZA==", + "license": "BSD-2-Clause", + "dependencies": { + "dom-serializer": "^2.0.0", + "domelementtype": "^2.3.0", + "domhandler": "^5.0.3" + }, + "funding": { + "url": "https://github.com/fb55/domutils?sponsor=1" + } + }, + "node_modules/dot-case": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/dot-case/-/dot-case-3.0.4.tgz", + "integrity": "sha512-Kv5nKlh6yRrdrGvxeJ2e5y2eRUpkUosIW4A2AS38zwSz27zu7ufDwQPi5Jhs3XAlGNetl3bmnGhQsMtkKJnj3w==", + "license": "MIT", + "dependencies": { + "no-case": "^3.0.4", + "tslib": "^2.0.3" + } + }, + "node_modules/duplexer2": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/duplexer2/-/duplexer2-0.1.4.tgz", + "integrity": "sha512-asLFVfWWtJ90ZyOUHMqk7/S2w2guQKxUI2itj3d92ADHhxUSbCMGi1f1cBcJ7xM1To+pE/Khbwo1yuNbMEPKeA==", + "license": "BSD-3-Clause", + "dependencies": { + "readable-stream": "^2.0.2" + } + }, + "node_modules/duplexer2/node_modules/isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", + "license": "MIT" + }, + "node_modules/duplexer2/node_modules/readable-stream": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", + "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", + "license": "MIT", + "dependencies": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" + } + }, + "node_modules/duplexer2/node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "license": "MIT" + }, + "node_modules/duplexer2/node_modules/string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "license": "MIT", + "dependencies": { + "safe-buffer": "~5.1.0" + } + }, + "node_modules/electron-to-chromium": { + "version": "1.5.65", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.65.tgz", + "integrity": "sha512-PWVzBjghx7/wop6n22vS2MLU8tKGd4Q91aCEGhG/TYmW6PP5OcSXcdnxTe1NNt0T66N8D6jxh4kC8UsdzOGaIw==", + "license": "ISC" + }, + "node_modules/emoji-picker-react": { + "version": "4.12.0", + "resolved": "https://registry.npmjs.org/emoji-picker-react/-/emoji-picker-react-4.12.0.tgz", + "integrity": "sha512-q2c8UcZH0eRIMj41bj0k1akTjk69tsu+E7EzkW7giN66iltF6H9LQvQvw6ugscsxdC+1lmt3WZpQkkY65J95tg==", + "license": "MIT", + "dependencies": { + "flairup": "1.0.0" + }, + "engines": { + "node": ">=10" + }, + "peerDependencies": { + "react": ">=16" + } + }, + "node_modules/emoji-regex": { + "version": "9.2.2", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", + "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", + "dev": true, + "license": "MIT" + }, + "node_modules/encodeurl": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", + "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/end-of-stream": { + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "license": "MIT", + "dependencies": { + "once": "^1.4.0" + } + }, + "node_modules/enhanced-resolve": { + "version": "5.17.1", + "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.17.1.tgz", + "integrity": "sha512-LMHl3dXhTcfv8gM4kEzIUeTQ+7fpdA0l2tUf34BddXPkz2A5xJ5L/Pchd5BL6rdccM9QGvu0sWZzK1Z1t4wwyg==", + "dev": true, + "license": "MIT", + "dependencies": { + "graceful-fs": "^4.2.4", + "tapable": "^2.2.0" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/enquire.js": { + "version": "2.1.6", + "resolved": "https://registry.npmjs.org/enquire.js/-/enquire.js-2.1.6.tgz", + "integrity": "sha512-/KujNpO+PT63F7Hlpu4h3pE3TokKRHN26JYmQpPyjkRD/N57R7bPDNojMXdi7uveAKjYB7yQnartCxZnFWr0Xw==" + }, + "node_modules/entities": { + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-4.5.0.tgz", + "integrity": "sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==", + "engines": { + "node": ">=0.12" + }, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, + "node_modules/error-ex": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", + "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", + "dependencies": { + "is-arrayish": "^0.2.1" + } + }, + "node_modules/es-abstract": { + "version": "1.23.5", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.23.5.tgz", + "integrity": "sha512-vlmniQ0WNPwXqA0BnmwV3Ng7HxiGlh6r5U6JcTMNx8OilcAGqVJBHJcPjqOMaczU9fRuRK5Px2BdVyPRnKMMVQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "array-buffer-byte-length": "^1.0.1", + "arraybuffer.prototype.slice": "^1.0.3", + "available-typed-arrays": "^1.0.7", + "call-bind": "^1.0.7", + "data-view-buffer": "^1.0.1", + "data-view-byte-length": "^1.0.1", + "data-view-byte-offset": "^1.0.0", + "es-define-property": "^1.0.0", + "es-errors": "^1.3.0", + "es-object-atoms": "^1.0.0", + "es-set-tostringtag": "^2.0.3", + "es-to-primitive": "^1.2.1", + "function.prototype.name": "^1.1.6", + "get-intrinsic": "^1.2.4", + "get-symbol-description": "^1.0.2", + "globalthis": "^1.0.4", + "gopd": "^1.0.1", + "has-property-descriptors": "^1.0.2", + "has-proto": "^1.0.3", + "has-symbols": "^1.0.3", + "hasown": "^2.0.2", + "internal-slot": "^1.0.7", + "is-array-buffer": "^3.0.4", + "is-callable": "^1.2.7", + "is-data-view": "^1.0.1", + "is-negative-zero": "^2.0.3", + "is-regex": "^1.1.4", + "is-shared-array-buffer": "^1.0.3", + "is-string": "^1.0.7", + "is-typed-array": "^1.1.13", + "is-weakref": "^1.0.2", + "object-inspect": "^1.13.3", + "object-keys": "^1.1.1", + "object.assign": "^4.1.5", + "regexp.prototype.flags": "^1.5.3", + "safe-array-concat": "^1.1.2", + "safe-regex-test": "^1.0.3", + "string.prototype.trim": "^1.2.9", + "string.prototype.trimend": "^1.0.8", + "string.prototype.trimstart": "^1.0.8", + "typed-array-buffer": "^1.0.2", + "typed-array-byte-length": "^1.0.1", + "typed-array-byte-offset": "^1.0.2", + "typed-array-length": "^1.0.6", + "unbox-primitive": "^1.0.2", + "which-typed-array": "^1.1.15" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/es-define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.0.tgz", + "integrity": "sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.2.4" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-errors": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", + "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", + "dev": true, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-iterator-helpers": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.2.0.tgz", + "integrity": "sha512-tpxqxncxnpw3c93u8n3VOzACmRFoVmWJqbWXvX/JfKbkhBw1oslgPrUfeSt2psuqyEJFD6N/9lg5i7bsKpoq+Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.3", + "es-errors": "^1.3.0", + "es-set-tostringtag": "^2.0.3", + "function-bind": "^1.1.2", + "get-intrinsic": "^1.2.4", + "globalthis": "^1.0.4", + "gopd": "^1.0.1", + "has-property-descriptors": "^1.0.2", + "has-proto": "^1.0.3", + "has-symbols": "^1.0.3", + "internal-slot": "^1.0.7", + "iterator.prototype": "^1.1.3", + "safe-array-concat": "^1.1.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-object-atoms": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.0.0.tgz", + "integrity": "sha512-MZ4iQ6JwHOBQjahnjwaC1ZtIBH+2ohjamzAO3oaHcXYup7qxjF2fixyH+Q71voWHeOkI2q/TnJao/KfXYIZWbw==", + "dev": true, + "license": "MIT", + "dependencies": { + "es-errors": "^1.3.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-set-tostringtag": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.0.3.tgz", + "integrity": "sha512-3T8uNMC3OQTHkFUsFq8r/BwAXLHvU/9O9mE0fBc/MY5iq/8H7ncvO947LmYA6ldWw9Uh8Yhf25zu6n7nML5QWQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "get-intrinsic": "^1.2.4", + "has-tostringtag": "^1.0.2", + "hasown": "^2.0.1" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-shim-unscopables": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/es-shim-unscopables/-/es-shim-unscopables-1.0.2.tgz", + "integrity": "sha512-J3yBRXCzDu4ULnQwxyToo/OjdMx6akgVC7K6few0a7F/0wLtmKKN7I73AH5T2836UuXRqN7Qg+IIUw/+YJksRw==", + "dev": true, + "license": "MIT", + "dependencies": { + "hasown": "^2.0.0" + } + }, + "node_modules/es-to-primitive": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.1.tgz", + "integrity": "sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-callable": "^1.1.4", + "is-date-object": "^1.0.1", + "is-symbol": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/esbuild": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.24.0.tgz", + "integrity": "sha512-FuLPevChGDshgSicjisSooU0cemp/sGXR841D5LHMB7mTVOmsEHcAxaH3irL53+8YDIeVNQEySh4DaYU/iuPqQ==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "bin": { + "esbuild": "bin/esbuild" + }, + "engines": { + "node": ">=18" + }, + "optionalDependencies": { + "@esbuild/aix-ppc64": "0.24.0", + "@esbuild/android-arm": "0.24.0", + "@esbuild/android-arm64": "0.24.0", + "@esbuild/android-x64": "0.24.0", + "@esbuild/darwin-arm64": "0.24.0", + "@esbuild/darwin-x64": "0.24.0", + "@esbuild/freebsd-arm64": "0.24.0", + "@esbuild/freebsd-x64": "0.24.0", + "@esbuild/linux-arm": "0.24.0", + "@esbuild/linux-arm64": "0.24.0", + "@esbuild/linux-ia32": "0.24.0", + "@esbuild/linux-loong64": "0.24.0", + "@esbuild/linux-mips64el": "0.24.0", + "@esbuild/linux-ppc64": "0.24.0", + "@esbuild/linux-riscv64": "0.24.0", + "@esbuild/linux-s390x": "0.24.0", + "@esbuild/linux-x64": "0.24.0", + "@esbuild/netbsd-x64": "0.24.0", + "@esbuild/openbsd-arm64": "0.24.0", + "@esbuild/openbsd-x64": "0.24.0", + "@esbuild/sunos-x64": "0.24.0", + "@esbuild/win32-arm64": "0.24.0", + "@esbuild/win32-ia32": "0.24.0", + "@esbuild/win32-x64": "0.24.0" + } + }, + "node_modules/escalade": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.2.0.tgz", + "integrity": "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, + "node_modules/escape-string-regexp": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", + "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/eslint": { + "version": "8.45.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.45.0.tgz", + "integrity": "sha512-pd8KSxiQpdYRfYa9Wufvdoct3ZPQQuVuU5O6scNgMuOMYuxvH0IGaYK0wUFjo4UYYQQCUndlXiMbnxopwvvTiw==", + "dev": true, + "dependencies": { + "@eslint-community/eslint-utils": "^4.2.0", + "@eslint-community/regexpp": "^4.4.0", + "@eslint/eslintrc": "^2.1.0", + "@eslint/js": "8.44.0", + "@humanwhocodes/config-array": "^0.11.10", + "@humanwhocodes/module-importer": "^1.0.1", + "@nodelib/fs.walk": "^1.2.8", + "ajv": "^6.10.0", + "chalk": "^4.0.0", + "cross-spawn": "^7.0.2", + "debug": "^4.3.2", + "doctrine": "^3.0.0", + "escape-string-regexp": "^4.0.0", + "eslint-scope": "^7.2.0", + "eslint-visitor-keys": "^3.4.1", + "espree": "^9.6.0", + "esquery": "^1.4.2", + "esutils": "^2.0.2", + "fast-deep-equal": "^3.1.3", + "file-entry-cache": "^6.0.1", + "find-up": "^5.0.0", + "glob-parent": "^6.0.2", + "globals": "^13.19.0", + "graphemer": "^1.4.0", + "ignore": "^5.2.0", + "imurmurhash": "^0.1.4", + "is-glob": "^4.0.0", + "is-path-inside": "^3.0.3", + "js-yaml": "^4.1.0", + "json-stable-stringify-without-jsonify": "^1.0.1", + "levn": "^0.4.1", + "lodash.merge": "^4.6.2", + "minimatch": "^3.1.2", + "natural-compare": "^1.4.0", + "optionator": "^0.9.3", + "strip-ansi": "^6.0.1", + "text-table": "^0.2.0" + }, + "bin": { + "eslint": "bin/eslint.js" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/eslint-config-next": { + "version": "15.0.3", + "resolved": "https://registry.npmjs.org/eslint-config-next/-/eslint-config-next-15.0.3.tgz", + "integrity": "sha512-IGP2DdQQrgjcr4mwFPve4DrCqo7CVVez1WoYY47XwKSrYO4hC0Dlb+iJA60i0YfICOzgNADIb8r28BpQ5Zs0wg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@next/eslint-plugin-next": "15.0.3", + "@rushstack/eslint-patch": "^1.10.3", + "@typescript-eslint/eslint-plugin": "^5.4.2 || ^6.0.0 || ^7.0.0 || ^8.0.0", + "@typescript-eslint/parser": "^5.4.2 || ^6.0.0 || ^7.0.0 || ^8.0.0", + "eslint-import-resolver-node": "^0.3.6", + "eslint-import-resolver-typescript": "^3.5.2", + "eslint-plugin-import": "^2.31.0", + "eslint-plugin-jsx-a11y": "^6.10.0", + "eslint-plugin-react": "^7.35.0", + "eslint-plugin-react-hooks": "^5.0.0" + }, + "peerDependencies": { + "eslint": "^7.23.0 || ^8.0.0 || ^9.0.0", + "typescript": ">=3.3.1" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/eslint-import-resolver-node": { + "version": "0.3.9", + "resolved": "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.9.tgz", + "integrity": "sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g==", + "dev": true, + "license": "MIT", + "dependencies": { + "debug": "^3.2.7", + "is-core-module": "^2.13.0", + "resolve": "^1.22.4" + } + }, + "node_modules/eslint-import-resolver-node/node_modules/debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.1" + } + }, + "node_modules/eslint-import-resolver-typescript": { + "version": "3.6.3", + "resolved": "https://registry.npmjs.org/eslint-import-resolver-typescript/-/eslint-import-resolver-typescript-3.6.3.tgz", + "integrity": "sha512-ud9aw4szY9cCT1EWWdGv1L1XR6hh2PaRWif0j2QjQ0pgTY/69iw+W0Z4qZv5wHahOl8isEr+k/JnyAqNQkLkIA==", + "dev": true, + "license": "ISC", + "dependencies": { + "@nolyfill/is-core-module": "1.0.39", + "debug": "^4.3.5", + "enhanced-resolve": "^5.15.0", + "eslint-module-utils": "^2.8.1", + "fast-glob": "^3.3.2", + "get-tsconfig": "^4.7.5", + "is-bun-module": "^1.0.2", + "is-glob": "^4.0.3" + }, + "engines": { + "node": "^14.18.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/unts/projects/eslint-import-resolver-ts" + }, + "peerDependencies": { + "eslint": "*", + "eslint-plugin-import": "*", + "eslint-plugin-import-x": "*" + }, + "peerDependenciesMeta": { + "eslint-plugin-import": { + "optional": true + }, + "eslint-plugin-import-x": { + "optional": true + } + } + }, + "node_modules/eslint-module-utils": { + "version": "2.12.0", + "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.12.0.tgz", + "integrity": "sha512-wALZ0HFoytlyh/1+4wuZ9FJCD/leWHQzzrxJ8+rebyReSLk7LApMyd3WJaLVoN+D5+WIdJyDK1c6JnE65V4Zyg==", + "dev": true, + "license": "MIT", + "dependencies": { + "debug": "^3.2.7" + }, + "engines": { + "node": ">=4" + }, + "peerDependenciesMeta": { + "eslint": { + "optional": true + } + } + }, + "node_modules/eslint-module-utils/node_modules/debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.1" + } + }, + "node_modules/eslint-plugin-import": { + "version": "2.31.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.31.0.tgz", + "integrity": "sha512-ixmkI62Rbc2/w8Vfxyh1jQRTdRTF52VxwRVHl/ykPAmqG+Nb7/kNn+byLP0LxPgI7zWA16Jt82SybJInmMia3A==", + "dev": true, + "license": "MIT", + "dependencies": { + "@rtsao/scc": "^1.1.0", + "array-includes": "^3.1.8", + "array.prototype.findlastindex": "^1.2.5", + "array.prototype.flat": "^1.3.2", + "array.prototype.flatmap": "^1.3.2", + "debug": "^3.2.7", + "doctrine": "^2.1.0", + "eslint-import-resolver-node": "^0.3.9", + "eslint-module-utils": "^2.12.0", + "hasown": "^2.0.2", + "is-core-module": "^2.15.1", + "is-glob": "^4.0.3", + "minimatch": "^3.1.2", + "object.fromentries": "^2.0.8", + "object.groupby": "^1.0.3", + "object.values": "^1.2.0", + "semver": "^6.3.1", + "string.prototype.trimend": "^1.0.8", + "tsconfig-paths": "^3.15.0" + }, + "engines": { + "node": ">=4" + }, + "peerDependencies": { + "eslint": "^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8 || ^9" + } + }, + "node_modules/eslint-plugin-import/node_modules/debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.1" + } + }, + "node_modules/eslint-plugin-import/node_modules/doctrine": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", + "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "esutils": "^2.0.2" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/eslint-plugin-jsx-a11y": { + "version": "6.10.2", + "resolved": "https://registry.npmjs.org/eslint-plugin-jsx-a11y/-/eslint-plugin-jsx-a11y-6.10.2.tgz", + "integrity": "sha512-scB3nz4WmG75pV8+3eRUQOHZlNSUhFNq37xnpgRkCCELU3XMvXAxLk1eqWWyE22Ki4Q01Fnsw9BA3cJHDPgn2Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "aria-query": "^5.3.2", + "array-includes": "^3.1.8", + "array.prototype.flatmap": "^1.3.2", + "ast-types-flow": "^0.0.8", + "axe-core": "^4.10.0", + "axobject-query": "^4.1.0", + "damerau-levenshtein": "^1.0.8", + "emoji-regex": "^9.2.2", + "hasown": "^2.0.2", + "jsx-ast-utils": "^3.3.5", + "language-tags": "^1.0.9", + "minimatch": "^3.1.2", + "object.fromentries": "^2.0.8", + "safe-regex-test": "^1.0.3", + "string.prototype.includes": "^2.0.1" + }, + "engines": { + "node": ">=4.0" + }, + "peerDependencies": { + "eslint": "^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9" + } + }, + "node_modules/eslint-plugin-react": { + "version": "7.37.2", + "resolved": "https://registry.npmjs.org/eslint-plugin-react/-/eslint-plugin-react-7.37.2.tgz", + "integrity": "sha512-EsTAnj9fLVr/GZleBLFbj/sSuXeWmp1eXIN60ceYnZveqEaUCyW4X+Vh4WTdUhCkW4xutXYqTXCUSyqD4rB75w==", + "dev": true, + "license": "MIT", + "dependencies": { + "array-includes": "^3.1.8", + "array.prototype.findlast": "^1.2.5", + "array.prototype.flatmap": "^1.3.2", + "array.prototype.tosorted": "^1.1.4", + "doctrine": "^2.1.0", + "es-iterator-helpers": "^1.1.0", + "estraverse": "^5.3.0", + "hasown": "^2.0.2", + "jsx-ast-utils": "^2.4.1 || ^3.0.0", + "minimatch": "^3.1.2", + "object.entries": "^1.1.8", + "object.fromentries": "^2.0.8", + "object.values": "^1.2.0", + "prop-types": "^15.8.1", + "resolve": "^2.0.0-next.5", + "semver": "^6.3.1", + "string.prototype.matchall": "^4.0.11", + "string.prototype.repeat": "^1.0.0" + }, + "engines": { + "node": ">=4" + }, + "peerDependencies": { + "eslint": "^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9.7" + } + }, + "node_modules/eslint-plugin-react-hooks": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-react-hooks/-/eslint-plugin-react-hooks-5.0.0.tgz", + "integrity": "sha512-hIOwI+5hYGpJEc4uPRmz2ulCjAGD/N13Lukkh8cLV0i2IRk/bdZDYjgLVHj+U9Z704kLIdIO6iueGvxNur0sgw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=10" + }, + "peerDependencies": { + "eslint": "^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0-0 || ^9.0.0" + } + }, + "node_modules/eslint-plugin-react/node_modules/doctrine": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", + "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "esutils": "^2.0.2" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/eslint-plugin-react/node_modules/resolve": { + "version": "2.0.0-next.5", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-2.0.0-next.5.tgz", + "integrity": "sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-core-module": "^2.13.0", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + }, + "bin": { + "resolve": "bin/resolve" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/eslint-scope": { + "version": "7.2.2", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-7.2.2.tgz", + "integrity": "sha512-dOt21O7lTMhDM+X9mB4GX+DZrZtCUJPL/wlcTqxyrx5IvO0IYtILdtrQGQp+8n5S0gwSVmOf9NQrjMOgfQZlIg==", + "dev": true, + "dependencies": { + "esrecurse": "^4.3.0", + "estraverse": "^5.2.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/eslint-visitor-keys": { + "version": "3.4.3", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.4.3.tgz", + "integrity": "sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==", + "dev": true, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/eslint/node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/eslint/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/eslint/node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/eslint/node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, + "node_modules/eslint/node_modules/globals": { + "version": "13.24.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-13.24.0.tgz", + "integrity": "sha512-AhO5QUcj8llrbG09iWhPU2B204J1xnPeL8kQmVorSsy+Sjj1sk8gIyh6cUocGmH4L0UuhAJy+hJMRA4mgA4mFQ==", + "dev": true, + "dependencies": { + "type-fest": "^0.20.2" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/eslint/node_modules/has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/eslint/node_modules/supports-color": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/espree": { + "version": "9.6.1", + "resolved": "https://registry.npmjs.org/espree/-/espree-9.6.1.tgz", + "integrity": "sha512-oruZaFkjorTpF32kDSI5/75ViwGeZginGGy2NoOSg3Q9bnwlnmDm4HLnkl0RE3n+njDXR037aY1+x58Z/zFdwQ==", + "dev": true, + "dependencies": { + "acorn": "^8.9.0", + "acorn-jsx": "^5.3.2", + "eslint-visitor-keys": "^3.4.1" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/esprima": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", + "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", + "license": "BSD-2-Clause", + "bin": { + "esparse": "bin/esparse.js", + "esvalidate": "bin/esvalidate.js" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/esquery": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.6.0.tgz", + "integrity": "sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==", + "dev": true, + "dependencies": { + "estraverse": "^5.1.0" + }, + "engines": { + "node": ">=0.10" + } + }, + "node_modules/esrecurse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", + "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", + "dev": true, + "dependencies": { + "estraverse": "^5.2.0" + }, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/estree-walker": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-2.0.2.tgz", + "integrity": "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==", + "license": "MIT" + }, + "node_modules/esutils": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", + "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/expand-template": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/expand-template/-/expand-template-2.0.3.tgz", + "integrity": "sha512-XYfuKMvj4O35f/pOXLObndIRvyQ+/+6AhODh+OKWj9S9498pHHn/IMszH+gt0fBCRWMNfk1ZSp5x3AifmnI2vg==", + "license": "(MIT OR WTFPL)", + "engines": { + "node": ">=6" + } + }, + "node_modules/extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" + }, + "node_modules/extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha512-zCnTtlxNoAiDc3gqY2aYAWFx7XWWiasuF2K8Me5WbN8otHKTUKBwjPtNpRs/rbUZm7KxWAaNj7P1a/p52GbVug==", + "license": "MIT", + "dependencies": { + "is-extendable": "^0.1.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==" + }, + "node_modules/fast-fifo": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/fast-fifo/-/fast-fifo-1.3.2.tgz", + "integrity": "sha512-/d9sfos4yxzpwkDkuN7k2SqFKtYNmCTzgfEpz82x34IM9/zc8KGxQoXg1liNC/izpRM/MBdt44Nmx41ZWqk+FQ==", + "license": "MIT" + }, + "node_modules/fast-glob": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.3.2.tgz", + "integrity": "sha512-oX2ruAFQwf/Orj8m737Y5adxDQO0LAB7/S5MnxCdTNDd4p6BsyIVsv9JQsATbTSq8KHRpLwIHbVlUNatxd+1Ow==", + "dev": true, + "dependencies": { + "@nodelib/fs.stat": "^2.0.2", + "@nodelib/fs.walk": "^1.2.3", + "glob-parent": "^5.1.2", + "merge2": "^1.3.0", + "micromatch": "^4.0.4" + }, + "engines": { + "node": ">=8.6.0" + } + }, + "node_modules/fast-glob/node_modules/glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "dev": true, + "dependencies": { + "is-glob": "^4.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/fast-json-stable-stringify": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", + "dev": true + }, + "node_modules/fast-levenshtein": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", + "integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==", + "dev": true + }, + "node_modules/fastq": { + "version": "1.17.1", + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.17.1.tgz", + "integrity": "sha512-sRVD3lWVIXWg6By68ZN7vho9a1pQcN/WBFaAAsDDFzlJjvoGx0P8z7V1t72grFJfJhu3YPZBuu25f7Kaw2jN1w==", + "dev": true, + "dependencies": { + "reusify": "^1.0.4" + } + }, + "node_modules/fault": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/fault/-/fault-1.0.4.tgz", + "integrity": "sha512-CJ0HCB5tL5fYTEA7ToAq5+kTwd++Borf1/bifxd9iT70QcXr4MRrO3Llf8Ifs70q+SJcGHFtnIE/Nw6giCtECA==", + "dependencies": { + "format": "^0.2.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/file-entry-cache": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-6.0.1.tgz", + "integrity": "sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg==", + "dev": true, + "dependencies": { + "flat-cache": "^3.0.4" + }, + "engines": { + "node": "^10.12.0 || >=12.0.0" + } + }, + "node_modules/file-selector": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/file-selector/-/file-selector-0.6.0.tgz", + "integrity": "sha512-QlZ5yJC0VxHxQQsQhXvBaC7VRJ2uaxTf+Tfpu4Z/OcVQJVpZO+DGU0rkoVW5ce2SccxugvpBJoMvUs59iILYdw==", + "dependencies": { + "tslib": "^2.4.0" + }, + "engines": { + "node": ">= 12" + } + }, + "node_modules/fill-range": { + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", + "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", + "dev": true, + "dependencies": { + "to-regex-range": "^5.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/find-root": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/find-root/-/find-root-1.1.0.tgz", + "integrity": "sha512-NKfW6bec6GfKc0SGx1e07QZY9PE99u0Bft/0rzSD5k3sO/vwkVUpDUKVm5Gpp5Ue3YfShPFTX2070tDs5kB9Ng==", + "license": "MIT" + }, + "node_modules/find-up": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", + "integrity": "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==", + "dev": true, + "dependencies": { + "locate-path": "^6.0.0", + "path-exists": "^4.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/flairup": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/flairup/-/flairup-1.0.0.tgz", + "integrity": "sha512-IKlE+pNvL2R+kVL1kEhUYqRxVqeFnjiIvHWDMLFXNaqyUdFXQM2wte44EfMYJNHkW16X991t2Zg8apKkhv7OBA==", + "license": "MIT" + }, + "node_modules/flat-cache": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-3.2.0.tgz", + "integrity": "sha512-CYcENa+FtcUKLmhhqyctpclsq7QF38pKjZHsGNiSQF5r4FtoKDWabFDl3hzaEQMvT1LHEysw5twgLvpYYb4vbw==", + "dev": true, + "dependencies": { + "flatted": "^3.2.9", + "keyv": "^4.5.3", + "rimraf": "^3.0.2" + }, + "engines": { + "node": "^10.12.0 || >=12.0.0" + } + }, + "node_modules/flatted": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.3.1.tgz", + "integrity": "sha512-X8cqMLLie7KsNUDSdzeN8FYK9rEt4Dt67OsG/DNGnYTSDBG4uFAJFBnUeiV+zCVAvwFy56IjM9sH51jVaEhNxw==", + "dev": true + }, + "node_modules/follow-redirects": { + "version": "1.15.9", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.9.tgz", + "integrity": "sha512-gew4GsXizNgdoRyqmyfMHyAmXsZDk6mHkSxZFCzW9gwlbtOW44CDtYavM+y+72qD/Vq2l550kMF52DT8fOLJqQ==", + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/RubenVerborgh" + } + ], + "engines": { + "node": ">=4.0" + }, + "peerDependenciesMeta": { + "debug": { + "optional": true + } + } + }, + "node_modules/for-each": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", + "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-callable": "^1.1.3" + } + }, + "node_modules/form-data": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz", + "integrity": "sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==", + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/format": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/format/-/format-0.2.2.tgz", + "integrity": "sha512-wzsgA6WOq+09wrU1tsJ09udeR/YZRaeArL9e1wPbFg3GG2yDnC2ldKpxs4xunpFF9DgqCqOIra3bc1HWrJ37Ww==", + "engines": { + "node": ">=0.4.x" + } + }, + "node_modules/formik": { + "version": "2.4.5", + "resolved": "https://registry.npmjs.org/formik/-/formik-2.4.5.tgz", + "integrity": "sha512-Gxlht0TD3vVdzMDHwkiNZqJ7Mvg77xQNfmBRrNtvzcHZs72TJppSTDKHpImCMJZwcWPBJ8jSQQ95GJzXFf1nAQ==", + "funding": [ + { + "type": "individual", + "url": "https://opencollective.com/formik" + } + ], + "dependencies": { + "@types/hoist-non-react-statics": "^3.3.1", + "deepmerge": "^2.1.1", + "hoist-non-react-statics": "^3.3.0", + "lodash": "^4.17.21", + "lodash-es": "^4.17.21", + "react-fast-compare": "^2.0.1", + "tiny-warning": "^1.0.2", + "tslib": "^2.0.0" + }, + "peerDependencies": { + "react": ">=16.8.0" + } + }, + "node_modules/formik-mui": { + "version": "5.0.0-alpha.1", + "resolved": "https://registry.npmjs.org/formik-mui/-/formik-mui-5.0.0-alpha.1.tgz", + "integrity": "sha512-sHzrQwAWdVuKOdI0Xe1kCzXSjKXr50Jcot+szLc64SPw06J4DqwXN3GNxbhvfyEBGJBIL36e+cSSbm2i++tqqg==", + "license": "MIT", + "peerDependencies": { + "@mui/material": ">5.6.0", + "formik": ">=2.2.9", + "react": ">=17.0.2", + "tiny-warning": ">=1.0.3" + } + }, + "node_modules/formik/node_modules/deepmerge": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-2.2.1.tgz", + "integrity": "sha512-R9hc1Xa/NOBi9WRVUWg19rl1UB7Tt4kuPd+thNJgFZoxXsTz7ncaPaeIm+40oSGuP33DfMb4sZt1QIGiJzC4EA==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/framer-motion": { + "version": "10.16.4", + "resolved": "https://registry.npmjs.org/framer-motion/-/framer-motion-10.16.4.tgz", + "integrity": "sha512-p9V9nGomS3m6/CALXqv6nFGMuFOxbWsmaOrdmhyQimMIlLl3LC7h7l86wge/Js/8cRu5ktutS/zlzgR7eBOtFA==", + "dependencies": { + "tslib": "^2.4.0" + }, + "optionalDependencies": { + "@emotion/is-prop-valid": "^0.8.2" + }, + "peerDependencies": { + "react": "^18.0.0", + "react-dom": "^18.0.0" + }, + "peerDependenciesMeta": { + "react": { + "optional": true + }, + "react-dom": { + "optional": true + } + } + }, + "node_modules/framer-motion/node_modules/@emotion/is-prop-valid": { + "version": "0.8.8", + "resolved": "https://registry.npmjs.org/@emotion/is-prop-valid/-/is-prop-valid-0.8.8.tgz", + "integrity": "sha512-u5WtneEAr5IDG2Wv65yhunPSMLIpuKsbuOktRojfrEiEvRyC85LgPMZI63cr7NUqT8ZIGdSVg8ZKGxIug4lXcA==", + "optional": true, + "dependencies": { + "@emotion/memoize": "0.7.4" + } + }, + "node_modules/framer-motion/node_modules/@emotion/memoize": { + "version": "0.7.4", + "resolved": "https://registry.npmjs.org/@emotion/memoize/-/memoize-0.7.4.tgz", + "integrity": "sha512-Ja/Vfqe3HpuzRsG1oBtWTHk2PGZ7GR+2Vz5iYGelAw8dx32K0y7PjVuxK6z1nMpZOqAFsRUPCkK1YjJ56qJlgw==", + "optional": true + }, + "node_modules/fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", + "license": "MIT" + }, + "node_modules/fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", + "dev": true + }, + "node_modules/fsevents": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", + "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, + "node_modules/fslightbox-react": { + "version": "1.7.6", + "resolved": "https://registry.npmjs.org/fslightbox-react/-/fslightbox-react-1.7.6.tgz", + "integrity": "sha512-7LN2GZRLHo2vZGKdH+BZDJUoUDkCRCLlZ5hOwtLtZplmGZQ9nqzpG54cTax7XNjbYGTWLT6BHdMiL5zOEhiRlA==", + "peerDependencies": { + "prop-types": ">=15.6.2", + "react": ">=16.8.0", + "react-dom": ">=16.8.0" + } + }, + "node_modules/function-bind": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", + "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/function.prototype.name": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.1.6.tgz", + "integrity": "sha512-Z5kx79swU5P27WEayXM1tBi5Ze/lbIyiNgU3qyXUOf9b2rgXYyF9Dy9Cx+IQv/Lc8WCG6L82zwUPpSS9hGehIg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.2.0", + "es-abstract": "^1.22.1", + "functions-have-names": "^1.2.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/functions-have-names": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz", + "integrity": "sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/gensync": { + "version": "1.0.0-beta.2", + "resolved": "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz", + "integrity": "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==", + "license": "MIT", + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/get-intrinsic": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.4.tgz", + "integrity": "sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ==", + "dev": true, + "dependencies": { + "es-errors": "^1.3.0", + "function-bind": "^1.1.2", + "has-proto": "^1.0.1", + "has-symbols": "^1.0.3", + "hasown": "^2.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/get-symbol-description": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/get-symbol-description/-/get-symbol-description-1.0.2.tgz", + "integrity": "sha512-g0QYk1dZBxGwk+Ngc+ltRH2IBp2f7zBkBMBJZCDerh6EhlhSR6+9irMCuT/09zD6qkarHUSn529sK/yL4S27mg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.5", + "es-errors": "^1.3.0", + "get-intrinsic": "^1.2.4" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/get-tsconfig": { + "version": "4.8.1", + "resolved": "https://registry.npmjs.org/get-tsconfig/-/get-tsconfig-4.8.1.tgz", + "integrity": "sha512-k9PN+cFBmaLWtVz29SkUoqU5O0slLuHJXt/2P+tMVFT+phsSGXGkp9t3rQIqdz0e+06EHNGs3oM6ZX1s2zHxRg==", + "dev": true, + "license": "MIT", + "dependencies": { + "resolve-pkg-maps": "^1.0.0" + }, + "funding": { + "url": "https://github.com/privatenumber/get-tsconfig?sponsor=1" + } + }, + "node_modules/github-from-package": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/github-from-package/-/github-from-package-0.0.0.tgz", + "integrity": "sha512-SyHy3T1v2NUXn29OsWdxmK6RwHD+vkj3v8en8AOBZ1wBQ/hCAQ5bAQTD02kW4W9tUp/3Qh6J8r9EvntiyCmOOw==", + "license": "MIT" + }, + "node_modules/glob": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", + "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", + "deprecated": "Glob versions prior to v9 are no longer supported", + "dev": true, + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.1.1", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + }, + "engines": { + "node": "*" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/glob-parent": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", + "integrity": "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==", + "dev": true, + "dependencies": { + "is-glob": "^4.0.3" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/globalize": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/globalize/-/globalize-0.1.1.tgz", + "integrity": "sha512-5e01v8eLGfuQSOvx2MsDMOWS0GFtCx1wPzQSmcHw4hkxFzrQDBO3Xwg/m8Hr/7qXMrHeOIE29qWVzyv06u1TZA==" + }, + "node_modules/globals": { + "version": "11.12.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz", + "integrity": "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==", + "engines": { + "node": ">=4" + } + }, + "node_modules/globalthis": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/globalthis/-/globalthis-1.0.4.tgz", + "integrity": "sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "define-properties": "^1.2.1", + "gopd": "^1.0.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/globby": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz", + "integrity": "sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==", + "dev": true, + "dependencies": { + "array-union": "^2.1.0", + "dir-glob": "^3.0.1", + "fast-glob": "^3.2.9", + "ignore": "^5.2.0", + "merge2": "^1.4.1", + "slash": "^3.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/gopd": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", + "integrity": "sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.1.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/graceful-fs": { + "version": "4.2.11", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz", + "integrity": "sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==", + "dev": true, + "license": "ISC" + }, + "node_modules/grapheme-splitter": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/grapheme-splitter/-/grapheme-splitter-1.0.4.tgz", + "integrity": "sha512-bzh50DW9kTPM00T8y4o8vQg89Di9oLJVLW/KaOGIXJWP/iqCN6WKYkbNOF04vFLJhwcpYUh9ydh/+5vpOqV4YQ==", + "dev": true + }, + "node_modules/graphemer": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/graphemer/-/graphemer-1.4.0.tgz", + "integrity": "sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==", + "dev": true + }, + "node_modules/gray-matter": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/gray-matter/-/gray-matter-4.0.3.tgz", + "integrity": "sha512-5v6yZd4JK3eMI3FqqCouswVqwugaA9r4dNZB1wwcmrD02QkV5H0y7XBQW8QwQqEaZY1pM9aqORSORhJRdNK44Q==", + "license": "MIT", + "dependencies": { + "js-yaml": "^3.13.1", + "kind-of": "^6.0.2", + "section-matter": "^1.0.0", + "strip-bom-string": "^1.0.0" + }, + "engines": { + "node": ">=6.0" + } + }, + "node_modules/gray-matter/node_modules/argparse": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", + "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", + "license": "MIT", + "dependencies": { + "sprintf-js": "~1.0.2" + } + }, + "node_modules/gray-matter/node_modules/js-yaml": { + "version": "3.14.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.14.1.tgz", + "integrity": "sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==", + "license": "MIT", + "dependencies": { + "argparse": "^1.0.7", + "esprima": "^4.0.0" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, + "node_modules/has-bigints": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.0.2.tgz", + "integrity": "sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-property-descriptors": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", + "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", + "dev": true, + "dependencies": { + "es-define-property": "^1.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-proto": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.3.tgz", + "integrity": "sha512-SJ1amZAJUiZS+PhsVLf5tGydlaVB8EdFpaSO4gmiUKUOxk8qzn5AIy4ZeJUmh22znIdk/uMAUT2pl3FxzVUH+Q==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-symbols": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", + "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-tostringtag": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz", + "integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==", + "dev": true, + "dependencies": { + "has-symbols": "^1.0.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/hasown": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", + "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", + "dependencies": { + "function-bind": "^1.1.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/hast-util-parse-selector": { + "version": "2.2.5", + "resolved": "https://registry.npmjs.org/hast-util-parse-selector/-/hast-util-parse-selector-2.2.5.tgz", + "integrity": "sha512-7j6mrk/qqkSehsM92wQjdIgWM2/BW61u/53G6xmC8i1OmEdKLHbk419QKQUjz6LglWsfqoiHmyMRkP1BGjecNQ==", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hast-util-sanitize": { + "version": "5.0.2", + "resolved": "https://registry.npmjs.org/hast-util-sanitize/-/hast-util-sanitize-5.0.2.tgz", + "integrity": "sha512-3yTWghByc50aGS7JlGhk61SPenfE/p1oaFeNwkOOyrscaOkMGrcW9+Cy/QAIOBpZxP1yqDIzFMR0+Np0i0+usg==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "@ungap/structured-clone": "^1.0.0", + "unist-util-position": "^5.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hast-util-sanitize/node_modules/@types/hast": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", + "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", + "license": "MIT", + "dependencies": { + "@types/unist": "*" + } + }, + "node_modules/hast-util-to-html": { + "version": "9.0.3", + "resolved": "https://registry.npmjs.org/hast-util-to-html/-/hast-util-to-html-9.0.3.tgz", + "integrity": "sha512-M17uBDzMJ9RPCqLMO92gNNUDuBSq10a25SDBI08iCCxmorf4Yy6sYHK57n9WAbRAAaU+DuR4W6GN9K4DFZesYg==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "@types/unist": "^3.0.0", + "ccount": "^2.0.0", + "comma-separated-tokens": "^2.0.0", + "hast-util-whitespace": "^3.0.0", + "html-void-elements": "^3.0.0", + "mdast-util-to-hast": "^13.0.0", + "property-information": "^6.0.0", + "space-separated-tokens": "^2.0.0", + "stringify-entities": "^4.0.0", + "zwitch": "^2.0.4" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hast-util-to-html/node_modules/@types/hast": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", + "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", + "license": "MIT", + "dependencies": { + "@types/unist": "*" + } + }, + "node_modules/hast-util-to-html/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/hast-util-to-html/node_modules/comma-separated-tokens": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-2.0.3.tgz", + "integrity": "sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/hast-util-to-html/node_modules/property-information": { + "version": "6.5.0", + "resolved": "https://registry.npmjs.org/property-information/-/property-information-6.5.0.tgz", + "integrity": "sha512-PgTgs/BlvHxOu8QuEN7wi5A0OmXaBcHpmCSTehcs6Uuu9IkDIEo13Hy7n898RHfrQ49vKCoGeWZSaAK01nwVig==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/hast-util-to-html/node_modules/space-separated-tokens": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/space-separated-tokens/-/space-separated-tokens-2.0.2.tgz", + "integrity": "sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/hast-util-whitespace": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/hast-util-whitespace/-/hast-util-whitespace-3.0.0.tgz", + "integrity": "sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hast-util-whitespace/node_modules/@types/hast": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", + "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", + "license": "MIT", + "dependencies": { + "@types/unist": "*" + } + }, + "node_modules/hastscript": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/hastscript/-/hastscript-6.0.0.tgz", + "integrity": "sha512-nDM6bvd7lIqDUiYEiu5Sl/+6ReP0BMk/2f4U/Rooccxkj0P5nm+acM5PrGJ/t5I8qPGiqZSE6hVAwZEdZIvP4w==", + "dependencies": { + "@types/hast": "^2.0.0", + "comma-separated-tokens": "^1.0.0", + "hast-util-parse-selector": "^2.0.0", + "property-information": "^5.0.0", + "space-separated-tokens": "^1.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/highlight.js": { + "version": "10.7.3", + "resolved": "https://registry.npmjs.org/highlight.js/-/highlight.js-10.7.3.tgz", + "integrity": "sha512-tzcUFauisWKNHaRkN4Wjl/ZA07gENAjFl3J/c480dprkGTg5EQstgaNFqBfUqCq54kZRIEcreTsAgF/m2quD7A==", + "engines": { + "node": "*" + } + }, + "node_modules/hoist-non-react-statics": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/hoist-non-react-statics/-/hoist-non-react-statics-3.3.2.tgz", + "integrity": "sha512-/gGivxi8JPKWNm/W0jSmzcMPpfpPLc3dY/6GxhX2hQ9iGj3aDfklV4ET7NjKpSinLpJ5vafa9iiGIEZg10SfBw==", + "dependencies": { + "react-is": "^16.7.0" + } + }, + "node_modules/hoist-non-react-statics/node_modules/react-is": { + "version": "16.13.1", + "resolved": "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz", + "integrity": "sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==" + }, + "node_modules/html-parse-stringify": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/html-parse-stringify/-/html-parse-stringify-3.0.1.tgz", + "integrity": "sha512-KknJ50kTInJ7qIScF3jeaFRpMpE8/lfiTdzf/twXyPBLAGrLRTmkz3AdTnKeh40X8k9L2fdYwEp/42WGXIRGcg==", + "dependencies": { + "void-elements": "3.1.0" + } + }, + "node_modules/html-tokenize": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/html-tokenize/-/html-tokenize-2.0.1.tgz", + "integrity": "sha512-QY6S+hZ0f5m1WT8WffYN+Hg+xm/w5I8XeUcAq/ZYP5wVC8xbKi4Whhru3FtrAebD5EhBW8rmFzkDI6eCAuFe2w==", + "license": "MIT", + "dependencies": { + "buffer-from": "~0.1.1", + "inherits": "~2.0.1", + "minimist": "~1.2.5", + "readable-stream": "~1.0.27-1", + "through2": "~0.4.1" + }, + "bin": { + "html-tokenize": "bin/cmd.js" + } + }, + "node_modules/html-void-elements": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/html-void-elements/-/html-void-elements-3.0.0.tgz", + "integrity": "sha512-bEqo66MRXsUGxWHV5IP0PUiAWwoEjba4VCzg0LjFJBpchPaTfyfCKTG6bc5F8ucKec3q5y6qOdGyYTSBEvhCrg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/i18next": { + "version": "23.16.8", + "resolved": "https://registry.npmjs.org/i18next/-/i18next-23.16.8.tgz", + "integrity": "sha512-06r/TitrM88Mg5FdUXAKL96dJMzgqLE5dv3ryBAra4KCwD9mJ4ndOTS95ZuymIGoE+2hzfdaMak2X11/es7ZWg==", + "funding": [ + { + "type": "individual", + "url": "https://locize.com" + }, + { + "type": "individual", + "url": "https://locize.com/i18next.html" + }, + { + "type": "individual", + "url": "https://www.i18next.com/how-to/faq#i18next-is-awesome.-how-can-i-support-the-project" + } + ], + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.23.2" + } + }, + "node_modules/ieee754": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", + "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "BSD-3-Clause" + }, + "node_modules/ignore": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz", + "integrity": "sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==", + "dev": true, + "engines": { + "node": ">= 4" + } + }, + "node_modules/immer": { + "version": "10.1.1", + "resolved": "https://registry.npmjs.org/immer/-/immer-10.1.1.tgz", + "integrity": "sha512-s2MPrmjovJcoMaHtx6K11Ra7oD05NT97w1IC5zpMkT6Atjr7H8LjaDd81iIxUYpMKSRRNMJE703M1Fhr/TctHw==", + "license": "MIT", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/immer" + } + }, + "node_modules/import-fresh": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz", + "integrity": "sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==", + "dependencies": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==", + "dev": true, + "engines": { + "node": ">=0.8.19" + } + }, + "node_modules/inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", + "deprecated": "This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful.", + "dev": true, + "dependencies": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "node_modules/inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" + }, + "node_modules/ini": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz", + "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==", + "license": "ISC" + }, + "node_modules/internal-slot": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.0.7.tgz", + "integrity": "sha512-NGnrKwXzSms2qUUih/ILZ5JBqNTSa1+ZmP6flaIp6KmSElgE9qdndzS3cqjrDovwFdmwsGsLdeFgB6suw+1e9g==", + "dev": true, + "license": "MIT", + "dependencies": { + "es-errors": "^1.3.0", + "hasown": "^2.0.0", + "side-channel": "^1.0.4" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/internmap": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/internmap/-/internmap-2.0.3.tgz", + "integrity": "sha512-5Hh7Y1wQbvY5ooGgPbDaL5iYLAPzMTUrjMulskHLH6wnv/A+1q5rgEaiuqEjB+oxGXIVZs1FF+R/KPN3ZSQYYg==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/invariant": { + "version": "2.2.4", + "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.4.tgz", + "integrity": "sha512-phJfQVBuaJM5raOpJjSfkiD6BpbCE4Ns//LaXl6wGYtUBY83nWS6Rf9tXm2e8VaK60JEjYldbPif/A2B1C2gNA==", + "dependencies": { + "loose-envify": "^1.0.0" + } + }, + "node_modules/is-alphabetical": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-1.0.4.tgz", + "integrity": "sha512-DwzsA04LQ10FHTZuL0/grVDk4rFoVH1pjAToYwBrHSxcrBIGQuXrQMtD5U1b0U2XVgKZCTLLP8u2Qxqhy3l2Vg==", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/is-alphanumerical": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-1.0.4.tgz", + "integrity": "sha512-UzoZUr+XfVz3t3v4KyGEniVL9BDRoQtY7tOyrRybkVNjDFWyo1yhXNGrrBTQxp3ib9BLAWs7k2YKBQsFRkZG9A==", + "dependencies": { + "is-alphabetical": "^1.0.0", + "is-decimal": "^1.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/is-array-buffer": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.4.tgz", + "integrity": "sha512-wcjaerHw0ydZwfhiKbXJWLDY8A7yV7KhjQOpb83hGgGfId/aQa4TOvwyzn2PuswW2gPCYEL/nEAiSVpdOj1lXw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.2.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-arrayish": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", + "integrity": "sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==" + }, + "node_modules/is-async-function": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-async-function/-/is-async-function-2.0.0.tgz", + "integrity": "sha512-Y1JXKrfykRJGdlDwdKlLpLyMIiWqWvuSd17TvZk68PLAOGOoF4Xyav1z0Xhoi+gCYjZVeC5SI+hYFOfvXmGRCA==", + "dev": true, + "license": "MIT", + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-bigint": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.0.4.tgz", + "integrity": "sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg==", + "dev": true, + "license": "MIT", + "dependencies": { + "has-bigints": "^1.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-boolean-object": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.1.2.tgz", + "integrity": "sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-buffer": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-2.0.5.tgz", + "integrity": "sha512-i2R6zNFDwgEHJyQUtJEk0XFi1i0dPFn/oqjK3/vPCcDeJvW5NQ83V8QbicfF1SupOaB0h8ntgBC2YiE7dfyctQ==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "engines": { + "node": ">=4" + } + }, + "node_modules/is-bun-module": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/is-bun-module/-/is-bun-module-1.2.1.tgz", + "integrity": "sha512-AmidtEM6D6NmUiLOvvU7+IePxjEjOzra2h0pSrsfSAcXwl/83zLLXDByafUJy9k/rKK0pvXMLdwKwGHlX2Ke6Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "semver": "^7.6.3" + } + }, + "node_modules/is-bun-module/node_modules/semver": { + "version": "7.6.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.3.tgz", + "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", + "dev": true, + "license": "ISC", + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/is-callable": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz", + "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-core-module": { + "version": "2.15.1", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.15.1.tgz", + "integrity": "sha512-z0vtXSwucUJtANQWldhbtbt7BnL0vxiFjIdDLAatwhDYty2bad6s+rijD6Ri4YuYJubLzIJLUidCh09e1djEVQ==", + "dependencies": { + "hasown": "^2.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-data-view": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-data-view/-/is-data-view-1.0.1.tgz", + "integrity": "sha512-AHkaJrsUVW6wq6JS8y3JnM/GJF/9cf+k20+iDzlSaJrinEo5+7vRiteOSwBhHRiAyQATN1AmY4hwzxJKPmYf+w==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-typed-array": "^1.1.13" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-date-object": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.5.tgz", + "integrity": "sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ==", + "dev": true, + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-decimal": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-decimal/-/is-decimal-1.0.4.tgz", + "integrity": "sha512-RGdriMmQQvZ2aqaQq3awNA6dCGtKpiDFcOzrTWrDAT2MiWrKQVPmxLGHl7Y2nNu6led0kEyoX0enY0qXYsv9zw==", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/is-extendable": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", + "integrity": "sha512-5BMULNob1vgFX6EjQw5izWDxrecWK9AM72rugNr0TFldMOi0fj6Jk+zeKIt0xGj4cEfQIJth4w3OKWOJ4f+AFw==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-finalizationregistry": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-finalizationregistry/-/is-finalizationregistry-1.1.0.tgz", + "integrity": "sha512-qfMdqbAQEwBw78ZyReKnlA8ezmPdb9BemzIIip/JkjaZUhitfXDkkr+3QTboW0JrSXT1QWyYShpvnNHGZ4c4yA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-generator-function": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/is-generator-function/-/is-generator-function-1.0.10.tgz", + "integrity": "sha512-jsEjy9l3yiXEQ+PsXdmBwEPcOxaXWLspKdplFUVI9vq1iZgIekeC0L167qeu86czQaxed3q/Uzuw0swL0irL8A==", + "dev": true, + "license": "MIT", + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-glob": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", + "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", + "dev": true, + "dependencies": { + "is-extglob": "^2.1.1" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-hexadecimal": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-1.0.4.tgz", + "integrity": "sha512-gyPJuv83bHMpocVYoqof5VDiZveEoGoFL8m3BXNb2VW8Xs+rz9kqO8LOQ5DH6EsuvilT1ApazU0pyl+ytbPtlw==", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/is-map": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/is-map/-/is-map-2.0.3.tgz", + "integrity": "sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-negative-zero": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.3.tgz", + "integrity": "sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-number": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", + "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", + "dev": true, + "engines": { + "node": ">=0.12.0" + } + }, + "node_modules/is-number-object": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.0.7.tgz", + "integrity": "sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-path-inside": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-3.0.3.tgz", + "integrity": "sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/is-plain-obj": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-4.1.0.tgz", + "integrity": "sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==", + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/is-regex": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.1.4.tgz", + "integrity": "sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-set": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/is-set/-/is-set-2.0.3.tgz", + "integrity": "sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-shared-array-buffer": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.3.tgz", + "integrity": "sha512-nA2hv5XIhLR3uVzDDfCIknerhx8XUKnstuOERPNNIinXG7v9u+ohXF67vxm4TPTEPU6lm61ZkwP3c9PCB97rhg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-string": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.0.7.tgz", + "integrity": "sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg==", + "dev": true, + "license": "MIT", + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-symbol": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.4.tgz", + "integrity": "sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg==", + "dev": true, + "license": "MIT", + "dependencies": { + "has-symbols": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-typed-array": { + "version": "1.1.13", + "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.13.tgz", + "integrity": "sha512-uZ25/bUAlUY5fR4OKT4rZQEBrzQWYV9ZJYGGsUmEJ6thodVJ1HX64ePQ6Z0qPWP+m+Uq6e9UugrE38jeYsDSMw==", + "dev": true, + "license": "MIT", + "dependencies": { + "which-typed-array": "^1.1.14" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-weakmap": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/is-weakmap/-/is-weakmap-2.0.2.tgz", + "integrity": "sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-weakref": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-weakref/-/is-weakref-1.0.2.tgz", + "integrity": "sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-weakset": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/is-weakset/-/is-weakset-2.0.3.tgz", + "integrity": "sha512-LvIm3/KWzS9oRFHugab7d+M/GcBXuXX5xZkzPmN+NxihdQlZUQ4dWuSV1xR/sq6upL1TJEDrfBgRepHFdBtSNQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "get-intrinsic": "^1.2.4" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/isarray": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", + "integrity": "sha512-D2S+3GLxWH+uhrNEcoh/fnmYeP8E8/zHl644d/jdA0g2uyXvy3sb0qxotE+ne0LtccHknQzWwZEzhak7oJ0COQ==", + "license": "MIT" + }, + "node_modules/isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", + "dev": true + }, + "node_modules/iterator.prototype": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/iterator.prototype/-/iterator.prototype-1.1.3.tgz", + "integrity": "sha512-FW5iMbeQ6rBGm/oKgzq2aW4KvAGpxPzYES8N4g4xNXUKpL1mclMvOe+76AcLDTvD+Ze+sOpVhgdAQEKF4L9iGQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "define-properties": "^1.2.1", + "get-intrinsic": "^1.2.1", + "has-symbols": "^1.0.3", + "reflect.getprototypeof": "^1.0.4", + "set-function-name": "^2.0.1" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/js-tokens": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==" + }, + "node_modules/js-yaml": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", + "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", + "dependencies": { + "argparse": "^2.0.1" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, + "node_modules/jsesc": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.0.2.tgz", + "integrity": "sha512-xKqzzWXDttJuOcawBt4KnKHHIf5oQ/Cxax+0PWFG+DFDgHNAdi+TXECADI+RYiFUMmx8792xsMbbgXj4CwnP4g==", + "license": "MIT", + "bin": { + "jsesc": "bin/jsesc" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/json-buffer": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz", + "integrity": "sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==", + "dev": true + }, + "node_modules/json-parse-even-better-errors": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", + "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==" + }, + "node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "node_modules/json-stable-stringify-without-jsonify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", + "integrity": "sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==", + "dev": true + }, + "node_modules/json2mq": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/json2mq/-/json2mq-0.2.0.tgz", + "integrity": "sha512-SzoRg7ux5DWTII9J2qkrZrqV1gt+rTaoufMxEzXbS26Uid0NwaJd123HcoB80TgubEppxxIGdNxCx50fEoEWQA==", + "dependencies": { + "string-convert": "^0.2.0" + } + }, + "node_modules/json5": { + "version": "2.2.3", + "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", + "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", + "license": "MIT", + "bin": { + "json5": "lib/cli.js" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/jsx-ast-utils": { + "version": "3.3.5", + "resolved": "https://registry.npmjs.org/jsx-ast-utils/-/jsx-ast-utils-3.3.5.tgz", + "integrity": "sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "array-includes": "^3.1.6", + "array.prototype.flat": "^1.3.1", + "object.assign": "^4.1.4", + "object.values": "^1.1.6" + }, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/keyv": { + "version": "4.5.4", + "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz", + "integrity": "sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==", + "dev": true, + "dependencies": { + "json-buffer": "3.0.1" + } + }, + "node_modules/kind-of": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz", + "integrity": "sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/language-subtag-registry": { + "version": "0.3.23", + "resolved": "https://registry.npmjs.org/language-subtag-registry/-/language-subtag-registry-0.3.23.tgz", + "integrity": "sha512-0K65Lea881pHotoGEa5gDlMxt3pctLi2RplBb7Ezh4rRdLEOtgi7n4EwK9lamnUCkKBqaeKRVebTq6BAxSkpXQ==", + "dev": true, + "license": "CC0-1.0" + }, + "node_modules/language-tags": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/language-tags/-/language-tags-1.0.9.tgz", + "integrity": "sha512-MbjN408fEndfiQXbFQ1vnd+1NoLDsnQW41410oQBXiyXDMYH5z505juWa4KUE1LqxRC7DgOgZDbKLxHIwm27hA==", + "dev": true, + "license": "MIT", + "dependencies": { + "language-subtag-registry": "^0.3.20" + }, + "engines": { + "node": ">=0.10" + } + }, + "node_modules/levn": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", + "integrity": "sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==", + "dev": true, + "dependencies": { + "prelude-ls": "^1.2.1", + "type-check": "~0.4.0" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/lines-and-columns": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/lines-and-columns/-/lines-and-columns-1.2.4.tgz", + "integrity": "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==" + }, + "node_modules/linkify-it": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-5.0.0.tgz", + "integrity": "sha512-5aHCbzQRADcdP+ATqnDuhhJ/MRIqDkZX5pyjFHRRysS8vZ5AbqGEoFIb6pYHPZ+L/OC2Lc+xT8uHVVR5CAK/wQ==", + "license": "MIT", + "dependencies": { + "uc.micro": "^2.0.0" + } + }, + "node_modules/locate-path": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz", + "integrity": "sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==", + "dev": true, + "dependencies": { + "p-locate": "^5.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/lodash": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" + }, + "node_modules/lodash-es": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash-es/-/lodash-es-4.17.21.tgz", + "integrity": "sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw==" + }, + "node_modules/lodash.debounce": { + "version": "4.0.8", + "resolved": "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz", + "integrity": "sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==" + }, + "node_modules/lodash.merge": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", + "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", + "dev": true + }, + "node_modules/longest-streak": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/longest-streak/-/longest-streak-3.1.0.tgz", + "integrity": "sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/loose-envify": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", + "integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==", + "dependencies": { + "js-tokens": "^3.0.0 || ^4.0.0" + }, + "bin": { + "loose-envify": "cli.js" + } + }, + "node_modules/lower-case": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/lower-case/-/lower-case-2.0.2.tgz", + "integrity": "sha512-7fm3l3NAF9WfN6W3JOmf5drwpVqX78JtoGJ3A6W0a6ZnldM41w2fV5D490psKFTpMds8TJse/eHLFFsNHHjHgg==", + "license": "MIT", + "dependencies": { + "tslib": "^2.0.3" + } + }, + "node_modules/lowlight": { + "version": "1.20.0", + "resolved": "https://registry.npmjs.org/lowlight/-/lowlight-1.20.0.tgz", + "integrity": "sha512-8Ktj+prEb1RoCPkEOrPMYUN/nCggB7qAWe3a7OpMjWQkh3l2RD5wKRQ+o8Q8YuI9RG/xs95waaI/E6ym/7NsTw==", + "dependencies": { + "fault": "^1.0.0", + "highlight.js": "~10.7.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/lru-cache": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", + "integrity": "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==", + "license": "ISC", + "dependencies": { + "yallist": "^3.0.2" + } + }, + "node_modules/luxon": { + "version": "3.5.0", + "resolved": "https://registry.npmjs.org/luxon/-/luxon-3.5.0.tgz", + "integrity": "sha512-rh+Zjr6DNfUYR3bPwJEnuwDdqMbxZW7LOQfUN4B54+Cl+0o5zaU9RJ6bcidfDtC1cWCZXQ+nvX8bf6bAji37QQ==", + "engines": { + "node": ">=12" + } + }, + "node_modules/markdown-it": { + "version": "14.1.0", + "resolved": "https://registry.npmjs.org/markdown-it/-/markdown-it-14.1.0.tgz", + "integrity": "sha512-a54IwgWPaeBCAAsv13YgmALOF1elABB08FxO9i+r4VFk5Vl4pKokRPeX8u5TCgSsPi6ec1otfLjdOpVcgbpshg==", + "license": "MIT", + "dependencies": { + "argparse": "^2.0.1", + "entities": "^4.4.0", + "linkify-it": "^5.0.0", + "mdurl": "^2.0.0", + "punycode.js": "^2.3.1", + "uc.micro": "^2.1.0" + }, + "bin": { + "markdown-it": "bin/markdown-it.mjs" + } + }, + "node_modules/mdast-util-from-markdown": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-2.0.2.tgz", + "integrity": "sha512-uZhTV/8NBuw0WHkPTrCqDOl0zVe1BIng5ZtHoDk49ME1qqcjYmmLmOf0gELgcRMxN4w2iuIeVso5/6QymSrgmA==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "@types/unist": "^3.0.0", + "decode-named-character-reference": "^1.0.0", + "devlop": "^1.0.0", + "mdast-util-to-string": "^4.0.0", + "micromark": "^4.0.0", + "micromark-util-decode-numeric-character-reference": "^2.0.0", + "micromark-util-decode-string": "^2.0.0", + "micromark-util-normalize-identifier": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0", + "unist-util-stringify-position": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-from-markdown/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/mdast-util-phrasing": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-phrasing/-/mdast-util-phrasing-4.1.0.tgz", + "integrity": "sha512-TqICwyvJJpBwvGAMZjj4J2n0X8QWp21b9l0o7eXyVJ25YNWYbJDVIyD1bZXE6WtV6RmKJVYmQAKWa0zWOABz2w==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "unist-util-is": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-to-hast": { + "version": "13.2.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-hast/-/mdast-util-to-hast-13.2.0.tgz", + "integrity": "sha512-QGYKEuUsYT9ykKBCMOEDLsU5JRObWQusAolFMeko/tYPufNkRffBAQjIE+99jbA87xv6FgmjLtwjh9wBWajwAA==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "@types/mdast": "^4.0.0", + "@ungap/structured-clone": "^1.0.0", + "devlop": "^1.0.0", + "micromark-util-sanitize-uri": "^2.0.0", + "trim-lines": "^3.0.0", + "unist-util-position": "^5.0.0", + "unist-util-visit": "^5.0.0", + "vfile": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-to-hast/node_modules/@types/hast": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", + "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", + "license": "MIT", + "dependencies": { + "@types/unist": "*" + } + }, + "node_modules/mdast-util-to-markdown": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/mdast-util-to-markdown/-/mdast-util-to-markdown-2.1.2.tgz", + "integrity": "sha512-xj68wMTvGXVOKonmog6LwyJKrYXZPvlwabaryTjLh9LuvovB/KAH+kvi8Gjj+7rJjsFi23nkUxRQv1KqSroMqA==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "@types/unist": "^3.0.0", + "longest-streak": "^3.0.0", + "mdast-util-phrasing": "^4.0.0", + "mdast-util-to-string": "^4.0.0", + "micromark-util-classify-character": "^2.0.0", + "micromark-util-decode-string": "^2.0.0", + "unist-util-visit": "^5.0.0", + "zwitch": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-to-markdown/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/mdast-util-to-string": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-4.0.0.tgz", + "integrity": "sha512-0H44vDimn51F0YwvxSJSm0eCDOJTRlmN0R1yBh4HLj9wiV1Dn0QoXGbvFAWj2hSItVTlCmBF1hqKlIyUBVFLPg==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdn-data": { + "version": "2.0.30", + "resolved": "https://registry.npmjs.org/mdn-data/-/mdn-data-2.0.30.tgz", + "integrity": "sha512-GaqWWShW4kv/G9IEucWScBx9G1/vsFZZJUO+tD26M8J8z3Kw5RDQjaoZe03YAClgeS/SWPOcb4nkFBTEi5DUEA==", + "license": "CC0-1.0" + }, + "node_modules/mdurl": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdurl/-/mdurl-2.0.0.tgz", + "integrity": "sha512-Lf+9+2r+Tdp5wXDXC4PcIBjTDtq4UKjCPMQhKIuzpJNW0b96kVqSwW0bT7FhRSfmAiFYgP+SCRvdrDozfh0U5w==", + "license": "MIT" + }, + "node_modules/merge2": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", + "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", + "dev": true, + "engines": { + "node": ">= 8" + } + }, + "node_modules/micromark": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-4.0.1.tgz", + "integrity": "sha512-eBPdkcoCNvYcxQOAKAlceo5SNdzZWfF+FcSupREAzdAh9rRmE239CEQAiTwIgblwnoM8zzj35sZ5ZwvSEOF6Kw==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "@types/debug": "^4.0.0", + "debug": "^4.0.0", + "decode-named-character-reference": "^1.0.0", + "devlop": "^1.0.0", + "micromark-core-commonmark": "^2.0.0", + "micromark-factory-space": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-chunked": "^2.0.0", + "micromark-util-combine-extensions": "^2.0.0", + "micromark-util-decode-numeric-character-reference": "^2.0.0", + "micromark-util-encode": "^2.0.0", + "micromark-util-normalize-identifier": "^2.0.0", + "micromark-util-resolve-all": "^2.0.0", + "micromark-util-sanitize-uri": "^2.0.0", + "micromark-util-subtokenize": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-core-commonmark": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/micromark-core-commonmark/-/micromark-core-commonmark-2.0.2.tgz", + "integrity": "sha512-FKjQKbxd1cibWMM1P9N+H8TwlgGgSkWZMmfuVucLCHaYqeSvJ0hFeHsIa65pA2nYbes0f8LDHPMrd9X7Ujxg9w==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "decode-named-character-reference": "^1.0.0", + "devlop": "^1.0.0", + "micromark-factory-destination": "^2.0.0", + "micromark-factory-label": "^2.0.0", + "micromark-factory-space": "^2.0.0", + "micromark-factory-title": "^2.0.0", + "micromark-factory-whitespace": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-chunked": "^2.0.0", + "micromark-util-classify-character": "^2.0.0", + "micromark-util-html-tag-name": "^2.0.0", + "micromark-util-normalize-identifier": "^2.0.0", + "micromark-util-resolve-all": "^2.0.0", + "micromark-util-subtokenize": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-factory-destination": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-factory-destination/-/micromark-factory-destination-2.0.1.tgz", + "integrity": "sha512-Xe6rDdJlkmbFRExpTOmRj9N3MaWmbAgdpSrBQvCFqhezUn4AHqJHbaEnfbVYYiexVSs//tqOdY/DxhjdCiJnIA==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-factory-label": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-factory-label/-/micromark-factory-label-2.0.1.tgz", + "integrity": "sha512-VFMekyQExqIW7xIChcXn4ok29YE3rnuyveW3wZQWWqF4Nv9Wk5rgJ99KzPvHjkmPXF93FXIbBp6YdW3t71/7Vg==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "devlop": "^1.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-factory-space": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.1.tgz", + "integrity": "sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-character": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-factory-title": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-factory-title/-/micromark-factory-title-2.0.1.tgz", + "integrity": "sha512-5bZ+3CjhAd9eChYTHsjy6TGxpOFSKgKKJPJxr293jTbfry2KDoWkhBb6TcPVB4NmzaPhMs1Frm9AZH7OD4Cjzw==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-factory-space": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-factory-whitespace": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-factory-whitespace/-/micromark-factory-whitespace-2.0.1.tgz", + "integrity": "sha512-Ob0nuZ3PKt/n0hORHyvoD9uZhr+Za8sFoP+OnMcnWK5lngSzALgQYKMr9RJVOWLqQYuyn6ulqGWSXdwf6F80lQ==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-factory-space": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-character": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", + "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-chunked": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-chunked/-/micromark-util-chunked-2.0.1.tgz", + "integrity": "sha512-QUNFEOPELfmvv+4xiNg2sRYeS/P84pTW0TCgP5zc9FpXetHY0ab7SxKyAQCNCc1eK0459uoLI1y5oO5Vc1dbhA==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-classify-character": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-classify-character/-/micromark-util-classify-character-2.0.1.tgz", + "integrity": "sha512-K0kHzM6afW/MbeWYWLjoHQv1sgg2Q9EccHEDzSkxiP/EaagNzCm7T/WMKZ3rjMbvIpvBiZgwR3dKMygtA4mG1Q==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-combine-extensions": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-combine-extensions/-/micromark-util-combine-extensions-2.0.1.tgz", + "integrity": "sha512-OnAnH8Ujmy59JcyZw8JSbK9cGpdVY44NKgSM7E9Eh7DiLS2E9RNQf0dONaGDzEG9yjEl5hcqeIsj4hfRkLH/Bg==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-chunked": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-decode-numeric-character-reference": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-2.0.2.tgz", + "integrity": "sha512-ccUbYk6CwVdkmCQMyr64dXz42EfHGkPQlBj5p7YVGzq8I7CtjXZJrubAYezf7Rp+bjPseiROqe7G6foFd+lEuw==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-decode-string": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-decode-string/-/micromark-util-decode-string-2.0.1.tgz", + "integrity": "sha512-nDV/77Fj6eH1ynwscYTOsbK7rR//Uj0bZXBwJZRfaLEJ1iGBR6kIfNmlNqaqJf649EP0F3NWNdeJi03elllNUQ==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "decode-named-character-reference": "^1.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-decode-numeric-character-reference": "^2.0.0", + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-encode": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-2.0.1.tgz", + "integrity": "sha512-c3cVx2y4KqUnwopcO9b/SCdo2O67LwJJ/UyqGfbigahfegL9myoEFoDYZgkT7f36T0bLrM9hZTAaAyH+PCAXjw==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT" + }, + "node_modules/micromark-util-html-tag-name": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-html-tag-name/-/micromark-util-html-tag-name-2.0.1.tgz", + "integrity": "sha512-2cNEiYDhCWKI+Gs9T0Tiysk136SnR13hhO8yW6BGNyhOC4qYFnwF1nKfD3HFAIXA5c45RrIG1ub11GiXeYd1xA==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT" + }, + "node_modules/micromark-util-normalize-identifier": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-2.0.1.tgz", + "integrity": "sha512-sxPqmo70LyARJs0w2UclACPUUEqltCkJ6PhKdMIDuJ3gSf/Q+/GIe3WKl0Ijb/GyH9lOpUkRAO2wp0GVkLvS9Q==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-resolve-all": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-resolve-all/-/micromark-util-resolve-all-2.0.1.tgz", + "integrity": "sha512-VdQyxFWFT2/FGJgwQnJYbe1jjQoNTS4RjglmSjTUlpUMa95Htx9NHeYW4rGDJzbjvCsl9eLjMQwGeElsqmzcHg==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-sanitize-uri": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-2.0.1.tgz", + "integrity": "sha512-9N9IomZ/YuGGZZmQec1MbgxtlgougxTodVwDzzEouPKo3qFWvymFHWcnDi2vzV1ff6kas9ucW+o3yzJK9YB1AQ==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-character": "^2.0.0", + "micromark-util-encode": "^2.0.0", + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-subtokenize": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/micromark-util-subtokenize/-/micromark-util-subtokenize-2.0.3.tgz", + "integrity": "sha512-VXJJuNxYWSoYL6AJ6OQECCFGhIU2GGHMw8tahogePBrjkG8aCCas3ibkp7RnVOSTClg2is05/R7maAhF1XyQMg==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "devlop": "^1.0.0", + "micromark-util-chunked": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-symbol": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", + "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT" + }, + "node_modules/micromark-util-types": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-2.0.1.tgz", + "integrity": "sha512-534m2WhVTddrcKVepwmVEVnUAmtrx9bfIjNoQHRqfnvdaHQiFytEhJoTgpWJvDEXCO5gLTQh3wYC1PgOJA4NSQ==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT" + }, + "node_modules/micromatch": { + "version": "4.0.8", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.8.tgz", + "integrity": "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==", + "dev": true, + "dependencies": { + "braces": "^3.0.3", + "picomatch": "^2.3.1" + }, + "engines": { + "node": ">=8.6" + } + }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mimic-response": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-3.1.0.tgz", + "integrity": "sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ==", + "license": "MIT", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/minimatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", + "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", + "dev": true, + "dependencies": { + "brace-expansion": "^1.1.7" + }, + "engines": { + "node": "*" + } + }, + "node_modules/minimist": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.8.tgz", + "integrity": "sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==", + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/mkdirp-classic": { + "version": "0.5.3", + "resolved": "https://registry.npmjs.org/mkdirp-classic/-/mkdirp-classic-0.5.3.tgz", + "integrity": "sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A==", + "license": "MIT" + }, + "node_modules/moment": { + "version": "2.29.4", + "resolved": "https://registry.npmjs.org/moment/-/moment-2.29.4.tgz", + "integrity": "sha512-5LC9SOxjSc2HF6vO2CyuTDNivEdoz2IvyJJGj6X8DJ0eFyfszE0QiEd+iXmBvUP3WHxSjFH/vIsA0EN00cgr8w==", + "engines": { + "node": "*" + } + }, + "node_modules/moment-timezone": { + "version": "0.5.45", + "resolved": "https://registry.npmjs.org/moment-timezone/-/moment-timezone-0.5.45.tgz", + "integrity": "sha512-HIWmqA86KcmCAhnMAN0wuDOARV/525R2+lOLotuGFzn4HO+FH+/645z2wx0Dt3iDv6/p61SIvKnDstISainhLQ==", + "dependencies": { + "moment": "^2.29.4" + }, + "engines": { + "node": "*" + } + }, + "node_modules/ms": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==" + }, + "node_modules/mui-tiptap": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/mui-tiptap/-/mui-tiptap-1.15.0.tgz", + "integrity": "sha512-bNFpS9aViQ0/e5epk83+OT7anKeWojNqIY0b6F0EzSLUtpplPjb667JIvQ0ObZKjQ/tc/3YQkEqvp4RLhX+hyA==", + "license": "MIT", + "dependencies": { + "encodeurl": "^1.0.2", + "lodash": "^4.17.21", + "react-colorful": "^5.6.1", + "tss-react": "^4.8.3", + "type-fest": "^3.12.0" + }, + "engines": { + "pnpm": ">=9" + }, + "peerDependencies": { + "@emotion/react": "^11.4.1", + "@mui/icons-material": "^5.0.0 || ^6.0.0", + "@mui/material": "^5.0.1 || ^6.0.0", + "@tiptap/core": "^2.0.0-beta.210", + "@tiptap/extension-heading": "^2.0.0-beta.210", + "@tiptap/extension-image": "^2.0.0-beta.210", + "@tiptap/extension-table": "^2.0.0-beta.210", + "@tiptap/pm": "^2.0.0-beta.210", + "@tiptap/react": "^2.0.0-beta.210", + "react": "^16.8.0 || ^17.0.2 || ^18.0.0", + "react-dom": "^16.8.0 || ^17.0.2 || ^18.0.0" + } + }, + "node_modules/mui-tiptap/node_modules/type-fest": { + "version": "3.13.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-3.13.1.tgz", + "integrity": "sha512-tLq3bSNx+xSpwvAJnzrK0Ep5CLNWjvFTOp71URMaAEWBfRb9nnJiBoUe0tF8bI4ZFO3omgBR6NvnbzVUT3Ly4g==", + "license": "(MIT OR CC0-1.0)", + "engines": { + "node": ">=14.16" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/multipipe": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/multipipe/-/multipipe-1.0.2.tgz", + "integrity": "sha512-6uiC9OvY71vzSGX8lZvSqscE7ft9nPupJ8fMjrCNRAUy2LREUW42UL+V/NTrogr6rFgRydUrCX4ZitfpSNkSCQ==", + "license": "MIT", + "dependencies": { + "duplexer2": "^0.1.2", + "object-assign": "^4.1.0" + } + }, + "node_modules/nanoclone": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/nanoclone/-/nanoclone-0.2.1.tgz", + "integrity": "sha512-wynEP02LmIbLpcYw8uBKpcfF6dmg2vcpKqxeH5UcoKEYdExslsdUA4ugFauuaeYdTB76ez6gJW8XAZ6CgkXYxA==" + }, + "node_modules/nanoid": { + "version": "3.3.8", + "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.8.tgz", + "integrity": "sha512-WNLf5Sd8oZxOm+TzppcYk8gVOgP+l58xNy58D0nbUnOxOWRWvlcCV4kUF7ltmI6PsrLl/BgKEyS4mqsGChFN0w==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/ai" + } + ], + "license": "MIT", + "bin": { + "nanoid": "bin/nanoid.cjs" + }, + "engines": { + "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" + } + }, + "node_modules/napi-build-utils": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/napi-build-utils/-/napi-build-utils-1.0.2.tgz", + "integrity": "sha512-ONmRUqK7zj7DWX0D9ADe03wbwOBZxNAfF20PlGfCWQcD3+/MakShIHrMqx9YwPTfxDdF1zLeL+RGZiR9kGMLdg==", + "license": "MIT" + }, + "node_modules/natural-compare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", + "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", + "dev": true + }, + "node_modules/natural-compare-lite": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare-lite/-/natural-compare-lite-1.4.0.tgz", + "integrity": "sha512-Tj+HTDSJJKaZnfiuw+iaF9skdPpTo2GtEly5JHnWV/hfv2Qj/9RKsGISQtLh2ox3l5EAGw487hnBee0sIJ6v2g==", + "dev": true + }, + "node_modules/no-case": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/no-case/-/no-case-3.0.4.tgz", + "integrity": "sha512-fgAN3jGAh+RoxUGZHTSOLJIqUc2wmoBwGR4tbpNAKmmovFoWq0OdRkb0VkldReO2a2iBT/OEulG9XSUc10r3zg==", + "license": "MIT", + "dependencies": { + "lower-case": "^2.0.2", + "tslib": "^2.0.3" + } + }, + "node_modules/node-abi": { + "version": "3.71.0", + "resolved": "https://registry.npmjs.org/node-abi/-/node-abi-3.71.0.tgz", + "integrity": "sha512-SZ40vRiy/+wRTf21hxkkEjPJZpARzUMVcJoQse2EF8qkUWbbO2z7vd5oA/H6bVH6SZQ5STGcu0KRDS7biNRfxw==", + "license": "MIT", + "dependencies": { + "semver": "^7.3.5" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/node-abi/node_modules/semver": { + "version": "7.6.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.3.tgz", + "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", + "license": "ISC", + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/node-addon-api": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-6.1.0.tgz", + "integrity": "sha512-+eawOlIgy680F0kBzPUNFhMZGtJ1YmqM6l4+Crf4IkImjYrO/mqPwRMh352g23uIaQKFItcQ64I7KMaJxHgAVA==", + "license": "MIT" + }, + "node_modules/node-releases": { + "version": "2.0.18", + "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.18.tgz", + "integrity": "sha512-d9VeXT4SJ7ZeOqGX6R5EM022wpL+eWPooLI+5UpWn2jCT1aosUQEhQP214x33Wkwx3JQMvIm+tIoVOdodFS40g==", + "license": "MIT" + }, + "node_modules/nth-check": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/nth-check/-/nth-check-2.1.1.tgz", + "integrity": "sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w==", + "license": "BSD-2-Clause", + "dependencies": { + "boolbase": "^1.0.0" + }, + "funding": { + "url": "https://github.com/fb55/nth-check?sponsor=1" + } + }, + "node_modules/object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/object-inspect": { + "version": "1.13.3", + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.3.tgz", + "integrity": "sha512-kDCGIbxkDSXE3euJZZXzc6to7fCrKHNI/hSRQnRuQ+BWjFNzZwiFF8fj/6o2t2G9/jTj8PSIYTfCLelLZEeRpA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/object-keys": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", + "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", + "dev": true, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/object.assign": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.5.tgz", + "integrity": "sha512-byy+U7gp+FVwmyzKPYhW2h5l3crpmGsxl7X2s8y43IgxvG4g3QZ6CffDtsNQy1WsmZpQbO+ybo0AlW7TY6DcBQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.5", + "define-properties": "^1.2.1", + "has-symbols": "^1.0.3", + "object-keys": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/object.entries": { + "version": "1.1.8", + "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.1.8.tgz", + "integrity": "sha512-cmopxi8VwRIAw/fkijJohSfpef5PdN0pMQJN6VC/ZKvn0LIknWD8KtgY6KlQdEc4tIjcQ3HxSMmnvtzIscdaYQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-object-atoms": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/object.fromentries": { + "version": "2.0.8", + "resolved": "https://registry.npmjs.org/object.fromentries/-/object.fromentries-2.0.8.tgz", + "integrity": "sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.2", + "es-object-atoms": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/object.groupby": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/object.groupby/-/object.groupby-1.0.3.tgz", + "integrity": "sha512-+Lhy3TQTuzXI5hevh8sBGqbmurHbbIjAi0Z4S63nthVLmLxfbj4T54a4CfZrXIrt9iP4mVAPYMo/v99taj3wjQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/object.values": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.2.0.tgz", + "integrity": "sha512-yBYjY9QX2hnRmZHAjG/f13MzmBzxzYgQhFrke06TTyKY5zSTEqkOeukBzIdVA3j3ulu8Qa3MbVFShV7T2RmGtQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-object-atoms": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", + "dependencies": { + "wrappy": "1" + } + }, + "node_modules/optionator": { + "version": "0.9.4", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.4.tgz", + "integrity": "sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==", + "dev": true, + "dependencies": { + "deep-is": "^0.1.3", + "fast-levenshtein": "^2.0.6", + "levn": "^0.4.1", + "prelude-ls": "^1.2.1", + "type-check": "^0.4.0", + "word-wrap": "^1.2.5" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/orderedmap": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/orderedmap/-/orderedmap-2.1.1.tgz", + "integrity": "sha512-TvAWxi0nDe1j/rtMcWcIj94+Ffe6n7zhow33h40SKxmsmozs6dz/e+EajymfoFcHd7sxNn8yHM8839uixMOV6g==", + "license": "MIT" + }, + "node_modules/p-limit": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz", + "integrity": "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==", + "dev": true, + "dependencies": { + "yocto-queue": "^0.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/p-locate": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz", + "integrity": "sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==", + "dev": true, + "dependencies": { + "p-limit": "^3.0.2" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/parent-module": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", + "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", + "dependencies": { + "callsites": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/parse-entities": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/parse-entities/-/parse-entities-2.0.0.tgz", + "integrity": "sha512-kkywGpCcRYhqQIchaWqZ875wzpS/bMKhz5HnN3p7wveJTkTtyAB/AlnS0f8DFSqYW1T82t6yEAkEcB+A1I3MbQ==", + "dependencies": { + "character-entities": "^1.0.0", + "character-entities-legacy": "^1.0.0", + "character-reference-invalid": "^1.0.0", + "is-alphanumerical": "^1.0.0", + "is-decimal": "^1.0.0", + "is-hexadecimal": "^1.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/parse-json": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-5.2.0.tgz", + "integrity": "sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==", + "dependencies": { + "@babel/code-frame": "^7.0.0", + "error-ex": "^1.3.1", + "json-parse-even-better-errors": "^2.3.0", + "lines-and-columns": "^1.1.6" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/path-exists": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", + "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/path-key": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", + "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/path-parse": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", + "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==" + }, + "node_modules/path-type": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", + "integrity": "sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==", + "engines": { + "node": ">=8" + } + }, + "node_modules/picocolors": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", + "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==", + "license": "ISC" + }, + "node_modules/picomatch": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", + "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", + "dev": true, + "engines": { + "node": ">=8.6" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, + "node_modules/possible-typed-array-names": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/possible-typed-array-names/-/possible-typed-array-names-1.0.0.tgz", + "integrity": "sha512-d7Uw+eZoloe0EHDIYoe+bQ5WXnGMOpmiZFTuMWCwpjzzkL2nTjcKiAk4hh8TjnGye2TwWOk3UXucZ+3rbmBa8Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/postcss": { + "version": "8.4.49", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.49.tgz", + "integrity": "sha512-OCVPnIObs4N29kxTjzLfUryOkvZEq+pf8jTF0lg8E7uETuWHA+v7j3c/xJmiqpX450191LlmZfUKkXxkTry7nA==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/postcss/" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/postcss" + }, + { + "type": "github", + "url": "https://github.com/sponsors/ai" + } + ], + "license": "MIT", + "dependencies": { + "nanoid": "^3.3.7", + "picocolors": "^1.1.1", + "source-map-js": "^1.2.1" + }, + "engines": { + "node": "^10 || ^12 || >=14" + } + }, + "node_modules/prebuild-install": { + "version": "7.1.2", + "resolved": "https://registry.npmjs.org/prebuild-install/-/prebuild-install-7.1.2.tgz", + "integrity": "sha512-UnNke3IQb6sgarcZIDU3gbMeTp/9SSU1DAIkil7PrqG1vZlBtY5msYccSKSHDqa3hNg436IXK+SNImReuA1wEQ==", + "license": "MIT", + "dependencies": { + "detect-libc": "^2.0.0", + "expand-template": "^2.0.3", + "github-from-package": "0.0.0", + "minimist": "^1.2.3", + "mkdirp-classic": "^0.5.3", + "napi-build-utils": "^1.0.1", + "node-abi": "^3.3.0", + "pump": "^3.0.0", + "rc": "^1.2.7", + "simple-get": "^4.0.0", + "tar-fs": "^2.0.0", + "tunnel-agent": "^0.6.0" + }, + "bin": { + "prebuild-install": "bin.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/prebuild-install/node_modules/readable-stream": { + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", + "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", + "license": "MIT", + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/prebuild-install/node_modules/string_decoder": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", + "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", + "license": "MIT", + "dependencies": { + "safe-buffer": "~5.2.0" + } + }, + "node_modules/prebuild-install/node_modules/tar-fs": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.1.tgz", + "integrity": "sha512-V0r2Y9scmbDRLCNex/+hYzvp/zyYjvFbHPNgVTKfQvVrb6guiE/fxP+XblDNR011utopbkex2nM4dHNV6GDsng==", + "license": "MIT", + "dependencies": { + "chownr": "^1.1.1", + "mkdirp-classic": "^0.5.2", + "pump": "^3.0.0", + "tar-stream": "^2.1.4" + } + }, + "node_modules/prebuild-install/node_modules/tar-stream": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.2.0.tgz", + "integrity": "sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==", + "license": "MIT", + "dependencies": { + "bl": "^4.0.3", + "end-of-stream": "^1.4.1", + "fs-constants": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^3.1.1" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/prelude-ls": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", + "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", + "dev": true, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/prismjs": { + "version": "1.29.0", + "resolved": "https://registry.npmjs.org/prismjs/-/prismjs-1.29.0.tgz", + "integrity": "sha512-Kx/1w86q/epKcmte75LNrEoT+lX8pBpavuAbvJWRXar7Hz8jrtF+e3vY751p0R8H9HdArwaCTNDDzHg/ScJK1Q==", + "engines": { + "node": ">=6" + } + }, + "node_modules/process-nextick-args": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", + "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", + "license": "MIT" + }, + "node_modules/prop-types": { + "version": "15.8.1", + "resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz", + "integrity": "sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==", + "dependencies": { + "loose-envify": "^1.4.0", + "object-assign": "^4.1.1", + "react-is": "^16.13.1" + } + }, + "node_modules/prop-types/node_modules/react-is": { + "version": "16.13.1", + "resolved": "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz", + "integrity": "sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==" + }, + "node_modules/property-expr": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/property-expr/-/property-expr-2.0.6.tgz", + "integrity": "sha512-SVtmxhRE/CGkn3eZY1T6pC8Nln6Fr/lu1mKSgRud0eC73whjGfoAogbn78LkD8aFL0zz3bAFerKSnOl7NlErBA==" + }, + "node_modules/property-information": { + "version": "5.6.0", + "resolved": "https://registry.npmjs.org/property-information/-/property-information-5.6.0.tgz", + "integrity": "sha512-YUHSPk+A30YPv+0Qf8i9Mbfe/C0hdPXk1s1jPVToV8pk8BQtpw10ct89Eo7OWkutrwqvT0eicAxlOg3dOAu8JA==", + "dependencies": { + "xtend": "^4.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/prosemirror-changeset": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/prosemirror-changeset/-/prosemirror-changeset-2.2.1.tgz", + "integrity": "sha512-J7msc6wbxB4ekDFj+n9gTW/jav/p53kdlivvuppHsrZXCaQdVgRghoZbSS3kwrRyAstRVQ4/+u5k7YfLgkkQvQ==", + "license": "MIT", + "dependencies": { + "prosemirror-transform": "^1.0.0" + } + }, + "node_modules/prosemirror-collab": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/prosemirror-collab/-/prosemirror-collab-1.3.1.tgz", + "integrity": "sha512-4SnynYR9TTYaQVXd/ieUvsVV4PDMBzrq2xPUWutHivDuOshZXqQ5rGbZM84HEaXKbLdItse7weMGOUdDVcLKEQ==", + "license": "MIT", + "dependencies": { + "prosemirror-state": "^1.0.0" + } + }, + "node_modules/prosemirror-commands": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/prosemirror-commands/-/prosemirror-commands-1.6.2.tgz", + "integrity": "sha512-0nDHH++qcf/BuPLYvmqZTUUsPJUCPBUXt0J1ErTcDIS369CTp773itzLGIgIXG4LJXOlwYCr44+Mh4ii6MP1QA==", + "license": "MIT", + "dependencies": { + "prosemirror-model": "^1.0.0", + "prosemirror-state": "^1.0.0", + "prosemirror-transform": "^1.10.2" + } + }, + "node_modules/prosemirror-dropcursor": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/prosemirror-dropcursor/-/prosemirror-dropcursor-1.8.1.tgz", + "integrity": "sha512-M30WJdJZLyXHi3N8vxN6Zh5O8ZBbQCz0gURTfPmTIBNQ5pxrdU7A58QkNqfa98YEjSAL1HUyyU34f6Pm5xBSGw==", + "license": "MIT", + "dependencies": { + "prosemirror-state": "^1.0.0", + "prosemirror-transform": "^1.1.0", + "prosemirror-view": "^1.1.0" + } + }, + "node_modules/prosemirror-gapcursor": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/prosemirror-gapcursor/-/prosemirror-gapcursor-1.3.2.tgz", + "integrity": "sha512-wtjswVBd2vaQRrnYZaBCbyDqr232Ed4p2QPtRIUK5FuqHYKGWkEwl08oQM4Tw7DOR0FsasARV5uJFvMZWxdNxQ==", + "license": "MIT", + "dependencies": { + "prosemirror-keymap": "^1.0.0", + "prosemirror-model": "^1.0.0", + "prosemirror-state": "^1.0.0", + "prosemirror-view": "^1.0.0" + } + }, + "node_modules/prosemirror-history": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/prosemirror-history/-/prosemirror-history-1.4.1.tgz", + "integrity": "sha512-2JZD8z2JviJrboD9cPuX/Sv/1ChFng+xh2tChQ2X4bB2HeK+rra/bmJ3xGntCcjhOqIzSDG6Id7e8RJ9QPXLEQ==", + "license": "MIT", + "dependencies": { + "prosemirror-state": "^1.2.2", + "prosemirror-transform": "^1.0.0", + "prosemirror-view": "^1.31.0", + "rope-sequence": "^1.3.0" + } + }, + "node_modules/prosemirror-inputrules": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/prosemirror-inputrules/-/prosemirror-inputrules-1.4.0.tgz", + "integrity": "sha512-6ygpPRuTJ2lcOXs9JkefieMst63wVJBgHZGl5QOytN7oSZs3Co/BYbc3Yx9zm9H37Bxw8kVzCnDsihsVsL4yEg==", + "license": "MIT", + "dependencies": { + "prosemirror-state": "^1.0.0", + "prosemirror-transform": "^1.0.0" + } + }, + "node_modules/prosemirror-keymap": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/prosemirror-keymap/-/prosemirror-keymap-1.2.2.tgz", + "integrity": "sha512-EAlXoksqC6Vbocqc0GtzCruZEzYgrn+iiGnNjsJsH4mrnIGex4qbLdWWNza3AW5W36ZRrlBID0eM6bdKH4OStQ==", + "license": "MIT", + "dependencies": { + "prosemirror-state": "^1.0.0", + "w3c-keyname": "^2.2.0" + } + }, + "node_modules/prosemirror-markdown": { + "version": "1.13.1", + "resolved": "https://registry.npmjs.org/prosemirror-markdown/-/prosemirror-markdown-1.13.1.tgz", + "integrity": "sha512-Sl+oMfMtAjWtlcZoj/5L/Q39MpEnVZ840Xo330WJWUvgyhNmLBLN7MsHn07s53nG/KImevWHSE6fEj4q/GihHw==", + "license": "MIT", + "dependencies": { + "@types/markdown-it": "^14.0.0", + "markdown-it": "^14.0.0", + "prosemirror-model": "^1.20.0" + } + }, + "node_modules/prosemirror-menu": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/prosemirror-menu/-/prosemirror-menu-1.2.4.tgz", + "integrity": "sha512-S/bXlc0ODQup6aiBbWVsX/eM+xJgCTAfMq/nLqaO5ID/am4wS0tTCIkzwytmao7ypEtjj39i7YbJjAgO20mIqA==", + "license": "MIT", + "dependencies": { + "crelt": "^1.0.0", + "prosemirror-commands": "^1.0.0", + "prosemirror-history": "^1.0.0", + "prosemirror-state": "^1.0.0" + } + }, + "node_modules/prosemirror-model": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/prosemirror-model/-/prosemirror-model-1.23.0.tgz", + "integrity": "sha512-Q/fgsgl/dlOAW9ILu4OOhYWQbc7TQd4BwKH/RwmUjyVf8682Be4zj3rOYdLnYEcGzyg8LL9Q5IWYKD8tdToreQ==", + "license": "MIT", + "dependencies": { + "orderedmap": "^2.0.0" + } + }, + "node_modules/prosemirror-schema-basic": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/prosemirror-schema-basic/-/prosemirror-schema-basic-1.2.3.tgz", + "integrity": "sha512-h+H0OQwZVqMon1PNn0AG9cTfx513zgIG2DY00eJ00Yvgb3UD+GQ/VlWW5rcaxacpCGT1Yx8nuhwXk4+QbXUfJA==", + "license": "MIT", + "dependencies": { + "prosemirror-model": "^1.19.0" + } + }, + "node_modules/prosemirror-schema-list": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/prosemirror-schema-list/-/prosemirror-schema-list-1.4.1.tgz", + "integrity": "sha512-jbDyaP/6AFfDfu70VzySsD75Om2t3sXTOdl5+31Wlxlg62td1haUpty/ybajSfJ1pkGadlOfwQq9kgW5IMo1Rg==", + "license": "MIT", + "dependencies": { + "prosemirror-model": "^1.0.0", + "prosemirror-state": "^1.0.0", + "prosemirror-transform": "^1.7.3" + } + }, + "node_modules/prosemirror-state": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/prosemirror-state/-/prosemirror-state-1.4.3.tgz", + "integrity": "sha512-goFKORVbvPuAQaXhpbemJFRKJ2aixr+AZMGiquiqKxaucC6hlpHNZHWgz5R7dS4roHiwq9vDctE//CZ++o0W1Q==", + "license": "MIT", + "dependencies": { + "prosemirror-model": "^1.0.0", + "prosemirror-transform": "^1.0.0", + "prosemirror-view": "^1.27.0" + } + }, + "node_modules/prosemirror-tables": { + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/prosemirror-tables/-/prosemirror-tables-1.6.1.tgz", + "integrity": "sha512-p8WRJNA96jaNQjhJolmbxTzd6M4huRE5xQ8OxjvMhQUP0Nzpo4zz6TztEiwk6aoqGBhz9lxRWR1yRZLlpQN98w==", + "license": "MIT", + "dependencies": { + "prosemirror-keymap": "^1.1.2", + "prosemirror-model": "^1.8.1", + "prosemirror-state": "^1.3.1", + "prosemirror-transform": "^1.2.1", + "prosemirror-view": "^1.13.3" + } + }, + "node_modules/prosemirror-trailing-node": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/prosemirror-trailing-node/-/prosemirror-trailing-node-3.0.0.tgz", + "integrity": "sha512-xiun5/3q0w5eRnGYfNlW1uU9W6x5MoFKWwq/0TIRgt09lv7Hcser2QYV8t4muXbEr+Fwo0geYn79Xs4GKywrRQ==", + "license": "MIT", + "dependencies": { + "@remirror/core-constants": "3.0.0", + "escape-string-regexp": "^4.0.0" + }, + "peerDependencies": { + "prosemirror-model": "^1.22.1", + "prosemirror-state": "^1.4.2", + "prosemirror-view": "^1.33.8" + } + }, + "node_modules/prosemirror-transform": { + "version": "1.10.2", + "resolved": "https://registry.npmjs.org/prosemirror-transform/-/prosemirror-transform-1.10.2.tgz", + "integrity": "sha512-2iUq0wv2iRoJO/zj5mv8uDUriOHWzXRnOTVgCzSXnktS/2iQRa3UUQwVlkBlYZFtygw6Nh1+X4mGqoYBINn5KQ==", + "license": "MIT", + "dependencies": { + "prosemirror-model": "^1.21.0" + } + }, + "node_modules/prosemirror-view": { + "version": "1.37.0", + "resolved": "https://registry.npmjs.org/prosemirror-view/-/prosemirror-view-1.37.0.tgz", + "integrity": "sha512-z2nkKI1sJzyi7T47Ji/ewBPuIma1RNvQCCYVdV+MqWBV7o4Sa1n94UJCJJ1aQRF/xRkFfyqLGlGFWitIcCOtbg==", + "license": "MIT", + "dependencies": { + "prosemirror-model": "^1.20.0", + "prosemirror-state": "^1.0.0", + "prosemirror-transform": "^1.1.0" + } + }, + "node_modules/proxy-from-env": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", + "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==" + }, + "node_modules/pump": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.2.tgz", + "integrity": "sha512-tUPXtzlGM8FE3P0ZL6DVs/3P58k9nk8/jZeQCurTJylQA8qFYzHFfhBJkuqyE0FifOsQ0uKWekiZ5g8wtr28cw==", + "license": "MIT", + "dependencies": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "node_modules/punycode": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", + "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/punycode.js": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/punycode.js/-/punycode.js-2.3.1.tgz", + "integrity": "sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, + "node_modules/queue-microtask": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", + "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, + "node_modules/queue-tick": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/queue-tick/-/queue-tick-1.0.1.tgz", + "integrity": "sha512-kJt5qhMxoszgU/62PLP1CJytzd2NKetjSRnyuj31fDd3Rlcz3fzlFdFLD1SItunPwyqEOkca6GbV612BWfaBag==", + "license": "MIT" + }, + "node_modules/raf-schd": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/raf-schd/-/raf-schd-4.0.3.tgz", + "integrity": "sha512-tQkJl2GRWh83ui2DiPTJz9wEiMN20syf+5oKfB03yYP7ioZcJwsIK8FjrtLwH1m7C7e+Tt2yYBlrOpdT+dyeIQ==" + }, + "node_modules/rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "license": "(BSD-2-Clause OR MIT OR Apache-2.0)", + "dependencies": { + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + }, + "bin": { + "rc": "cli.js" + } + }, + "node_modules/rc/node_modules/strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha512-4gB8na07fecVVkOI6Rs4e7T6NOTki5EmL7TUduTs6bu3EdnSycntVJ4re8kgZA+wx9IueI2Y11bfbgwtzuE0KQ==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/react": { + "version": "19.0.0-rc-02c0e824-20241028", + "resolved": "https://registry.npmjs.org/react/-/react-19.0.0-rc-02c0e824-20241028.tgz", + "integrity": "sha512-GbZ7hpPHQMiEu53BqEaPQVM/4GG4hARo+mqEEnx4rYporDvNvUjutiAFxYFSbu6sgHwcr7LeFv8htEOwALVA2A==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/react-apexcharts": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/react-apexcharts/-/react-apexcharts-1.4.1.tgz", + "integrity": "sha512-G14nVaD64Bnbgy8tYxkjuXEUp/7h30Q0U33xc3AwtGFijJB9nHqOt1a6eG0WBn055RgRg+NwqbKGtqPxy15d0Q==", + "dependencies": { + "prop-types": "^15.8.1" + }, + "peerDependencies": { + "apexcharts": "^3.41.0", + "react": ">=0.13" + } + }, + "node_modules/react-big-calendar": { + "version": "1.11.3", + "resolved": "https://registry.npmjs.org/react-big-calendar/-/react-big-calendar-1.11.3.tgz", + "integrity": "sha512-+vc1ev7VhvOtHY9sgLCgVLmEyQyiIiv3N0if45eqHZtX55wPPRo8WpONXMBvVz3LzfLjS0NwBtYRRcLlLqHoLQ==", + "dependencies": { + "@babel/runtime": "^7.20.7", + "clsx": "^1.2.1", + "date-arithmetic": "^4.1.0", + "dayjs": "^1.11.7", + "dom-helpers": "^5.2.1", + "globalize": "^0.1.1", + "invariant": "^2.2.4", + "lodash": "^4.17.21", + "lodash-es": "^4.17.21", + "luxon": "^3.2.1", + "memoize-one": "^6.0.0", + "moment": "^2.29.4", + "moment-timezone": "^0.5.40", + "prop-types": "^15.8.1", + "react-overlays": "^5.2.1", + "uncontrollable": "^7.2.1" + }, + "peerDependencies": { + "react": "^16.14.0 || ^17 || ^18", + "react-dom": "^16.14.0 || ^17 || ^18" + } + }, + "node_modules/react-big-calendar/node_modules/clsx": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/clsx/-/clsx-1.2.1.tgz", + "integrity": "sha512-EcR6r5a8bj6pu3ycsa/E/cKVGuTgZJZdsyUYHOksG/UHIiKfjxzRxYJpyVBwYaQeOvghal9fcc4PidlgzugAQg==", + "engines": { + "node": ">=6" + } + }, + "node_modules/react-big-calendar/node_modules/memoize-one": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/memoize-one/-/memoize-one-6.0.0.tgz", + "integrity": "sha512-rkpe71W0N0c0Xz6QD0eJETuWAJGnJ9afsl1srmwPrI+yBCkge5EycXXbYRyvL29zZVUWQCY7InPRCv3GDXuZNw==" + }, + "node_modules/react-colorful": { + "version": "5.6.1", + "resolved": "https://registry.npmjs.org/react-colorful/-/react-colorful-5.6.1.tgz", + "integrity": "sha512-1exovf0uGTGyq5mXQT0zgQ80uvj2PCwvF8zY1RN9/vbJVSjSo3fsB/4L3ObbF7u70NduSiK4xu4Y6q1MHoUGEw==", + "license": "MIT", + "peerDependencies": { + "react": ">=16.8.0", + "react-dom": ">=16.8.0" + } + }, + "node_modules/react-dom": { + "version": "19.0.0-rc-02c0e824-20241028", + "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.0.0-rc-02c0e824-20241028.tgz", + "integrity": "sha512-LrZf3DfHL6Fs07wwlUCHrzFTCMM19yA99MvJpfLokN4I2nBAZvREGZjZAn8VPiSfN72+i9j1eL4wB8gC695F3Q==", + "license": "MIT", + "dependencies": { + "scheduler": "0.25.0-rc-02c0e824-20241028" + }, + "peerDependencies": { + "react": "19.0.0-rc-02c0e824-20241028" + } + }, + "node_modules/react-dropzone": { + "version": "14.2.3", + "resolved": "https://registry.npmjs.org/react-dropzone/-/react-dropzone-14.2.3.tgz", + "integrity": "sha512-O3om8I+PkFKbxCukfIR3QAGftYXDZfOE2N1mr/7qebQJHs7U+/RSL/9xomJNpRg9kM5h9soQSdf0Gc7OHF5Fug==", + "dependencies": { + "attr-accept": "^2.2.2", + "file-selector": "^0.6.0", + "prop-types": "^15.8.1" + }, + "engines": { + "node": ">= 10.13" + }, + "peerDependencies": { + "react": ">= 16.8 || 18.0.0" + } + }, + "node_modules/react-fast-compare": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/react-fast-compare/-/react-fast-compare-2.0.4.tgz", + "integrity": "sha512-suNP+J1VU1MWFKcyt7RtjiSWUjvidmQSlqu+eHslq+342xCbGTYmC0mEhPCOHxlW0CywylOC1u2DFAT+bv4dBw==" + }, + "node_modules/react-helmet": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/react-helmet/-/react-helmet-6.1.0.tgz", + "integrity": "sha512-4uMzEY9nlDlgxr61NL3XbKRy1hEkXmKNXhjbAIOVw5vcFrsdYbH2FEwcNyWvWinl103nXgzYNlns9ca+8kFiWw==", + "license": "MIT", + "dependencies": { + "object-assign": "^4.1.1", + "prop-types": "^15.7.2", + "react-fast-compare": "^3.1.1", + "react-side-effect": "^2.1.0" + }, + "peerDependencies": { + "react": ">=16.3.0" + } + }, + "node_modules/react-helmet/node_modules/react-fast-compare": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/react-fast-compare/-/react-fast-compare-3.2.2.tgz", + "integrity": "sha512-nsO+KSNgo1SbJqJEYRE9ERzo7YtYbou/OqjSQKxV7jcKox7+usiUVZOAC+XnDOABXggQTno0Y1CpVnuWEc1boQ==", + "license": "MIT" + }, + "node_modules/react-i18next": { + "version": "13.5.0", + "resolved": "https://registry.npmjs.org/react-i18next/-/react-i18next-13.5.0.tgz", + "integrity": "sha512-CFJ5NDGJ2MUyBohEHxljOq/39NQ972rh1ajnadG9BjTk+UXbHLq4z5DKEbEQBDoIhUmmbuS/fIMJKo6VOax1HA==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.22.5", + "html-parse-stringify": "^3.0.1" + }, + "peerDependencies": { + "i18next": ">= 23.2.3", + "react": ">= 16.8.0" + }, + "peerDependenciesMeta": { + "react-dom": { + "optional": true + }, + "react-native": { + "optional": true + } + } + }, + "node_modules/react-intersection-observer": { + "version": "9.13.1", + "resolved": "https://registry.npmjs.org/react-intersection-observer/-/react-intersection-observer-9.13.1.tgz", + "integrity": "sha512-tSzDaTy0qwNPLJHg8XZhlyHTgGW6drFKTtvjdL+p6um12rcnp8Z5XstE+QNBJ7c64n5o0Lj4ilUleA41bmDoMw==", + "license": "MIT", + "peerDependencies": { + "react": "^15.0.0 || ^16.0.0 || ^17.0.0 || ^18.0.0 || ^19.0.0", + "react-dom": "^15.0.0 || ^16.0.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" + }, + "peerDependenciesMeta": { + "react-dom": { + "optional": true + } + } + }, + "node_modules/react-is": { + "version": "18.3.1", + "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", + "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==" + }, + "node_modules/react-lifecycles-compat": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/react-lifecycles-compat/-/react-lifecycles-compat-3.0.4.tgz", + "integrity": "sha512-fBASbA6LnOU9dOU2eW7aQ8xmYBSXUIWr+UmF9b1efZBazGNO+rcXT/icdKnYm2pTwcRylVUYwW7H1PHfLekVzA==" + }, + "node_modules/react-overlays": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/react-overlays/-/react-overlays-5.2.1.tgz", + "integrity": "sha512-GLLSOLWr21CqtJn8geSwQfoJufdt3mfdsnIiQswouuQ2MMPns+ihZklxvsTDKD3cR2tF8ELbi5xUsvqVhR6WvA==", + "dependencies": { + "@babel/runtime": "^7.13.8", + "@popperjs/core": "^2.11.6", + "@restart/hooks": "^0.4.7", + "@types/warning": "^3.0.0", + "dom-helpers": "^5.2.0", + "prop-types": "^15.7.2", + "uncontrollable": "^7.2.1", + "warning": "^4.0.3" + }, + "peerDependencies": { + "react": ">=16.3.0", + "react-dom": ">=16.3.0" + } + }, + "node_modules/react-redux": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/react-redux/-/react-redux-9.1.2.tgz", + "integrity": "sha512-0OA4dhM1W48l3uzmv6B7TXPCGmokUU4p1M44DGN2/D9a1FjVPukVjER1PcPX97jIg6aUeLq1XJo1IpfbgULn0w==", + "license": "MIT", + "dependencies": { + "@types/use-sync-external-store": "^0.0.3", + "use-sync-external-store": "^1.0.0" + }, + "peerDependencies": { + "@types/react": "^18.2.25", + "react": "^18.0", + "redux": "^5.0.0" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + }, + "redux": { + "optional": true + } + } + }, + "node_modules/react-refresh": { + "version": "0.14.2", + "resolved": "https://registry.npmjs.org/react-refresh/-/react-refresh-0.14.2.tgz", + "integrity": "sha512-jCvmsr+1IUSMUyzOkRcvnVbX3ZYC6g9TDrDbFuFmRDq7PD4yaGbLKNQL6k2jnArV8hjYxh7hVhAZB6s9HDGpZA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/react-router": { + "version": "7.0.2", + "resolved": "https://registry.npmjs.org/react-router/-/react-router-7.0.2.tgz", + "integrity": "sha512-m5AcPfTRUcjwmhBzOJGEl6Y7+Crqyju0+TgTQxoS4SO+BkWbhOrcfZNq6wSWdl2BBbJbsAoBUb8ZacOFT+/JlA==", + "license": "MIT", + "dependencies": { + "@types/cookie": "^0.6.0", + "cookie": "^1.0.1", + "set-cookie-parser": "^2.6.0", + "turbo-stream": "2.4.0" + }, + "engines": { + "node": ">=20.0.0" + }, + "peerDependencies": { + "react": ">=18", + "react-dom": ">=18" + }, + "peerDependenciesMeta": { + "react-dom": { + "optional": true + } + } + }, + "node_modules/react-side-effect": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/react-side-effect/-/react-side-effect-2.1.2.tgz", + "integrity": "sha512-PVjOcvVOyIILrYoyGEpDN3vmYNLdy1CajSFNt4TDsVQC5KpTijDvWVoR+/7Rz2xT978D8/ZtFceXxzsPwZEDvw==", + "license": "MIT", + "peerDependencies": { + "react": "^16.3.0 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/react-slick": { + "version": "0.29.0", + "resolved": "https://registry.npmjs.org/react-slick/-/react-slick-0.29.0.tgz", + "integrity": "sha512-TGdOKE+ZkJHHeC4aaoH85m8RnFyWqdqRfAGkhd6dirmATXMZWAxOpTLmw2Ll/jPTQ3eEG7ercFr/sbzdeYCJXA==", + "dependencies": { + "classnames": "^2.2.5", + "enquire.js": "^2.1.6", + "json2mq": "^0.2.0", + "lodash.debounce": "^4.0.8", + "resize-observer-polyfill": "^1.5.0" + }, + "peerDependencies": { + "react": "^0.14.0 || ^15.0.1 || ^16.0.0 || ^17.0.0 || ^18.0.0", + "react-dom": "^0.14.0 || ^15.0.1 || ^16.0.0 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/react-spring": { + "version": "9.7.4", + "resolved": "https://registry.npmjs.org/react-spring/-/react-spring-9.7.4.tgz", + "integrity": "sha512-ypxdsOwmCfbDZGTBRyBo7eLjF55xNFN86e/QkflZ1Rfo8QMzVjCAWocrEEbsuFKkQAg2RRdhNkinWJ6BpCvJoQ==", + "license": "MIT", + "dependencies": { + "@react-spring/core": "~9.7.4", + "@react-spring/konva": "~9.7.4", + "@react-spring/native": "~9.7.4", + "@react-spring/three": "~9.7.4", + "@react-spring/web": "~9.7.4", + "@react-spring/zdog": "~9.7.4" + }, + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0", + "react-dom": "^16.8.0 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/react-syntax-highlighter": { + "version": "15.5.0", + "resolved": "https://registry.npmjs.org/react-syntax-highlighter/-/react-syntax-highlighter-15.5.0.tgz", + "integrity": "sha512-+zq2myprEnQmH5yw6Gqc8lD55QHnpKaU8TOcFeC/Lg/MQSs8UknEA0JC4nTZGFAXC2J2Hyj/ijJ7NlabyPi2gg==", + "dependencies": { + "@babel/runtime": "^7.3.1", + "highlight.js": "^10.4.1", + "lowlight": "^1.17.0", + "prismjs": "^1.27.0", + "refractor": "^3.6.0" + }, + "peerDependencies": { + "react": ">= 0.14.0" + } + }, + "node_modules/react-top-loading-bar": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/react-top-loading-bar/-/react-top-loading-bar-2.3.1.tgz", + "integrity": "sha512-rQk2Nm+TOBrM1C4E3e6KwT65iXyRSgBHjCkr2FNja1S51WaPulRA5nKj/xazuQ3x89wDDdGsrqkqy0RBIfd0xg==", + "license": "MIT", + "engines": { + "node": ">=10" + }, + "peerDependencies": { + "react": "^16 || ^17 || ^18" + } + }, + "node_modules/react-transition-group": { + "version": "4.4.5", + "resolved": "https://registry.npmjs.org/react-transition-group/-/react-transition-group-4.4.5.tgz", + "integrity": "sha512-pZcd1MCJoiKiBR2NRxeCRg13uCXbydPnmB4EOeRrY7480qNWO8IIgQG6zlDkm6uRMsURXPuKq0GWtiM59a5Q6g==", + "dependencies": { + "@babel/runtime": "^7.5.5", + "dom-helpers": "^5.0.1", + "loose-envify": "^1.4.0", + "prop-types": "^15.6.2" + }, + "peerDependencies": { + "react": ">=16.6.0", + "react-dom": ">=16.6.0" + } + }, + "node_modules/readable-stream": { + "version": "1.0.34", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", + "integrity": "sha512-ok1qVCJuRkNmvebYikljxJA/UEsKwLl2nI1OmaqAu4/UE+h0wKCHok4XkL/gvi39OacXvw59RJUOFUkDib2rHg==", + "license": "MIT", + "dependencies": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.1", + "isarray": "0.0.1", + "string_decoder": "~0.10.x" + } + }, + "node_modules/redux": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/redux/-/redux-5.0.1.tgz", + "integrity": "sha512-M9/ELqF6fy8FwmkpnF0S3YKOqMyoWJ4+CS5Efg2ct3oY9daQvd/Pc71FpGZsVsbl3Cpb+IIcjBDUnnyBdQbq4w==", + "license": "MIT" + }, + "node_modules/redux-persist": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/redux-persist/-/redux-persist-6.0.0.tgz", + "integrity": "sha512-71LLMbUq2r02ng2We9S215LtPu3fY0KgaGE0k8WRgl6RkqxtGfl7HUozz1Dftwsb0D/5mZ8dwAaPbtnzfvbEwQ==", + "license": "MIT", + "peerDependencies": { + "redux": ">4.0.0" + } + }, + "node_modules/redux-thunk": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/redux-thunk/-/redux-thunk-3.1.0.tgz", + "integrity": "sha512-NW2r5T6ksUKXCabzhL9z+h206HQw/NJkcLm1GPImRQ8IzfXwRGqjVhKJGauHirT0DAuyy6hjdnMZaRoAcy0Klw==", + "license": "MIT", + "peerDependencies": { + "redux": "^5.0.0" + } + }, + "node_modules/reflect.getprototypeof": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/reflect.getprototypeof/-/reflect.getprototypeof-1.0.7.tgz", + "integrity": "sha512-bMvFGIUKlc/eSfXNX+aZ+EL95/EgZzuwA0OBPTbZZDEJw/0AkentjMuM1oiRfwHrshqk4RzdgiTg5CcDalXN5g==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.5", + "es-errors": "^1.3.0", + "get-intrinsic": "^1.2.4", + "gopd": "^1.0.1", + "which-builtin-type": "^1.1.4" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/refractor": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/refractor/-/refractor-3.6.0.tgz", + "integrity": "sha512-MY9W41IOWxxk31o+YvFCNyNzdkc9M20NoZK5vq6jkv4I/uh2zkWcfudj0Q1fovjUQJrNewS9NMzeTtqPf+n5EA==", + "dependencies": { + "hastscript": "^6.0.0", + "parse-entities": "^2.0.0", + "prismjs": "~1.27.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/refractor/node_modules/prismjs": { + "version": "1.27.0", + "resolved": "https://registry.npmjs.org/prismjs/-/prismjs-1.27.0.tgz", + "integrity": "sha512-t13BGPUlFDR7wRB5kQDG4jjl7XeuH6jbJGt11JHPL96qwsEHNX2+68tFXqc1/k+/jALsbSWJKUOT/hcYAZ5LkA==", + "engines": { + "node": ">=6" + } + }, + "node_modules/regenerate": { + "version": "1.4.2", + "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.4.2.tgz", + "integrity": "sha512-zrceR/XhGYU/d/opr2EKO7aRHUeiBI8qjtfHqADTwZd6Szfy16la6kqD0MIUs5z5hx6AaKa+PixpPrR289+I0A==", + "license": "MIT" + }, + "node_modules/regenerate-unicode-properties": { + "version": "10.2.0", + "resolved": "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-10.2.0.tgz", + "integrity": "sha512-DqHn3DwbmmPVzeKj9woBadqmXxLvQoQIwu7nopMc72ztvxVmVk2SBhSnx67zuye5TP+lJsb/TBQsjLKhnDf3MA==", + "license": "MIT", + "dependencies": { + "regenerate": "^1.4.2" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/regenerator-runtime": { + "version": "0.14.1", + "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.1.tgz", + "integrity": "sha512-dYnhHh0nJoMfnkZs6GmmhFknAGRrLznOu5nc9ML+EJxGvrx6H7teuevqVqCuPcPK//3eDrrjQhehXVx9cnkGdw==" + }, + "node_modules/regenerator-transform": { + "version": "0.15.2", + "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.15.2.tgz", + "integrity": "sha512-hfMp2BoF0qOk3uc5V20ALGDS2ddjQaLrdl7xrGXvAIow7qeWRM2VA2HuCHkUKk9slq3VwEwLNK3DFBqDfPGYtg==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.8.4" + } + }, + "node_modules/regexp.prototype.flags": { + "version": "1.5.3", + "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.5.3.tgz", + "integrity": "sha512-vqlC04+RQoFalODCbCumG2xIOvapzVMHwsyIGM/SIE8fRhFFsXeH8/QQ+s0T0kDAhKc4k30s73/0ydkHQz6HlQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-errors": "^1.3.0", + "set-function-name": "^2.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/regexpu-core": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-6.2.0.tgz", + "integrity": "sha512-H66BPQMrv+V16t8xtmq+UC0CBpiTBA60V8ibS1QVReIp8T1z8hwFxqcGzm9K6lgsN7sB5edVH8a+ze6Fqm4weA==", + "license": "MIT", + "dependencies": { + "regenerate": "^1.4.2", + "regenerate-unicode-properties": "^10.2.0", + "regjsgen": "^0.8.0", + "regjsparser": "^0.12.0", + "unicode-match-property-ecmascript": "^2.0.0", + "unicode-match-property-value-ecmascript": "^2.1.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/regjsgen": { + "version": "0.8.0", + "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.8.0.tgz", + "integrity": "sha512-RvwtGe3d7LvWiDQXeQw8p5asZUmfU1G/l6WbUXeHta7Y2PEIvBTwH6E2EfmYUK8pxcxEdEmaomqyp0vZZ7C+3Q==", + "license": "MIT" + }, + "node_modules/regjsparser": { + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.12.0.tgz", + "integrity": "sha512-cnE+y8bz4NhMjISKbgeVJtqNbtf5QpjZP+Bslo+UqkIt9QPnX9q095eiRRASJG1/tz6dlNr6Z5NsBiWYokp6EQ==", + "license": "BSD-2-Clause", + "dependencies": { + "jsesc": "~3.0.2" + }, + "bin": { + "regjsparser": "bin/parser" + } + }, + "node_modules/remark": { + "version": "15.0.1", + "resolved": "https://registry.npmjs.org/remark/-/remark-15.0.1.tgz", + "integrity": "sha512-Eht5w30ruCXgFmxVUSlNWQ9iiimq07URKeFS3hNc8cUWy1llX4KDWfyEDZRycMc+znsN9Ux5/tJ/BFdgdOwA3A==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "remark-parse": "^11.0.0", + "remark-stringify": "^11.0.0", + "unified": "^11.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-html": { + "version": "16.0.1", + "resolved": "https://registry.npmjs.org/remark-html/-/remark-html-16.0.1.tgz", + "integrity": "sha512-B9JqA5i0qZe0Nsf49q3OXyGvyXuZFDzAP2iOFLEumymuYJITVpiH1IgsTEwTpdptDmZlMDMWeDmSawdaJIGCXQ==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "hast-util-sanitize": "^5.0.0", + "hast-util-to-html": "^9.0.0", + "mdast-util-to-hast": "^13.0.0", + "unified": "^11.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-parse": { + "version": "11.0.0", + "resolved": "https://registry.npmjs.org/remark-parse/-/remark-parse-11.0.0.tgz", + "integrity": "sha512-FCxlKLNGknS5ba/1lmpYijMUzX2esxW5xQqjWxw2eHFfS2MSdaHVINFmhjo+qN1WhZhNimq0dZATN9pH0IDrpA==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "mdast-util-from-markdown": "^2.0.0", + "micromark-util-types": "^2.0.0", + "unified": "^11.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-stringify": { + "version": "11.0.0", + "resolved": "https://registry.npmjs.org/remark-stringify/-/remark-stringify-11.0.0.tgz", + "integrity": "sha512-1OSmLd3awB/t8qdoEOMazZkNsfVTeY4fTsgzcQFdXNq8ToTN4ZGwrMnlda4K6smTFKD+GRV6O48i6Z4iKgPPpw==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "mdast-util-to-markdown": "^2.0.0", + "unified": "^11.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/reselect": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/reselect/-/reselect-5.1.1.tgz", + "integrity": "sha512-K/BG6eIky/SBpzfHZv/dd+9JBFiS4SWV7FIujVyJRux6e45+73RaUHXLmIR1f7WOMaQ0U1km6qwklRQxpJJY0w==", + "license": "MIT" + }, + "node_modules/resize-observer-polyfill": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/resize-observer-polyfill/-/resize-observer-polyfill-1.5.1.tgz", + "integrity": "sha512-LwZrotdHOo12nQuZlHEmtuXdqGoOD0OhaxopaNFxWzInpEgaLWoVuAMbTzixuosCx2nEG58ngzW3vxdWoxIgdg==" + }, + "node_modules/resolve": { + "version": "1.22.8", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.8.tgz", + "integrity": "sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==", + "dependencies": { + "is-core-module": "^2.13.0", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + }, + "bin": { + "resolve": "bin/resolve" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/resolve-from": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", + "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", + "engines": { + "node": ">=4" + } + }, + "node_modules/resolve-pkg-maps": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/resolve-pkg-maps/-/resolve-pkg-maps-1.0.0.tgz", + "integrity": "sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/privatenumber/resolve-pkg-maps?sponsor=1" + } + }, + "node_modules/reusify": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz", + "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", + "dev": true, + "engines": { + "iojs": ">=1.0.0", + "node": ">=0.10.0" + } + }, + "node_modules/rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "deprecated": "Rimraf versions prior to v4 are no longer supported", + "dev": true, + "dependencies": { + "glob": "^7.1.3" + }, + "bin": { + "rimraf": "bin.js" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/robust-predicates": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/robust-predicates/-/robust-predicates-3.0.2.tgz", + "integrity": "sha512-IXgzBWvWQwE6PrDI05OvmXUIruQTcoMDzRsOd5CDvHCVLcLHMTSYvOK5Cm46kWqlV3yAbuSpBZdJ5oP5OUoStg==", + "license": "Unlicense" + }, + "node_modules/rollup": { + "version": "4.27.4", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.27.4.tgz", + "integrity": "sha512-RLKxqHEMjh/RGLsDxAEsaLO3mWgyoU6x9w6n1ikAzet4B3gI2/3yP6PWY2p9QzRTh6MfEIXB3MwsOY0Iv3vNrw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/estree": "1.0.6" + }, + "bin": { + "rollup": "dist/bin/rollup" + }, + "engines": { + "node": ">=18.0.0", + "npm": ">=8.0.0" + }, + "optionalDependencies": { + "@rollup/rollup-android-arm-eabi": "4.27.4", + "@rollup/rollup-android-arm64": "4.27.4", + "@rollup/rollup-darwin-arm64": "4.27.4", + "@rollup/rollup-darwin-x64": "4.27.4", + "@rollup/rollup-freebsd-arm64": "4.27.4", + "@rollup/rollup-freebsd-x64": "4.27.4", + "@rollup/rollup-linux-arm-gnueabihf": "4.27.4", + "@rollup/rollup-linux-arm-musleabihf": "4.27.4", + "@rollup/rollup-linux-arm64-gnu": "4.27.4", + "@rollup/rollup-linux-arm64-musl": "4.27.4", + "@rollup/rollup-linux-powerpc64le-gnu": "4.27.4", + "@rollup/rollup-linux-riscv64-gnu": "4.27.4", + "@rollup/rollup-linux-s390x-gnu": "4.27.4", + "@rollup/rollup-linux-x64-gnu": "4.27.4", + "@rollup/rollup-linux-x64-musl": "4.27.4", + "@rollup/rollup-win32-arm64-msvc": "4.27.4", + "@rollup/rollup-win32-ia32-msvc": "4.27.4", + "@rollup/rollup-win32-x64-msvc": "4.27.4", + "fsevents": "~2.3.2" + } + }, + "node_modules/rope-sequence": { + "version": "1.3.4", + "resolved": "https://registry.npmjs.org/rope-sequence/-/rope-sequence-1.3.4.tgz", + "integrity": "sha512-UT5EDe2cu2E/6O4igUr5PSFs23nvvukicWHx6GnOPlHAiiYbzNuCRQCuiUdHJQcqKalLKlrYJnjY0ySGsXNQXQ==", + "license": "MIT" + }, + "node_modules/run-parallel": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", + "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "dependencies": { + "queue-microtask": "^1.2.2" + } + }, + "node_modules/safe-array-concat": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.1.2.tgz", + "integrity": "sha512-vj6RsCsWBCf19jIeHEfkRMw8DPiBb+DMXklQ/1SGDHOMlHdPUkZXFQ2YdplS23zESTijAcurb1aSgJA3AgMu1Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "get-intrinsic": "^1.2.4", + "has-symbols": "^1.0.3", + "isarray": "^2.0.5" + }, + "engines": { + "node": ">=0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/safe-array-concat/node_modules/isarray": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", + "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", + "dev": true, + "license": "MIT" + }, + "node_modules/safe-buffer": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT" + }, + "node_modules/safe-regex-test": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.0.3.tgz", + "integrity": "sha512-CdASjNJPvRa7roO6Ra/gLYBTzYzzPyyBXxIMdGW3USQLyjWEls2RgW5UBTXaQVp+OrpeCK3bLem8smtmheoRuw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.6", + "es-errors": "^1.3.0", + "is-regex": "^1.1.4" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/scheduler": { + "version": "0.25.0-rc-02c0e824-20241028", + "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.25.0-rc-02c0e824-20241028.tgz", + "integrity": "sha512-GysnKjmMSaWcwsKTLzeJO0IhU3EyIiC0ivJKE6yDNLqt3IMxDByx8b6lSNXRNdN+ULUY0WLLjSPaZ0LuU/GnTg==", + "license": "MIT" + }, + "node_modules/section-matter": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/section-matter/-/section-matter-1.0.0.tgz", + "integrity": "sha512-vfD3pmTzGpufjScBh50YHKzEu2lxBWhVEHsNGoEXmCmn2hKGfeNLYMzCJpe8cD7gqX7TJluOVpBkAequ6dgMmA==", + "license": "MIT", + "dependencies": { + "extend-shallow": "^2.0.1", + "kind-of": "^6.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/semver": { + "version": "6.3.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", + "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", + "bin": { + "semver": "bin/semver.js" + } + }, + "node_modules/set-cookie-parser": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/set-cookie-parser/-/set-cookie-parser-2.7.1.tgz", + "integrity": "sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==", + "license": "MIT" + }, + "node_modules/set-function-length": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", + "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", + "dev": true, + "dependencies": { + "define-data-property": "^1.1.4", + "es-errors": "^1.3.0", + "function-bind": "^1.1.2", + "get-intrinsic": "^1.2.4", + "gopd": "^1.0.1", + "has-property-descriptors": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/set-function-name": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/set-function-name/-/set-function-name-2.0.2.tgz", + "integrity": "sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==", + "dev": true, + "dependencies": { + "define-data-property": "^1.1.4", + "es-errors": "^1.3.0", + "functions-have-names": "^1.2.3", + "has-property-descriptors": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/sharp": { + "version": "0.32.6", + "resolved": "https://registry.npmjs.org/sharp/-/sharp-0.32.6.tgz", + "integrity": "sha512-KyLTWwgcR9Oe4d9HwCwNM2l7+J0dUQwn/yf7S0EnTtb0eVS4RxO0eUSvxPtzT4F3SY+C4K6fqdv/DO27sJ/v/w==", + "hasInstallScript": true, + "license": "Apache-2.0", + "dependencies": { + "color": "^4.2.3", + "detect-libc": "^2.0.2", + "node-addon-api": "^6.1.0", + "prebuild-install": "^7.1.1", + "semver": "^7.5.4", + "simple-get": "^4.0.1", + "tar-fs": "^3.0.4", + "tunnel-agent": "^0.6.0" + }, + "engines": { + "node": ">=14.15.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/sharp/node_modules/semver": { + "version": "7.6.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.3.tgz", + "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", + "license": "ISC", + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/shebang-command": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", + "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", + "dev": true, + "dependencies": { + "shebang-regex": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/shebang-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", + "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/side-channel": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.6.tgz", + "integrity": "sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "es-errors": "^1.3.0", + "get-intrinsic": "^1.2.4", + "object-inspect": "^1.13.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/simple-concat": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.1.tgz", + "integrity": "sha512-cSFtAPtRhljv69IK0hTVZQ+OfE9nePi/rtJmw5UjHeVyVroEqJXP1sFztKUy1qU+xvz3u/sfYJLa947b7nAN2Q==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT" + }, + "node_modules/simple-get": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-4.0.1.tgz", + "integrity": "sha512-brv7p5WgH0jmQJr1ZDDfKDOSeWWg+OVypG99A/5vYGPqJ6pxiaHLy8nxtFjBA7oMa01ebA9gfh1uMCFqOuXxvA==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT", + "dependencies": { + "decompress-response": "^6.0.0", + "once": "^1.3.1", + "simple-concat": "^1.0.0" + } + }, + "node_modules/simple-swizzle": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/simple-swizzle/-/simple-swizzle-0.2.2.tgz", + "integrity": "sha512-JA//kQgZtbuY83m+xT+tXJkmJncGMTFT+C+g2h2R9uxkYIrE2yy9sgmcLhCnw57/WSD+Eh3J97FPEDFnbXnDUg==", + "license": "MIT", + "dependencies": { + "is-arrayish": "^0.3.1" + } + }, + "node_modules/simple-swizzle/node_modules/is-arrayish": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.3.2.tgz", + "integrity": "sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ==", + "license": "MIT" + }, + "node_modules/simplebar": { + "version": "6.2.7", + "resolved": "https://registry.npmjs.org/simplebar/-/simplebar-6.2.7.tgz", + "integrity": "sha512-IdD6HwZLz4f83lG0yN5r/3Mts4qR+pKAc9IjVdtJ96Ow6IqSA+jG2PlniQ710XUygal/mOA774IgAvcoirUP4g==", + "license": "MIT", + "dependencies": { + "can-use-dom": "^0.1.0", + "simplebar-core": "^1.2.6" + } + }, + "node_modules/simplebar-core": { + "version": "1.2.6", + "resolved": "https://registry.npmjs.org/simplebar-core/-/simplebar-core-1.2.6.tgz", + "integrity": "sha512-H5NYU+O+uvqOH5VXw3+lgoc1vTI6jL8LOZJsw4xgRpV7uIPjRpmLPdz0TrouxwKHBhpVLzVIlyKhaRLelIThMw==", + "dependencies": { + "@types/lodash-es": "^4.17.6", + "lodash": "^4.17.21", + "lodash-es": "^4.17.21" + } + }, + "node_modules/simplebar-react": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/simplebar-react/-/simplebar-react-3.2.4.tgz", + "integrity": "sha512-ogLN79e7JUm82wJChD7NSUB+4EHCFvDkjXpiu8hT1Alk7DnCekUWds61NXcsP9jC97KOgF5To/AVjYFbX0olgg==", + "dependencies": { + "simplebar-core": "^1.2.4" + }, + "peerDependencies": { + "react": ">=16.8.0" + } + }, + "node_modules/slash": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz", + "integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/slick-carousel": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/slick-carousel/-/slick-carousel-1.8.1.tgz", + "integrity": "sha512-XB9Ftrf2EEKfzoQXt3Nitrt/IPbT+f1fgqBdoxO3W/+JYvtEOW6EgxnWfr9GH6nmULv7Y2tPmEX3koxThVmebA==", + "peerDependencies": { + "jquery": ">=1.8.0" + } + }, + "node_modules/snake-case": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/snake-case/-/snake-case-3.0.4.tgz", + "integrity": "sha512-LAOh4z89bGQvl9pFfNF8V146i7o7/CqFPbqzYgP+yYzDIDeS9HaNFtXABamRW+AQzEVODcvE79ljJ+8a9YSdMg==", + "license": "MIT", + "dependencies": { + "dot-case": "^3.0.4", + "tslib": "^2.0.3" + } + }, + "node_modules/source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha512-LbrmJOMUSdEVxIKvdcJzQC+nQhe8FUZQTXQy6+I75skNgn3OoQ0DZA8YnFa7gp8tqtL3KPf1kmo0R5DoApeSGQ==", + "license": "BSD-3-Clause", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/source-map-js": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.2.1.tgz", + "integrity": "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/space-separated-tokens": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/space-separated-tokens/-/space-separated-tokens-1.1.5.tgz", + "integrity": "sha512-q/JSVd1Lptzhf5bkYm4ob4iWPjx0KiRe3sRFBNrVqbJkFaBm5vbbowy1mymoPNLRa52+oadOhJ+K49wsSeSjTA==", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/sprintf-js": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", + "integrity": "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==", + "license": "BSD-3-Clause" + }, + "node_modules/streamx": { + "version": "2.20.2", + "resolved": "https://registry.npmjs.org/streamx/-/streamx-2.20.2.tgz", + "integrity": "sha512-aDGDLU+j9tJcUdPGOaHmVF1u/hhI+CsGkT02V3OKlHDV7IukOI+nTWAGkiZEKCO35rWN1wIr4tS7YFr1f4qSvA==", + "license": "MIT", + "dependencies": { + "fast-fifo": "^1.3.2", + "queue-tick": "^1.0.1", + "text-decoder": "^1.1.0" + }, + "optionalDependencies": { + "bare-events": "^2.2.0" + } + }, + "node_modules/string_decoder": { + "version": "0.10.31", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", + "integrity": "sha512-ev2QzSzWPYmy9GuqfIVildA4OdcGLeFZQrq5ys6RtiuF+RQQiZWr8TZNyAcuVXyQRYfEO+MsoB/1BuQVhOJuoQ==", + "license": "MIT" + }, + "node_modules/string-convert": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/string-convert/-/string-convert-0.2.1.tgz", + "integrity": "sha512-u/1tdPl4yQnPBjnVrmdLo9gtuLvELKsAoRapekWggdiQNvvvum+jYF329d84NAa660KQw7pB2n36KrIKVoXa3A==" + }, + "node_modules/string.prototype.includes": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/string.prototype.includes/-/string.prototype.includes-2.0.1.tgz", + "integrity": "sha512-o7+c9bW6zpAdJHTtujeePODAhkuicdAryFsfVKwA+wGw89wJ4GTY484WTucM9hLtDEOpOvI+aHnzqnC5lHp4Rg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.3" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/string.prototype.matchall": { + "version": "4.0.11", + "resolved": "https://registry.npmjs.org/string.prototype.matchall/-/string.prototype.matchall-4.0.11.tgz", + "integrity": "sha512-NUdh0aDavY2og7IbBPenWqR9exH+E26Sv8e0/eTe1tltDGZL+GtBkDAnnyBtmekfK6/Dq3MkcGtzXFEd1LQrtg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.2", + "es-errors": "^1.3.0", + "es-object-atoms": "^1.0.0", + "get-intrinsic": "^1.2.4", + "gopd": "^1.0.1", + "has-symbols": "^1.0.3", + "internal-slot": "^1.0.7", + "regexp.prototype.flags": "^1.5.2", + "set-function-name": "^2.0.2", + "side-channel": "^1.0.6" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/string.prototype.repeat": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/string.prototype.repeat/-/string.prototype.repeat-1.0.0.tgz", + "integrity": "sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==", + "dev": true, + "license": "MIT", + "dependencies": { + "define-properties": "^1.1.3", + "es-abstract": "^1.17.5" + } + }, + "node_modules/string.prototype.trim": { + "version": "1.2.9", + "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.2.9.tgz", + "integrity": "sha512-klHuCNxiMZ8MlsOihJhJEBJAiMVqU3Z2nEXWfWnIqjN0gEFS9J9+IxKozWWtQGcgoa1WUZzLjKPTr4ZHNFTFxw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.0", + "es-object-atoms": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/string.prototype.trimend": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.8.tgz", + "integrity": "sha512-p73uL5VCHCO2BZZ6krwwQE3kCzM7NKmis8S//xEC6fQonchbum4eP6kR4DLEjQFO3Wnj3Fuo8NM0kOSjVdHjZQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-object-atoms": "^1.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/string.prototype.trimstart": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.8.tgz", + "integrity": "sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-object-atoms": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/stringify-entities": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/stringify-entities/-/stringify-entities-4.0.4.tgz", + "integrity": "sha512-IwfBptatlO+QCJUo19AqvrPNqlVMpW9YEL2LIVY+Rpv2qsjCGxaDLNRgeGsQWJhfItebuJhsGSLjaBbNSQ+ieg==", + "license": "MIT", + "dependencies": { + "character-entities-html4": "^2.0.0", + "character-entities-legacy": "^3.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/stringify-entities/node_modules/character-entities-legacy": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz", + "integrity": "sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/strip-ansi": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", + "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", + "dev": true, + "dependencies": { + "ansi-regex": "^5.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/strip-bom": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", + "integrity": "sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=4" + } + }, + "node_modules/strip-bom-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/strip-bom-string/-/strip-bom-string-1.0.0.tgz", + "integrity": "sha512-uCC2VHvQRYu+lMh4My/sFNmF2klFymLX1wHJeXnbEJERpV/ZsVuonzerjfrGpIGF7LBVa1O7i9kjiWvJiFck8g==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/strip-json-comments": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", + "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/stylis": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/stylis/-/stylis-4.2.0.tgz", + "integrity": "sha512-Orov6g6BB1sDfYgzWfTHDOxamtX1bE/zo104Dh9e6fqJ3PooipYyfJ0pUmrZO2wAvO8YbEyeFrkV91XTsGMSrw==" + }, + "node_modules/stylis-plugin-rtl": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/stylis-plugin-rtl/-/stylis-plugin-rtl-2.1.1.tgz", + "integrity": "sha512-q6xIkri6fBufIO/sV55md2CbgS5c6gg9EhSVATtHHCdOnbN/jcI0u3lYhNVeuI65c4lQPo67g8xmq5jrREvzlg==", + "license": "MIT", + "dependencies": { + "cssjanus": "^2.0.1" + }, + "peerDependencies": { + "stylis": "4.x" + } + }, + "node_modules/supports-preserve-symlinks-flag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", + "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/svg-parser": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/svg-parser/-/svg-parser-2.0.4.tgz", + "integrity": "sha512-e4hG1hRwoOdRb37cIMSgzNsxyzKfayW6VOflrwvR+/bzrkyxY/31WkbgnQpgtrNp1SdpJvpUAGTa/ZoiPNDuRQ==", + "license": "MIT" + }, + "node_modules/svg.draggable.js": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/svg.draggable.js/-/svg.draggable.js-2.2.2.tgz", + "integrity": "sha512-JzNHBc2fLQMzYCZ90KZHN2ohXL0BQJGQimK1kGk6AvSeibuKcIdDX9Kr0dT9+UJ5O8nYA0RB839Lhvk4CY4MZw==", + "dependencies": { + "svg.js": "^2.0.1" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/svg.easing.js": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/svg.easing.js/-/svg.easing.js-2.0.0.tgz", + "integrity": "sha512-//ctPdJMGy22YoYGV+3HEfHbm6/69LJUTAqI2/5qBvaNHZ9uUFVC82B0Pl299HzgH13rKrBgi4+XyXXyVWWthA==", + "dependencies": { + "svg.js": ">=2.3.x" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/svg.filter.js": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/svg.filter.js/-/svg.filter.js-2.0.2.tgz", + "integrity": "sha512-xkGBwU+dKBzqg5PtilaTb0EYPqPfJ9Q6saVldX+5vCRy31P6TlRCP3U9NxH3HEufkKkpNgdTLBJnmhDHeTqAkw==", + "dependencies": { + "svg.js": "^2.2.5" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/svg.js": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/svg.js/-/svg.js-2.7.1.tgz", + "integrity": "sha512-ycbxpizEQktk3FYvn/8BH+6/EuWXg7ZpQREJvgacqn46gIddG24tNNe4Son6omdXCnSOaApnpZw6MPCBA1dODA==" + }, + "node_modules/svg.pathmorphing.js": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/svg.pathmorphing.js/-/svg.pathmorphing.js-0.1.3.tgz", + "integrity": "sha512-49HWI9X4XQR/JG1qXkSDV8xViuTLIWm/B/7YuQELV5KMOPtXjiwH4XPJvr/ghEDibmLQ9Oc22dpWpG0vUDDNww==", + "dependencies": { + "svg.js": "^2.4.0" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/svg.resize.js": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/svg.resize.js/-/svg.resize.js-1.4.3.tgz", + "integrity": "sha512-9k5sXJuPKp+mVzXNvxz7U0uC9oVMQrrf7cFsETznzUDDm0x8+77dtZkWdMfRlmbkEEYvUn9btKuZ3n41oNA+uw==", + "dependencies": { + "svg.js": "^2.6.5", + "svg.select.js": "^2.1.2" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/svg.resize.js/node_modules/svg.select.js": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/svg.select.js/-/svg.select.js-2.1.2.tgz", + "integrity": "sha512-tH6ABEyJsAOVAhwcCjF8mw4crjXSI1aa7j2VQR8ZuJ37H2MBUbyeqYr5nEO7sSN3cy9AR9DUwNg0t/962HlDbQ==", + "dependencies": { + "svg.js": "^2.2.5" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/svg.select.js": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/svg.select.js/-/svg.select.js-3.0.1.tgz", + "integrity": "sha512-h5IS/hKkuVCbKSieR9uQCj9w+zLHoPh+ce19bBYyqF53g6mnPB8sAtIbe1s9dh2S2fCmYX2xel1Ln3PJBbK4kw==", + "dependencies": { + "svg.js": "^2.6.5" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/svgo": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/svgo/-/svgo-3.3.2.tgz", + "integrity": "sha512-OoohrmuUlBs8B8o6MB2Aevn+pRIH9zDALSR+6hhqVfa6fRwG/Qw9VUMSMW9VNg2CFc/MTIfabtdOVl9ODIJjpw==", + "license": "MIT", + "dependencies": { + "@trysound/sax": "0.2.0", + "commander": "^7.2.0", + "css-select": "^5.1.0", + "css-tree": "^2.3.1", + "css-what": "^6.1.0", + "csso": "^5.0.5", + "picocolors": "^1.0.0" + }, + "bin": { + "svgo": "bin/svgo" + }, + "engines": { + "node": ">=14.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/svgo" + } + }, + "node_modules/tapable": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", + "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6" + } + }, + "node_modules/tar-fs": { + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-3.0.6.tgz", + "integrity": "sha512-iokBDQQkUyeXhgPYaZxmczGPhnhXZ0CmrqI+MOb/WFGS9DW5wnfrLgtjUJBvz50vQ3qfRwJ62QVoCFu8mPVu5w==", + "license": "MIT", + "dependencies": { + "pump": "^3.0.0", + "tar-stream": "^3.1.5" + }, + "optionalDependencies": { + "bare-fs": "^2.1.1", + "bare-path": "^2.1.0" + } + }, + "node_modules/tar-stream": { + "version": "3.1.7", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-3.1.7.tgz", + "integrity": "sha512-qJj60CXt7IU1Ffyc3NJMjh6EkuCFej46zUqJ4J7pqYlThyd9bO0XBTmcOIhSzZJVWfsLks0+nle/j538YAW9RQ==", + "license": "MIT", + "dependencies": { + "b4a": "^1.6.4", + "fast-fifo": "^1.2.0", + "streamx": "^2.15.0" + } + }, + "node_modules/text-decoder": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/text-decoder/-/text-decoder-1.2.1.tgz", + "integrity": "sha512-x9v3H/lTKIJKQQe7RPQkLfKAnc9lUTkWDypIQgTzPJAq+5/GCDHonmshfvlsNSj58yyshbIJJDLmU15qNERrXQ==", + "license": "Apache-2.0" + }, + "node_modules/text-table": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", + "integrity": "sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==", + "dev": true + }, + "node_modules/through": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", + "integrity": "sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg==", + "license": "MIT" + }, + "node_modules/through2": { + "version": "0.4.2", + "resolved": "https://registry.npmjs.org/through2/-/through2-0.4.2.tgz", + "integrity": "sha512-45Llu+EwHKtAZYTPPVn3XZHBgakWMN3rokhEv5hu596XP+cNgplMg+Gj+1nmAvj+L0K7+N49zBKx5rah5u0QIQ==", + "license": "MIT", + "dependencies": { + "readable-stream": "~1.0.17", + "xtend": "~2.1.1" + } + }, + "node_modules/through2/node_modules/object-keys": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-0.4.0.tgz", + "integrity": "sha512-ncrLw+X55z7bkl5PnUvHwFK9FcGuFYo9gtjws2XtSzL+aZ8tm830P60WJ0dSmFVaSalWieW5MD7kEdnXda9yJw==", + "license": "MIT" + }, + "node_modules/through2/node_modules/xtend": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-2.1.2.tgz", + "integrity": "sha512-vMNKzr2rHP9Dp/e1NQFnLQlwlhp9L/LfvnsVdHxN1f+uggyVI3i08uD14GPvCToPkdsRfyPqIyYGmIk58V98ZQ==", + "dependencies": { + "object-keys": "~0.4.0" + }, + "engines": { + "node": ">=0.4" + } + }, + "node_modules/tiny-invariant": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/tiny-invariant/-/tiny-invariant-1.3.3.tgz", + "integrity": "sha512-+FbBPE1o9QAYvviau/qC5SE3caw21q3xkvWKBtja5vgqOWIHHJ3ioaq1VPfn/Szqctz2bU/oYeKd9/z5BL+PVg==" + }, + "node_modules/tiny-warning": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/tiny-warning/-/tiny-warning-1.0.3.tgz", + "integrity": "sha512-lBN9zLN/oAf68o3zNXYrdCt1kP8WsiGW8Oo2ka41b2IM5JL/S1CTyX1rW0mb/zSuJun0ZUrDxx4sqvYS2FWzPA==" + }, + "node_modules/tippy.js": { + "version": "6.3.7", + "resolved": "https://registry.npmjs.org/tippy.js/-/tippy.js-6.3.7.tgz", + "integrity": "sha512-E1d3oP2emgJ9dRQZdf3Kkn0qJgI6ZLpyS5z6ZkY1DF3kaQaBsGZsndEpHwx+eC+tYM41HaSNvNtLx8tU57FzTQ==", + "license": "MIT", + "dependencies": { + "@popperjs/core": "^2.9.0" + } + }, + "node_modules/to-regex-range": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", + "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", + "dev": true, + "dependencies": { + "is-number": "^7.0.0" + }, + "engines": { + "node": ">=8.0" + } + }, + "node_modules/toposort": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/toposort/-/toposort-2.0.2.tgz", + "integrity": "sha512-0a5EOkAUp8D4moMi2W8ZF8jcga7BgZd91O/yabJCFY8az+XSzeGyTKs0Aoo897iV1Nj6guFq8orWDS96z91oGg==" + }, + "node_modules/trim-lines": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/trim-lines/-/trim-lines-3.0.1.tgz", + "integrity": "sha512-kRj8B+YHZCc9kQYdWfJB2/oUl9rA99qbowYYBtr4ui4mZyAQ2JpvVBd/6U2YloATfqBhBTSMhTpgBHtU0Mf3Rg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/trough": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/trough/-/trough-2.2.0.tgz", + "integrity": "sha512-tmMpK00BjZiUyVyvrBK7knerNgmgvcV/KLVyuma/SC+TQN167GrMRciANTz09+k3zW8L8t60jWO1GpfkZdjTaw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/ts-api-utils": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-1.3.0.tgz", + "integrity": "sha512-UQMIo7pb8WRomKR1/+MFVLTroIvDVtMX3K6OUir8ynLyzB8Jeriont2bTAtmNPa1ekAgN7YPDyf6V+ygrdU+eQ==", + "dev": true, + "engines": { + "node": ">=16" + }, + "peerDependencies": { + "typescript": ">=4.2.0" + } + }, + "node_modules/tsconfig-paths": { + "version": "3.15.0", + "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.15.0.tgz", + "integrity": "sha512-2Ac2RgzDe/cn48GvOe3M+o82pEFewD3UPbyoUHHdKasHwJKjds4fLXWf/Ux5kATBKN20oaFGu+jbElp1pos0mg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/json5": "^0.0.29", + "json5": "^1.0.2", + "minimist": "^1.2.6", + "strip-bom": "^3.0.0" + } + }, + "node_modules/tsconfig-paths/node_modules/json5": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.2.tgz", + "integrity": "sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==", + "dev": true, + "license": "MIT", + "dependencies": { + "minimist": "^1.2.0" + }, + "bin": { + "json5": "lib/cli.js" + } + }, + "node_modules/tslib": { + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.7.0.tgz", + "integrity": "sha512-gLXCKdN1/j47AiHiOkJN69hJmcbGTHI0ImLmbYLHykhgeN0jVGola9yVjFgzCUklsZQMW55o+dW7IXv3RCXDzA==" + }, + "node_modules/tss-react": { + "version": "4.9.13", + "resolved": "https://registry.npmjs.org/tss-react/-/tss-react-4.9.13.tgz", + "integrity": "sha512-Gu19qqPH8/SAyKVIgDE5qHygirEDnNIQcXhiEc+l4Q9T7C1sfvUnbVWs+yBpmN26/wyk4FTOupjYS2wq4vH0yA==", + "license": "MIT", + "dependencies": { + "@emotion/cache": "*", + "@emotion/serialize": "*", + "@emotion/utils": "*" + }, + "peerDependencies": { + "@emotion/react": "^11.4.1", + "@emotion/server": "^11.4.0", + "@mui/material": "^5.0.0 || ^6.0.0", + "react": "^16.8.0 || ^17.0.2 || ^18.0.0" + }, + "peerDependenciesMeta": { + "@emotion/server": { + "optional": true + }, + "@mui/material": { + "optional": true + } + } + }, + "node_modules/tunnel-agent": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", + "integrity": "sha512-McnNiV1l8RYeY8tBgEpuodCC1mLUdbSN+CYBL7kJsJNInOP8UjDDEwdk6Mw60vdLLrr5NHKZhMAOSrR2NZuQ+w==", + "license": "Apache-2.0", + "dependencies": { + "safe-buffer": "^5.0.1" + }, + "engines": { + "node": "*" + } + }, + "node_modules/turbo-stream": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/turbo-stream/-/turbo-stream-2.4.0.tgz", + "integrity": "sha512-FHncC10WpBd2eOmGwpmQsWLDoK4cqsA/UT/GqNoaKOQnT8uzhtCbg3EoUDMvqpOSAI0S26mr0rkjzbOO6S3v1g==", + "license": "ISC" + }, + "node_modules/type-check": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", + "integrity": "sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==", + "dev": true, + "dependencies": { + "prelude-ls": "^1.2.1" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/type-fest": { + "version": "0.20.2", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz", + "integrity": "sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/typed-array-buffer": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/typed-array-buffer/-/typed-array-buffer-1.0.2.tgz", + "integrity": "sha512-gEymJYKZtKXzzBzM4jqa9w6Q1Jjm7x2d+sh19AdsD4wqnMPDYyvwpsIc2Q/835kHuo3BEQ7CjelGhfTsoBb2MQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "es-errors": "^1.3.0", + "is-typed-array": "^1.1.13" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/typed-array-byte-length": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/typed-array-byte-length/-/typed-array-byte-length-1.0.1.tgz", + "integrity": "sha512-3iMJ9q0ao7WE9tWcaYKIptkNBuOIcZCCT0d4MRvuuH88fEoEH62IuQe0OtraD3ebQEoTRk8XCBoknUNc1Y67pw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "for-each": "^0.3.3", + "gopd": "^1.0.1", + "has-proto": "^1.0.3", + "is-typed-array": "^1.1.13" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/typed-array-byte-offset": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/typed-array-byte-offset/-/typed-array-byte-offset-1.0.3.tgz", + "integrity": "sha512-GsvTyUHTriq6o/bHcTd0vM7OQ9JEdlvluu9YISaA7+KzDzPaIzEeDFNkTfhdE3MYcNhNi0vq/LlegYgIs5yPAw==", + "dev": true, + "license": "MIT", + "dependencies": { + "available-typed-arrays": "^1.0.7", + "call-bind": "^1.0.7", + "for-each": "^0.3.3", + "gopd": "^1.0.1", + "has-proto": "^1.0.3", + "is-typed-array": "^1.1.13", + "reflect.getprototypeof": "^1.0.6" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/typed-array-length": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/typed-array-length/-/typed-array-length-1.0.7.tgz", + "integrity": "sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "for-each": "^0.3.3", + "gopd": "^1.0.1", + "is-typed-array": "^1.1.13", + "possible-typed-array-names": "^1.0.0", + "reflect.getprototypeof": "^1.0.6" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/typescript": { + "version": "5.7.2", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.7.2.tgz", + "integrity": "sha512-i5t66RHxDvVN40HfDd1PsEThGNnlMCMT3jMUuoh9/0TaqWevNontacunWyN02LA9/fIbEWlcHZcgTKb9QoaLfg==", + "dev": true, + "license": "Apache-2.0", + "bin": { + "tsc": "bin/tsc", + "tsserver": "bin/tsserver" + }, + "engines": { + "node": ">=14.17" + } + }, + "node_modules/uc.micro": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/uc.micro/-/uc.micro-2.1.0.tgz", + "integrity": "sha512-ARDJmphmdvUk6Glw7y9DQ2bFkKBHwQHLi2lsaH6PPmz/Ka9sFOBsBluozhDltWmnv9u/cF6Rt87znRTPV+yp/A==", + "license": "MIT" + }, + "node_modules/unbox-primitive": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.0.2.tgz", + "integrity": "sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.2", + "has-bigints": "^1.0.2", + "has-symbols": "^1.0.3", + "which-boxed-primitive": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/uncontrollable": { + "version": "7.2.1", + "resolved": "https://registry.npmjs.org/uncontrollable/-/uncontrollable-7.2.1.tgz", + "integrity": "sha512-svtcfoTADIB0nT9nltgjujTi7BzVmwjZClOmskKu/E8FW9BXzg9os8OLr4f8Dlnk0rYWJIWr4wv9eKUXiQvQwQ==", + "dependencies": { + "@babel/runtime": "^7.6.3", + "@types/react": ">=16.9.11", + "invariant": "^2.2.4", + "react-lifecycles-compat": "^3.0.4" + }, + "peerDependencies": { + "react": ">=15.0.0" + } + }, + "node_modules/undici-types": { + "version": "6.20.0", + "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.20.0.tgz", + "integrity": "sha512-Ny6QZ2Nju20vw1SRHe3d9jVu6gJ+4e3+MMpqu7pqE5HT6WsTSlce++GQmK5UXS8mzV8DSYHrQH+Xrf2jVcuKNg==", + "dev": true, + "license": "MIT" + }, + "node_modules/unicode-canonical-property-names-ecmascript": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/unicode-canonical-property-names-ecmascript/-/unicode-canonical-property-names-ecmascript-2.0.1.tgz", + "integrity": "sha512-dA8WbNeb2a6oQzAQ55YlT5vQAWGV9WXOsi3SskE3bcCdM0P4SDd+24zS/OCacdRq5BkdsRj9q3Pg6YyQoxIGqg==", + "license": "MIT", + "engines": { + "node": ">=4" + } + }, + "node_modules/unicode-match-property-ecmascript": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/unicode-match-property-ecmascript/-/unicode-match-property-ecmascript-2.0.0.tgz", + "integrity": "sha512-5kaZCrbp5mmbz5ulBkDkbY0SsPOjKqVS35VpL9ulMPfSl0J0Xsm+9Evphv9CoIZFwre7aJoa94AY6seMKGVN5Q==", + "license": "MIT", + "dependencies": { + "unicode-canonical-property-names-ecmascript": "^2.0.0", + "unicode-property-aliases-ecmascript": "^2.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/unicode-match-property-value-ecmascript": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/unicode-match-property-value-ecmascript/-/unicode-match-property-value-ecmascript-2.2.0.tgz", + "integrity": "sha512-4IehN3V/+kkr5YeSSDDQG8QLqO26XpL2XP3GQtqwlT/QYSECAwFztxVHjlbh0+gjJ3XmNLS0zDsbgs9jWKExLg==", + "license": "MIT", + "engines": { + "node": ">=4" + } + }, + "node_modules/unicode-property-aliases-ecmascript": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/unicode-property-aliases-ecmascript/-/unicode-property-aliases-ecmascript-2.1.0.tgz", + "integrity": "sha512-6t3foTQI9qne+OZoVQB/8x8rk2k1eVy1gRXhV3oFQ5T6R1dqQ1xtin3XqSlx3+ATBkliTaR/hHyJBm+LVPNM8w==", + "license": "MIT", + "engines": { + "node": ">=4" + } + }, + "node_modules/unified": { + "version": "11.0.5", + "resolved": "https://registry.npmjs.org/unified/-/unified-11.0.5.tgz", + "integrity": "sha512-xKvGhPWw3k84Qjh8bI3ZeJjqnyadK+GEFtazSfZv/rKeTkTjOJho6mFqh2SM96iIcZokxiOpg78GazTSg8+KHA==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "bail": "^2.0.0", + "devlop": "^1.0.0", + "extend": "^3.0.0", + "is-plain-obj": "^4.0.0", + "trough": "^2.0.0", + "vfile": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unified/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/unist-util-is": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-6.0.0.tgz", + "integrity": "sha512-2qCTHimwdxLfz+YzdGfkqNlH0tLi9xjTnHddPmJwtIG9MGsdbutfTc4P+haPD7l7Cjxf/WZj+we5qfVPvvxfYw==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-is/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/unist-util-position": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/unist-util-position/-/unist-util-position-5.0.0.tgz", + "integrity": "sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-position/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/unist-util-stringify-position": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-4.0.0.tgz", + "integrity": "sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-stringify-position/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/unist-util-visit": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-5.0.0.tgz", + "integrity": "sha512-MR04uvD+07cwl/yhVuVWAtw+3GOR/knlL55Nd/wAdblk27GCVt3lqpTivy/tkJcZoNPzTwS1Y+KMojlLDhoTzg==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "unist-util-is": "^6.0.0", + "unist-util-visit-parents": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-visit-parents": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-6.0.1.tgz", + "integrity": "sha512-L/PqWzfTP9lzzEa6CKs0k2nARxTdZduw3zyh8d2NVBnsyvHjSX4TWse388YrrQKbvI8w20fGjGlhgT96WwKykw==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "unist-util-is": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-visit-parents/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/unist-util-visit/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/update-browserslist-db": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.1.1.tgz", + "integrity": "sha512-R8UzCaa9Az+38REPiJ1tXlImTJXlVfgHZsglwBD/k6nj76ctsH1E3q4doGrukiLQd3sGQYu56r5+lo5r94l29A==", + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/browserslist" + }, + { + "type": "github", + "url": "https://github.com/sponsors/ai" + } + ], + "license": "MIT", + "dependencies": { + "escalade": "^3.2.0", + "picocolors": "^1.1.0" + }, + "bin": { + "update-browserslist-db": "cli.js" + }, + "peerDependencies": { + "browserslist": ">= 4.21.0" + } + }, + "node_modules/uri-js": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", + "dev": true, + "dependencies": { + "punycode": "^2.1.0" + } + }, + "node_modules/use-memo-one": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/use-memo-one/-/use-memo-one-1.1.3.tgz", + "integrity": "sha512-g66/K7ZQGYrI6dy8GLpVcMsBp4s17xNkYJVSMvTEevGy3nDxHOfE6z8BVE22+5G5x7t3+bhzrlTDB7ObrEE0cQ==", + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/use-sync-external-store": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/use-sync-external-store/-/use-sync-external-store-1.2.2.tgz", + "integrity": "sha512-PElTlVMwpblvbNqQ82d2n6RjStvdSoNe9FG28kNfz3WiXilJm4DdNkEzRhCZuIDwY8U08WVihhGR5iRqAwfDiw==", + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0" + } + }, + "node_modules/util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", + "license": "MIT" + }, + "node_modules/vfile": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/vfile/-/vfile-6.0.3.tgz", + "integrity": "sha512-KzIbH/9tXat2u30jf+smMwFCsno4wHVdNmzFyL+T/L3UGqqk6JKfVqOFOZEpZSHADH1k40ab6NUIXZq422ov3Q==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "vfile-message": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/vfile-message": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/vfile-message/-/vfile-message-4.0.2.tgz", + "integrity": "sha512-jRDZ1IMLttGj41KcZvlrYAaI3CfqpLpfpf+Mfig13viT6NKvRzWZ+lXz0Y5D60w6uJIBAOGq9mSHf0gktF0duw==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "unist-util-stringify-position": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/vfile-message/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/vfile/node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, + "node_modules/vite": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/vite/-/vite-6.0.3.tgz", + "integrity": "sha512-Cmuo5P0ENTN6HxLSo6IHsjCLn/81Vgrp81oaiFFMRa8gGDj5xEjIcEpf2ZymZtZR8oU0P2JX5WuUp/rlXcHkAw==", + "dev": true, + "license": "MIT", + "dependencies": { + "esbuild": "^0.24.0", + "postcss": "^8.4.49", + "rollup": "^4.23.0" + }, + "bin": { + "vite": "bin/vite.js" + }, + "engines": { + "node": "^18.0.0 || ^20.0.0 || >=22.0.0" + }, + "funding": { + "url": "https://github.com/vitejs/vite?sponsor=1" + }, + "optionalDependencies": { + "fsevents": "~2.3.3" + }, + "peerDependencies": { + "@types/node": "^18.0.0 || ^20.0.0 || >=22.0.0", + "jiti": ">=1.21.0", + "less": "*", + "lightningcss": "^1.21.0", + "sass": "*", + "sass-embedded": "*", + "stylus": "*", + "sugarss": "*", + "terser": "^5.16.0", + "tsx": "^4.8.1", + "yaml": "^2.4.2" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + }, + "jiti": { + "optional": true + }, + "less": { + "optional": true + }, + "lightningcss": { + "optional": true + }, + "sass": { + "optional": true + }, + "sass-embedded": { + "optional": true + }, + "stylus": { + "optional": true + }, + "sugarss": { + "optional": true + }, + "terser": { + "optional": true + }, + "tsx": { + "optional": true + }, + "yaml": { + "optional": true + } + } + }, + "node_modules/void-elements": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/void-elements/-/void-elements-3.1.0.tgz", + "integrity": "sha512-Dhxzh5HZuiHQhbvTW9AMetFfBHDMYpo23Uo9btPXgdYP+3T5S+p+jgNy7spra+veYhBP2dCSgxR/i2Y02h5/6w==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/w3c-keyname": { + "version": "2.2.8", + "resolved": "https://registry.npmjs.org/w3c-keyname/-/w3c-keyname-2.2.8.tgz", + "integrity": "sha512-dpojBhNsCNN7T82Tm7k26A6G9ML3NkhDsnw9n/eoxSRlVBB4CEtIQ/KTCLI2Fwf3ataSXRhYFkQi3SlnFwPvPQ==", + "license": "MIT" + }, + "node_modules/warning": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/warning/-/warning-4.0.3.tgz", + "integrity": "sha512-rpJyN222KWIvHJ/F53XSZv0Zl/accqHR8et1kpaMTD/fLCRxtV8iX8czMzY7sVZupTI3zcUTg8eycS2kNF9l6w==", + "dependencies": { + "loose-envify": "^1.0.0" + } + }, + "node_modules/which": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", + "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", + "dev": true, + "dependencies": { + "isexe": "^2.0.0" + }, + "bin": { + "node-which": "bin/node-which" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/which-boxed-primitive": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.0.2.tgz", + "integrity": "sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-bigint": "^1.0.1", + "is-boolean-object": "^1.1.0", + "is-number-object": "^1.0.4", + "is-string": "^1.0.5", + "is-symbol": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/which-builtin-type": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/which-builtin-type/-/which-builtin-type-1.2.0.tgz", + "integrity": "sha512-I+qLGQ/vucCby4tf5HsLmGueEla4ZhwTBSqaooS+Y0BuxN4Cp+okmGuV+8mXZ84KDI9BA+oklo+RzKg0ONdSUA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "function.prototype.name": "^1.1.6", + "has-tostringtag": "^1.0.2", + "is-async-function": "^2.0.0", + "is-date-object": "^1.0.5", + "is-finalizationregistry": "^1.1.0", + "is-generator-function": "^1.0.10", + "is-regex": "^1.1.4", + "is-weakref": "^1.0.2", + "isarray": "^2.0.5", + "which-boxed-primitive": "^1.0.2", + "which-collection": "^1.0.2", + "which-typed-array": "^1.1.15" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/which-builtin-type/node_modules/isarray": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", + "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", + "dev": true, + "license": "MIT" + }, + "node_modules/which-collection": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/which-collection/-/which-collection-1.0.2.tgz", + "integrity": "sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-map": "^2.0.3", + "is-set": "^2.0.3", + "is-weakmap": "^2.0.2", + "is-weakset": "^2.0.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/which-typed-array": { + "version": "1.1.15", + "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.15.tgz", + "integrity": "sha512-oV0jmFtUky6CXfkqehVvBP/LSWJ2sy4vWMioiENyJLePrBO/yKyV9OyJySfAKosh+RYkIl5zJCNZ8/4JncrpdA==", + "dev": true, + "license": "MIT", + "dependencies": { + "available-typed-arrays": "^1.0.7", + "call-bind": "^1.0.7", + "for-each": "^0.3.3", + "gopd": "^1.0.1", + "has-tostringtag": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/word-wrap": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.5.tgz", + "integrity": "sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==" + }, + "node_modules/xtend": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", + "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", + "engines": { + "node": ">=0.4" + } + }, + "node_modules/yallist": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz", + "integrity": "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==", + "license": "ISC" + }, + "node_modules/yaml": { + "version": "1.10.2", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz", + "integrity": "sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==", + "license": "ISC", + "engines": { + "node": ">= 6" + } + }, + "node_modules/yocto-queue": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", + "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/yup": { + "version": "0.32.11", + "resolved": "https://registry.npmjs.org/yup/-/yup-0.32.11.tgz", + "integrity": "sha512-Z2Fe1bn+eLstG8DRR6FTavGD+MeAwyfmouhHsIUgaADz8jvFKbO/fXc2trJKZg+5EBjh4gGm3iU/t3onKlXHIg==", + "dependencies": { + "@babel/runtime": "^7.15.4", + "@types/lodash": "^4.14.175", + "lodash": "^4.17.21", + "lodash-es": "^4.17.21", + "nanoclone": "^0.2.1", + "property-expr": "^2.0.4", + "toposort": "^2.0.2" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/zwitch": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/zwitch/-/zwitch-2.0.4.tgz", + "integrity": "sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + } + } +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/package.json b/Modernize/Modernize/react-version/packages/typescript/main/package.json new file mode 100644 index 0000000..c36cc09 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/package.json @@ -0,0 +1,96 @@ +{ + "name": "main-vite-ts", + "private": true, + "version": "5.0.0", + "type": "module", + "scripts": { + "dev": "vite", + "build": "tsc && vite build", + "lint": "eslint . --ext ts,tsx --report-unused-disable-directives --max-warnings 0", + "preview": "vite preview" + }, + "dependencies": { + "@casl/ability": "^6.3.3", + "@casl/react": "^3.1.0", + "@dnd-kit/core": "^6.1.0", + "@dnd-kit/sortable": "^8.0.0", + "@emotion/cache": "^11.11.0", + "@emotion/react": "^11.13.3", + "@emotion/server": "^11.11.0", + "@emotion/styled": "^11.13.0", + "@hello-pangea/dnd": "^17.0.0", + "@mui/icons-material": "^5.14.13", + "@mui/lab": "6.0.0-beta.10", + "@mui/material": "^6.1.6", + "@mui/system": "^6.1.10", + "@mui/x-charts": "7.23.1", + "@mui/x-date-pickers": "7.18.0", + "@mui/x-tree-view": "^7.18.0", + "@reduxjs/toolkit": "2.2.3", + "@svgr/rollup": "8.1.0", + "@tabler/icons-react": "^2.39.0", + "@tanstack/react-table": "^8.20.1", + "@tiptap/core": "^2.9.1", + "@tiptap/extension-image": "^2.9.1", + "@tiptap/extension-table": "^2.9.1", + "@tiptap/react": "^2.9.1", + "@tiptap/starter-kit": "^2.9.1", + "apexcharts": "3.48.0", + "axios": "1.7.7", + "axios-mock-adapter": "2.0.0", + "chance": "^1.1.11", + "date-fns": "^2.30.0", + "dayjs": "^1.11.13", + "emoji-picker-react": "^4.12.0", + "formik": "^2.4.5", + "formik-mui": "^5.0.0-alpha.0", + "framer-motion": "^10.16.4", + "fslightbox-react": "^1.7.6", + "gray-matter": "^4.0.3", + "i18next": "^23.5.1", + "lodash": "^4.17.21", + "moment": "^2.29.4", + "mui-tiptap": "^1.13.0", + "prop-types": "^15.7.2", + "react": "19.0.0-rc-02c0e824-20241028", + "react-apexcharts": "^1.4.1", + "react-big-calendar": "1.11.3", + "react-dom": "19.0.0-rc-02c0e824-20241028", + "react-dropzone": "^14.2.3", + "react-helmet": "^6.1.0", + "react-i18next": "^13.2.2", + "react-intersection-observer": "^9.5.2", + "react-redux": "9.1.2", + "react-router": "^7.0.2", + "react-slick": "^0.29.0", + "react-spring": "^9.7.3", + "react-syntax-highlighter": "^15.5.0", + "react-top-loading-bar": "^2.3.1", + "redux": "^5.0.1", + "redux-persist": "^6.0.0", + "remark": "^15.0.1", + "remark-html": "^16.0.1", + "sharp": "^0.32.6", + "simplebar": "^6.2.7", + "simplebar-react": "^3.2.4", + "slick-carousel": "^1.8.1", + "stylis-plugin-rtl": "^2.1.1", + "yup": "^0.32.11" + }, + "devDependencies": { + "@types/chance": "^1.1.6", + "@types/fslightbox-react": "^1.7.8", + "@types/node": "22.10.1", + "@types/react": "19.0.1", + "@types/react-big-calendar": "^1.15.0", + "@types/react-dom": "19.0.1", + "@types/react-helmet": "^6.1.11", + "@types/react-slick": "^0.23.13", + "@types/react-syntax-highlighter": "^15.5.13", + "@vitejs/plugin-react": "^4.3.4", + "eslint": "latest", + "eslint-config-next": "latest", + "typescript": "5.7.2", + "vite": "6.0.3" + } +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/public/logoIcon.svg b/Modernize/Modernize/react-version/packages/typescript/main/public/logoIcon.svg new file mode 100644 index 0000000..8c5e0df --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/public/logoIcon.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/App.css b/Modernize/Modernize/react-version/packages/typescript/main/src/App.css new file mode 100644 index 0000000..fe59efc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/App.css @@ -0,0 +1,42 @@ +#root { + max-width: 1280px; + margin: 0 auto; + padding: 2rem; + text-align: center; +} + +.logo { + height: 6em; + padding: 1.5em; + will-change: filter; + transition: filter 300ms; +} +.logo:hover { + filter: drop-shadow(0 0 2em #646cffaa); +} +.logo.react:hover { + filter: drop-shadow(0 0 2em #61dafbaa); +} + +@keyframes logo-spin { + from { + transform: rotate(0deg); + } + to { + transform: rotate(360deg); + } +} + +@media (prefers-reduced-motion: no-preference) { + a:nth-of-type(2) .logo { + animation: logo-spin infinite 20s linear; + } +} + +.card { + padding: 2em; +} + +.read-the-docs { + color: #888; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/App.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/App.tsx new file mode 100644 index 0000000..8cc23aa --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/App.tsx @@ -0,0 +1,28 @@ +import { CssBaseline, ThemeProvider } from '@mui/material'; + +import { useSelector } from 'src/store/Store'; +import { ThemeSettings } from './theme/Theme'; +import RTL from './layouts/full/shared/customizer/RTL'; +import { RouterProvider } from 'react-router'; +import router from './routes/Router'; +import { AppState } from './store/Store'; + + +function App() { + + const theme = ThemeSettings(); + const customizer = useSelector((state: AppState) => state.customizer); + + + return ( + + + + + + + + ); +} + +export default App; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/LoadingBar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/LoadingBar.tsx new file mode 100644 index 0000000..522c65e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/LoadingBar.tsx @@ -0,0 +1,39 @@ +import { useState, useEffect } from 'react'; +import TopLoadingBar from 'react-top-loading-bar'; +import { useLocation } from 'react-router'; + + +function LoadingBar() { + const [progress, setProgress] = useState(0); + const location = useLocation(); // page navigation. + + const startLoading = () => { + setProgress(10); // Start loading + }; + + const finishLoading = () => { + setProgress(100); // Complete loading + setTimeout(() => setProgress(0), 10); // Reset progress after completion + }; + + // Trigger loading when route changes + useEffect(() => { + startLoading(); + setTimeout(() => { + finishLoading(); // Complete the loader after 2 seconds (or after data load) + }, 2000); // 2-second delay + }, [location]); // trigger whenever the route changes + + return ( + + ); +} + +export default LoadingBar; + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/blog/blogData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/blog/blogData.ts new file mode 100644 index 0000000..9148602 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/blog/blogData.ts @@ -0,0 +1,289 @@ +import mock from '../mock'; +import { Chance } from 'chance'; +import { random } from 'lodash'; +import { sub } from 'date-fns'; +import s1 from 'src/assets/images/blog/blog-img1.jpg'; +import s2 from 'src/assets/images/blog/blog-img2.jpg'; +import s3 from 'src/assets/images/blog/blog-img3.jpg'; +import s4 from 'src/assets/images/blog/blog-img4.jpg'; +import s5 from 'src/assets/images/blog/blog-img5.jpg'; +import s6 from 'src/assets/images/blog/blog-img6.jpg'; +import s7 from 'src/assets/images/blog/blog-img11.jpg'; +import s8 from 'src/assets/images/blog/blog-img8.jpg'; +import s9 from 'src/assets/images/blog/blog-img9.jpg'; +import s10 from 'src/assets/images/blog/blog-img10.jpg'; + +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; +import user4 from 'src/assets/images/profile/user-4.jpg'; +import user5 from 'src/assets/images/profile/user-5.jpg'; +import user6 from 'src/assets/images/profile/user-1.jpg'; +import { uniqueId } from 'lodash'; +import { BlogType, BlogPostType } from 'src/types/apps/blog'; + +const chance = new Chance(); + +const BlogComment: BlogType[] = [ + { + id: uniqueId('#comm_'), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user2, + name: chance.name(), + }, + time: chance.date(), + comment: chance.paragraph({ sentences: 2 }), + replies: [], + }, + { + id: uniqueId('#comm_'), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user3, + name: chance.name(), + }, + time: chance.date(), + comment: chance.paragraph({ sentences: 2 }), + replies: [ + { + id: uniqueId('#comm_'), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user3, + name: chance.name(), + }, + time: chance.date(), + comment: chance.paragraph({ sentences: 2 }), + }, + ], + }, + { + id: uniqueId('#comm_'), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user4, + name: chance.name(), + }, + time: chance.date(), + comment: chance.paragraph({ sentences: 2 }), + replies: [], + }, +]; + +const BlogPost: BlogPostType[] = [ + { + id: chance.integer({ min: 1, max: 2000 }), + title: 'Garmins Instinct Crossover is a rugged hybrid smartwatch', + content: chance.paragraph({ sentences: 2 }), + coverImg: s1, + createdAt: sub(new Date(), { days: 8, hours: 6, minutes: 20 }), + view: random(9999), + share: random(9999), + category: 'Gadget', + featured: false, + author: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user1, + name: chance.name(), + }, + comments: BlogComment, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + title: 'After Twitter Staff Cuts, Survivors Face ‘Radio Silence', + content: chance.paragraph({ sentences: 2 }), + coverImg: s2, + createdAt: sub(new Date(), { days: 7, hours: 3, minutes: 20 }), + view: random(9999), + share: random(9999), + category: 'Lifestyle', + featured: false, + author: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user2, + name: chance.name(), + }, + comments: BlogComment, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + title: 'Apple is apparently working on a new ‘streamlined’ accessibility for iOS', + content: chance.paragraph({ sentences: 2 }), + coverImg: s3, + createdAt: sub(new Date(), { days: 5, hours: 2, minutes: 20 }), + view: random(9999), + share: random(9999), + category: 'Design', + featured: false, + author: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user3, + name: chance.name(), + }, + comments: BlogComment, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + title: 'Why Figma is selling to Adobe for $20 billion', + content: chance.paragraph({ sentences: 2 }), + coverImg: s4, + createdAt: sub(new Date(), { days: 7, hours: 6, minutes: 20 }), + view: random(9999), + share: random(9999), + category: 'Design', + featured: false, + author: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user4, + name: chance.name(), + }, + comments: BlogComment, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + title: 'Streaming video way before it was cool, go dark tomorrow', + content: chance.paragraph({ sentences: 2 }), + coverImg: s5, + createdAt: sub(new Date(), { days: 4, hours: 6, minutes: 20 }), + view: random(9999), + share: random(9999), + category: 'Lifestyle', + featured: false, + author: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user5, + name: chance.name(), + }, + comments: BlogComment, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + title: 'As yen tumbles, gadget-loving Japan goes for secondhand iPhones ', + content: chance.paragraph({ sentences: 2 }), + coverImg: s6, + createdAt: sub(new Date(), { days: 2, hours: 6, minutes: 20 }), + view: random(9999), + share: random(9999), + category: 'Gadget', + featured: false, + author: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user6, + name: chance.name(), + }, + comments: BlogComment, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + title: 'Intel loses bid to revive antitrust case against patent foe Fortress', + content: chance.paragraph({ sentences: 2 }), + coverImg: s7, + createdAt: sub(new Date(), { days: 3, hours: 6, minutes: 20 }), + view: random(9999), + share: random(9999), + category: 'Social', + featured: false, + author: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user2, + name: chance.name(), + }, + comments: BlogComment, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + title: 'COVID outbreak deepens as more lockdowns loom in China', + content: chance.paragraph({ sentences: 2 }), + coverImg: s8, + createdAt: sub(new Date(), { days: 4, hours: 6, minutes: 20 }), + view: random(9999), + share: random(9999), + category: 'Health', + featured: false, + author: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user3, + name: chance.name(), + }, + comments: BlogComment, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + title: 'Early Black Friday Amazon deals: cheap TVs, headphones, laptops', + content: chance.paragraph({ sentences: 2 }), + coverImg: s9, + createdAt: sub(new Date(), { days: 5, hours: 3, minutes: 20 }), + view: random(9999), + share: random(9999), + category: 'Gadget', + featured: true, + author: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user4, + name: chance.name(), + }, + comments: BlogComment, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + title: 'Presented by Max Rushden with Barry Glendenning, Philippe Auclair', + content: chance.paragraph({ sentences: 2 }), + coverImg: s10, + createdAt: sub(new Date(), { days: 0, hours: 1, minutes: 20 }), + view: random(9999), + share: random(9999), + category: 'Health', + featured: true, + author: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user5, + name: chance.name(), + }, + comments: BlogComment, + }, +]; + +mock.onGet('/api/data/blog/BlogPosts').reply(() => { + return [200, BlogPost]; +}); + +// ---------------------------------------------------------------------- +mock.onPost('/api/data/blog/post').reply((config) => { + try { + const { title } = JSON.parse(config.data); + const paramCase = (t: string) => + t + .toLowerCase() + .replace(/ /g, '-') + .replace(/[^\w-]+/g, ''); + + const post = BlogPost.find((_post) => paramCase(_post.title) === title); + + if (!post) { + return [404, { message: 'Post not found' }]; + } + + return [200, { post }]; + } catch (error) { + console.error(error); + + return [500, { message: 'Internal server error' }]; + } +}); + +mock.onPost('/api/data/blog/post/add').reply((config) => { + try { + const { postId, comment } = JSON.parse(config.data); + const postIndex = BlogPost.findIndex((x) => x.id === postId); + const post = BlogPost[postIndex]; + const cComments = post.comments || []; + post.comments = [comment, ...cComments]; + + return [200, { posts: [...BlogPost] }]; + } catch (err) { + console.error(err); + + return [500, { message: 'Internal server error' }]; + } +}); diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/chat/Chatdata.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/chat/Chatdata.ts new file mode 100644 index 0000000..f385a9a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/chat/Chatdata.ts @@ -0,0 +1,532 @@ +import mock from '../mock'; +import bg1 from 'src/assets/images/blog/blog-img1.jpg'; +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; +import user4 from 'src/assets/images/profile/user-4.jpg'; +import user5 from 'src/assets/images/profile/user-5.jpg'; +import adobe from 'src/assets/images/chat/icon-adobe.svg'; +import chrome from 'src/assets/images/chat/icon-chrome.svg'; +import figma from 'src/assets/images/chat/icon-figma.svg'; +import java from 'src/assets/images/chat/icon-javascript.svg'; +import zip from 'src/assets/images/chat/icon-zip-folder.svg'; +import { Chance } from 'chance'; +import type { ChatsType } from 'src/types/apps/chat'; +import { sub } from 'date-fns'; +import { uniqueId } from 'lodash'; + +const chance = new Chance(); + +const ChatData: ChatsType[] = [ + { + id: 1, + name: 'James Johnson', + status: 'online', + thumb: user1, + recent: false, + excerpt: 'Theme Developer', + messages: [ + { + createdAt: sub(new Date(), { hours: 1 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [ + { icon: adobe, file: 'service-task.pdf', fileSize: '2MB' }, + { icon: chrome, file: 'homepage-design.fig', fileSize: '3MB' }, + { icon: figma, file: 'about-us.htmlf', fileSize: '1KB' }, + { icon: java, file: 'work-project.zip', fileSize: '20MB' }, + { icon: zip, file: 'custom.js', fileSize: '2MB' }, + ], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 30 }), + msg: chance.sentence({ words: 10 }), + senderId: 1, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: uniqueId(), + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + msg: bg1, + senderId: uniqueId(), + type: 'image', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 5 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [], + id: uniqueId(), + }, + ], + }, + { + id: 2, + name: 'Maria Hernandez', + status: 'away', + thumb: user2, + recent: true, + excerpt: 'Doctor', + messages: [ + { + createdAt: sub(new Date(), { hours: 1 }), + msg: chance.sentence({ words: 5 }), + senderId: uniqueId(), + type: 'text', + attachment: [ + { icon: adobe, file: 'service-task.pdf', fileSize: '2MB' }, + { icon: chrome, file: 'homepage-design.fig', fileSize: '3MB' }, + { icon: java, file: 'work-project.zip', fileSize: '20MB' }, + { icon: zip, file: 'custom.js', fileSize: '2MB' }, + ], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 30 }), + msg: chance.sentence({ words: 10 }), + senderId: uniqueId(), + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: 2, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + msg: bg1, + senderId: 2, + type: 'image', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 1 }), + msg: chance.sentence({ words: 5 }), + senderId: uniqueId(), + type: 'text', + attachment: [], + id: uniqueId(), + }, + ], + }, + { + id: 3, + name: 'David Smith', + status: 'busy', + thumb: user3, + recent: false, + excerpt: 'Hacker', + messages: [ + { + createdAt: sub(new Date(), { hours: 10 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [ + { icon: adobe, file: 'service-task.pdf', fileSize: '2MB' }, + { icon: zip, file: 'custom.js', fileSize: '2MB' }, + ], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 30 }), + msg: chance.sentence({ words: 10 }), + senderId: 1, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: 3, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: 3, + type: 'text', + attachment: [], + id: uniqueId(), + }, + + ], + }, + { + id: 4, + name: 'Maria Rodriguez', + status: 'offline', + thumb: user4, + recent: true, + excerpt: 'Please wait outside of the house', + messages: [ + { + createdAt: sub(new Date(), { hours: 1 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { hours: 10 }), + msg: chance.sentence({ words: 5 }), + senderId: 4, + type: 'text', + attachment: [ + { icon: java, file: 'work-project.zip', fileSize: '20MB' }, + { icon: zip, file: 'custom.js', fileSize: '2MB' }, + ], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { hours: 11 }), + msg: bg1, + senderId: uniqueId(), + type: 'image', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: 4, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 1 }), + msg: chance.sentence({ words: 7 }), + senderId: 3, + type: 'text', + attachment: [], + id: uniqueId(), + }, + ], + }, + { + id: 5, + name: 'Robert Smith', + status: 'online', + thumb: user5, + recent: true, + excerpt: 'Front End Developer', + messages: [ + { + createdAt: sub(new Date(), { hours: 1 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [ + { icon: adobe, file: 'service-task.pdf', fileSize: '2MB' }, + { icon: chrome, file: 'homepage-design.fig', fileSize: '3MB' }, + { icon: figma, file: 'about-us.htmlf', fileSize: '1KB' }, + { icon: java, file: 'work-project.zip', fileSize: '20MB' }, + { icon: zip, file: 'custom.js', fileSize: '2MB' }, + ], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 30 }), + msg: chance.sentence({ words: 10 }), + senderId: 1, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: uniqueId(), + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + msg: bg1, + senderId: 5, + type: 'image', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 5 }), + msg: chance.sentence({ words: 5 }), + senderId: 5, + type: 'text', + attachment: [], + id: uniqueId(), + }, + ], + }, + { + id: 6, + name: 'Joseph Sarah', + status: 'busy', + thumb: user1, + recent: false, + excerpt: 'Graphics Designer', + messages: [ + { + createdAt: sub(new Date(), { hours: 10 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [ + { icon: chrome, file: 'homepage-design.fig', fileSize: '3MB' }, + { icon: java, file: 'work-project.zip', fileSize: '20MB' }, + { icon: zip, file: 'custom.js', fileSize: '2MB' }, + ], + id: uniqueId(), + }, + { + msg: bg1, + senderId: uniqueId(), + type: 'image', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 5 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 2 }), + msg: chance.sentence({ words: 5 }), + senderId: 6, + type: 'text', + attachment: [], + id: uniqueId(), + }, + ], + }, + { + id: 7, + name: 'Thomas Smith', + status: 'away', + thumb: user2, + recent: true, + excerpt: 'Back End Developer', + messages: [ + { + createdAt: sub(new Date(), { hours: 10 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [ + { icon: adobe, file: 'service-task.pdf', fileSize: '2MB' }, + { icon: chrome, file: 'homepage-design.fig', fileSize: '3MB' }, + ], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { hours: 1 }), + msg: chance.sentence({ words: 10 }), + senderId: 1, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 15 }), + msg: chance.sentence({ words: 5 }), + senderId: 7, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 10 }), + msg: chance.sentence({ words: 5 }), + senderId: 7, + type: 'text', + attachment: [], + id: uniqueId(), + }, + ], + }, + { + id: 8, + name: 'David Elizabeth', + status: 'offline', + thumb: user3, + recent: false, + excerpt: 'Theme Developer', + messages: [ + { + createdAt: sub(new Date(), { hours: 10 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [ + { icon: adobe, file: 'service-task.pdf', fileSize: '2MB' }, + { icon: java, file: 'work-project.zip', fileSize: '20MB' }, + { icon: zip, file: 'custom.js', fileSize: '2MB' }, + ], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { hours: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: 3, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { hours: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 1 }), + msg: chance.sentence({ words: 5 }), + senderId: 8, + type: 'text', + attachment: [], + id: uniqueId(), + }, + ], + }, + { + id: 9, + name: 'Charles Martha', + status: 'online', + thumb: user4, + recent: false, + excerpt: 'Administrator', + messages: [ + { + createdAt: sub(new Date(), { hours: 10 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [ + { icon: java, file: 'work-project.zip', fileSize: '20MB' }, + { icon: zip, file: 'custom.js', fileSize: '2MB' }, + ], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { hours: 8 }), + msg: chance.sentence({ words: 5 }), + senderId: 3, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { hours: 8 }), + msg: chance.sentence({ words: 5 }), + senderId: 3, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 5 }), + msg: chance.sentence({ words: 5 }), + senderId: 9, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 2 }), + msg: chance.sentence({ words: 5 }), + senderId: 9, + type: 'text', + attachment: [], + id: uniqueId(), + }, + ], + }, + { + id: 10, + name: 'Samuel Eliza', + status: 'online', + thumb: user5, + recent: false, + excerpt: 'Doctor', + messages: [ + { + createdAt: sub(new Date(), { hours: 10 }), + msg: chance.sentence({ words: 5 }), + senderId: 1, + type: 'text', + attachment: [ + { icon: adobe, file: 'service-task.pdf', fileSize: '2MB' }, + { icon: zip, file: 'custom.js', fileSize: '2MB' }, + ], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { hours: 11 }), + msg: chance.sentence({ words: 5 }), + senderId: 3, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { hours: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: 3, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { hours: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: 3, + type: 'text', + attachment: [], + id: uniqueId(), + }, + { + createdAt: sub(new Date(), { minutes: 6 }), + msg: chance.sentence({ words: 5 }), + senderId: 10, + type: 'text', + attachment: [], + id: uniqueId(), + }, + ], + }, +]; + +mock.onGet('/api/data/chat/ChatData').reply(() => { + return [200, ChatData]; +}); + +export default ChatData; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/contacts/ContactsData.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/contacts/ContactsData.tsx new file mode 100644 index 0000000..0ec2823 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/contacts/ContactsData.tsx @@ -0,0 +1,470 @@ +import mock from '../mock'; +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; +import user4 from 'src/assets/images/profile/user-4.jpg'; +import user5 from 'src/assets/images/profile/user-5.jpg'; +import type { ContactType } from 'src/types/apps/contact'; +import { Chance } from 'chance'; + +const chance = new Chance(); + +export const ContactList: ContactType[] = [ + { + id: 1, + firstname: 'Georgeanna', + lastname: 'Ramero', + image: user2, + department: 'Sales', + company: 'Muller Inc', + phone: '456-485-5623', + email: 'qq739v47ggn@claimab.com', + address: '19214 110th Rd, Saint Albans, NY, 1141', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: true, + deleted: false, + }, + { + id: 2, + firstname: 'Cami', + lastname: 'Macha', + image: user3, + department: 'Support', + company: 'Zboncak LLC', + phone: '999-895-9652', + email: 'Camisad@claimab.com', + address: '76 Hamilton Ave, Yonkers, NY, 10705', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: false, + deleted: false, + }, + { + id: 3, + firstname: 'Alda', + lastname: 'Ziemer', + image: user4, + department: 'Engineering', + company: 'Lehner-Jacobson', + phone: '789-854-8950', + email: 'Ziemer234@claimab.com', + address: '930 Fruit Ave, Farrell, PA, 16121', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: false, + deleted: false, + }, + { + id: 4, + firstname: 'Luciano', + lastname: 'Macpherson', + image: user5, + department: 'Support', + company: 'Champlin', + phone: '452-652-5230', + email: 'Macpherson34@claimab.com', + address: '19103 Stefani Ave, Cerritos, CA, 90703', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: true, + deleted: true, + }, + { + id: 5, + firstname: 'Dalton', + lastname: 'Paden', + image: user1, + department: 'Engineering', + company: 'Balistreri', + phone: '985-985-7850', + email: 'Dalton321@claimab.com', + address: '3059 Edgewood Park Ct, Commerce Township', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: false, + deleted: false, + }, + { + id: 6, + firstname: 'Juan', + lastname: 'Granado', + image: user2, + department: 'Support', + company: 'Bernier-Ankunding', + phone: '230-541-5231', + email: 'Granado567@claimab.com', + address: '1330 N Douglas Ave, Arlington Heights', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: false, + deleted: true, + }, + { + id: 7, + firstname: 'Reva', + lastname: 'Allen', + image: user3, + department: 'Support', + company: 'Rosenbaum Inc', + phone: '478-582-6520', + email: 'Allen326@claimab.com', + address: '180 Topp Ln, Tupelo, MS', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: false, + deleted: true, + }, + { + id: 8, + firstname: 'Jule', + lastname: 'Huseman', + image: user4, + department: 'Sales', + company: 'Smith-Romaguera', + phone: '123-652-2301', + email: 'Huseman458@claimab.com', + address: '33 Caraway Rd, Reisterstown, MD', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: true, + deleted: true, + }, + { + id: 9, + firstname: 'Bridgette', + lastname: 'Phung', + image: user5, + department: 'Engineering', + company: 'Corwin-Kassulke', + phone: '652-452-6521', + email: 'Bridgette890@claimab.com', + address: '#RR, Bruceton Mills, WV', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: true, + deleted: true, + }, + { + id: 10, + firstname: 'Ernest', + lastname: 'Cousins', + image: user2, + department: 'Support', + company: 'Homenick-Hartmann', + phone: '785-985-6541', + email: 'Ernest6543@claimab.com', + address: 'Michael I. Days 3756 Preston Street Wichita', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: false, + deleted: true, + }, + { + id: 11, + firstname: 'Nicolette', + lastname: 'Trapani', + image: user1, + department: 'Engineering', + company: 'Gleason', + phone: '652-632-6520', + email: 'Nicoletteesdasd4@claimab.com', + address: 'Carol J. Stephens 1635 Franklin Street Montgomery', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: false, + deleted: true, + }, + { + id: 12, + firstname: 'Virginia', + lastname: 'Bourdeau', + image: user2, + department: 'Support', + company: 'McKenzie and Sons', + phone: '125-985-3210', + email: 'Bourdeauerwe@claimab.com', + address: 'Donald M. Palmer 2595 Pearlman Avenue', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: false, + deleted: false, + }, + { + id: 13, + firstname: 'Janita', + lastname: 'Vogl', + image: user3, + department: 'Sales', + company: 'Erdman-Moen', + phone: '541-521-6320', + email: 'Janitafdaa@claimab.com', + address: 'Micheal R. Porterfield 508 Virginia Street', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: true, + deleted: false, + }, + { + id: 14, + firstname: 'Jeneva', + lastname: 'Bridgeforth', + image: user4, + department: 'Engineering', + company: 'Fay LLC', + phone: '975-895-5240', + email: 'Bridgeforth564@claimab.com', + address: 'Nathan K. Flores 1516 Holt Street West Palm', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: true, + deleted: false, + }, + { + id: 15, + firstname: 'Roselia', + lastname: 'Principe', + image: user5, + department: 'Sales', + company: 'Bode-Oberbrunner', + phone: '874-546-6521', + email: 'Principe326@claimab.com', + address: '2915 Auburn Creek LnLeague City', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: true, + deleted: false, + }, + { + id: 16, + firstname: 'Elvira', + lastname: 'Hylton', + image: user1, + department: 'Support', + company: 'Pagac Group', + phone: '652-542-5200', + email: 'Elviraoknsss@claimab.com', + address: '2725 Cottage Rd Alpine', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: false, + deleted: false, + }, + { + id: 17, + firstname: 'Maragaret', + lastname: 'Pecor', + image: user2, + department: 'Sales', + company: 'Predovic and Sons', + phone: '326-984-1200', + email: 'Maragaret4352@mediafire.com', + address: '307 Hardy St Aberdeen', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: true, + deleted: false, + }, + { + id: 18, + firstname: 'Willena', + lastname: 'Sugrue', + image: user3, + department: 'Support', + company: 'Graham Group', + phone: '265-632-4521', + email: 'Willena75637@claimab.com', + address: '15919 Golf Club Dr Crosby', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: true, + deleted: false, + }, + { + id: 19, + firstname: 'Eura', + lastname: 'Solley', + image: user4, + department: 'Sales', + company: 'Toy-Ryan', + phone: '645-647-4800', + email: 'Solley6472@claimab.com', + address: 'Po Box 144 Rhome', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: false, + deleted: true, + }, + { + id: 20, + firstname: 'Velva', + lastname: 'Brockett', + image: user5, + department: 'Support', + company: 'Walsh Ltd', + phone: '654-985-6520', + email: 'Brocketterewgdb@claimab.com', + address: '34 Fairview Ln Palm Coast', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: true, + deleted: true, + }, + { + id: 21, + firstname: 'Anya', + lastname: 'Snapp', + image: user3, + department: 'Support', + company: 'Romaguera Inc', + phone: '456-652-3210', + email: 'Snapp76848@claimab.com', + address: '17919 Barney Dr Accokeek', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: false, + deleted: false, + }, + { + id: 22, + firstname: 'Latoria', + lastname: 'Penaloza', + image: user1, + department: 'Engineering', + company: 'Leuschke', + phone: '459-985-4520', + email: 'Penaloza3546@claimab.com', + address: '14 Huntington Dr Greenbrier', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: false, + deleted: true, + }, + { + id: 23, + firstname: 'Tamika', + lastname: 'Inman', + image: user2, + department: 'Sales', + company: 'Schumm', + phone: '645-978-4150', + email: 'Tamikadfdf45@claimab.com', + address: '1341 Mentionville Rd Darien', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: false, + deleted: true, + }, + { + id: 24, + firstname: 'Erich', + lastname: 'Aragon', + image: user3, + department: 'Business Development', + company: 'Brakus', + phone: '450-980-6520', + email: 'Aragondfdf4567@claimab.com', + address: '13 Pent Rd Branford', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: false, + deleted: true, + }, + { + id: 25, + firstname: 'Johanna', + lastname: 'Randel', + image: user4, + department: 'Sales', + company: 'Goyette', + phone: '120-320-4520', + email: 'Johanna456@claimab.com', + address: '5791 S Staghorn Cholla Ct Apache Junction', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: true, + deleted: true, + }, + { + id: 26, + firstname: 'Victorina', + lastname: 'Heinze', + image: user4, + department: 'Business Development', + company: 'Fritsch', + phone: '452-521-1230', + email: 'Victorina4545@claimab.com', + address: '69 El Molino Dr Clayton', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: false, + deleted: true, + }, + { + id: 27, + firstname: 'Kiley', + lastname: 'Light', + image: user5, + department: 'Sales', + company: 'Langosh', + phone: '652-452-1230', + email: 'Kileydfdfd45@claimab.com', + address: '215 Waterfront Ct Noblesville', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: true, + deleted: false, + }, + { + id: 28, + firstname: 'Sanford', + lastname: 'Delorenzo', + image: user1, + department: 'Engineering', + company: 'Huels', + phone: '963-652-1230', + email: 'Delorenzo3456@claimab.com', + address: '11212 Amber Rd Manistee', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: true, + starred: true, + deleted: false, + }, + { + id: 29, + firstname: 'Hans', + lastname: 'Strebel', + image: user2, + department: 'Sales', + company: 'Kohler', + phone: '546-654-1230', + email: 'Strebel345@claimab.com', + address: '2009 W Azalea Ave Baker', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: false, + deleted: false, + }, + { + id: 30, + firstname: 'Roger', + lastname: 'Trinidad', + image: user1, + department: 'Sales', + company: 'Kling-Hintz', + phone: '123-456-7890', + email: '3mcrz8gmymd@claimab.com', + address: '203 Dawn Dr, Mount Holly, NC, 28120', + notes: chance.paragraph({ sentences: 2 }), + frequentlycontacted: false, + starred: true, + deleted: true, + }, +]; + +mock.onGet('/api/data/contacts/ContactsData').reply(() => { + const contacts = ContactList; + + return [200, JSON.parse(JSON.stringify(contacts))]; +}); +export default ContactList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/eCommerce/ProductsData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/eCommerce/ProductsData.ts new file mode 100644 index 0000000..eabec0e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/eCommerce/ProductsData.ts @@ -0,0 +1,230 @@ +import mock from '../mock'; +import { sub } from 'date-fns'; +import { Chance } from 'chance'; +import s1 from 'src/assets/images/products/s1.jpg'; +import s2 from 'src/assets/images/products/s2.jpg'; +import s3 from 'src/assets/images/products/s3.jpg'; +import s4 from 'src/assets/images/products/s4.jpg'; +import s5 from 'src/assets/images/products/s5.jpg'; +import s6 from 'src/assets/images/products/s6.jpg'; +import s7 from 'src/assets/images/products/s7.jpg'; +import s8 from 'src/assets/images/products/s8.jpg'; +import s9 from 'src/assets/images/products/s9.jpg'; +import s10 from 'src/assets/images/products/s10.jpg'; +import s11 from 'src/assets/images/products/s11.jpg'; +import s12 from 'src/assets/images/products/s12.jpg'; + +const chance = new Chance(); + +const ProductsData = [ + { + title: 'How Innovation Works', + price: 275, + discount: 25, + related: false, + salesPrice: 350, + category: ['books'], + gender: 'Men', + rating: 3, + stock: true, + qty: 1, + colors: ['#1890FF'], + photo: s1, + id: 1, + created: sub(new Date(), { days: 8, hours: 6, minutes: 20 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'Psalms Book for Growth', + price: 89, + discount: 10, + related: true, + salesPrice: 99, + category: ['books'], + gender: 'Women', + rating: 3, + stock: false, + qty: 1, + colors: ['#1890FF', '#94D82D', '#FF4842'], + photo: s2, + id: 2, + created: sub(new Date(), { days: 10, hours: 8, minutes: 69 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'The Psychology of Money', + price: 125, + discount: 12, + related: false, + salesPrice: 137, + category: ['fashion', 'books'], + gender: 'Kids', + rating: 3, + stock: true, + qty: 1, + colors: ['#FF4842', '#1890FF', '#94D82D'], + photo: s3, + id: 3, + created: sub(new Date(), { days: 8, hours: 6, minutes: 20 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'Boat Headphone', + price: 50, + discount: 15, + related: true, + salesPrice: 65, + category: ['electronics'], + gender: 'Men', + rating: 3, + stock: true, + qty: 1, + colors: ['#1890FF', '#94D82D', '#FFC107'], + photo: s4, + id: 4, + created: sub(new Date(), { days: 4, hours: 9, minutes: 40 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'MacBook Air Pro', + price: 650, + discount: 250, + related: true, + salesPrice: 900, + category: ['fashion', 'electronics'], + gender: 'Women', + rating: 3, + stock: false, + qty: 1, + colors: ['#00AB55', '#000000'], + photo: s5, + id: 5, + created: sub(new Date(), { days: 2, hours: 5, minutes: 50 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'Gaming Console', + price: 25, + discount: 6, + related: true, + salesPrice: 31, + category: ['electronics'], + gender: 'Men', + rating: 3, + stock: true, + qty: 1, + colors: ['#FFC0CB', '#FF4842'], + photo: s6, + id: 6, + created: sub(new Date(), { days: 2, hours: 9, minutes: 45 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'Red Valvet Dress', + price: 150, + discount: 50, + related: false, + salesPrice: 200, + category: ['fashion'], + gender: 'Women', + rating: 3, + stock: true, + qty: 1, + colors: ['#FF4842', '#1890FF', '#94D82D'], + photo: s7, + id: 7, + created: sub(new Date(), { days: 6, hours: 10, minutes: 0 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'Shoes for Girls', + price: 300, + discount: 80, + related: false, + salesPrice: 380, + category: ['fashion', 'toys'], + gender: 'Women', + rating: 3, + stock: true, + qty: 1, + colors: ['#1890FF', '#94D82D', '#FFC107'], + photo: s8, + id: 8, + created: sub(new Date(), { days: 7, hours: 5, minutes: 20 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'Short & Sweet Purse', + price: 175, + discount: 25, + related: false, + salesPrice: 200, + category: ['fashion'], + gender: 'Women', + rating: 3, + stock: true, + qty: 1, + colors: ['#00AB55', '#000000'], + photo: s9, + id: 9, + created: sub(new Date(), { days: 8, hours: 6, minutes: 20 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'Toy Dino for Fun', + price: 210, + discount: 40, + related: false, + salesPrice: 250, + category: ['toys'], + gender: 'Kids', + rating: 3, + stock: true, + qty: 1, + colors: ['#FFC0CB', '#FF4842'], + photo: s10, + id: 10, + created: sub(new Date(), { days: 6, hours: 6, minutes: 20 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'Cute Soft Teddybear', + price: 285, + discount: 60, + related: false, + salesPrice: 345, + category: ['toys'], + gender: 'Kids', + rating: 3, + stock: true, + qty: 1, + colors: ['#FF4842', '#1890FF', '#94D82D'], + photo: s11, + id: 11, + created: sub(new Date(), { days: 1, hours: 6, minutes: 20 }), + description: chance.paragraph({ sentences: 2 }), + }, + { + title: 'Little Angel Toy', + price: 5, + discount: 5, + related: false, + salesPrice: 10, + category: ['toys'], + gender: 'Kids', + rating: 3, + stock: true, + qty: 1, + colors: ['#1890FF', '#94D82D', '#FFC107'], + photo: s12, + id: 12, + created: sub(new Date(), { days: 9, hours: 6, minutes: 20 }), + description: chance.paragraph({ sentences: 2 }), + }, +]; + +mock.onGet('/api/data/eCommerce/ProductsData').reply(() => { + return [200, ProductsData]; +}); + +export default ProductsData; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/email/EmailData.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/email/EmailData.tsx new file mode 100644 index 0000000..c5d4612 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/email/EmailData.tsx @@ -0,0 +1,508 @@ +import mock from '../mock'; +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; +import user4 from 'src/assets/images/profile/user-4.jpg'; +import user5 from 'src/assets/images/profile/user-5.jpg'; +import user6 from 'src/assets/images/profile/user-1.jpg'; +import user7 from 'src/assets/images/profile/user-2.jpg'; +import user8 from 'src/assets/images/profile/user-3.jpg'; +import type { EmailType } from 'src/types/apps/email'; +import adobe from 'src/assets/images/chat/icon-adobe.svg'; +import chrome from 'src/assets/images/chat/icon-chrome.svg'; +import figma from 'src/assets/images/chat/icon-figma.svg'; +import java from 'src/assets/images/chat/icon-javascript.svg'; +import zip from 'src/assets/images/chat/icon-zip-folder.svg'; + +import { sub } from 'date-fns'; + +const EmailData: EmailType[] = [ + { + id: 1, + from: 'James Smith', + thumbnail: user1, + subject: 'Kindly check this latest updated', + time: sub(new Date(), { days: 0, hours: 1, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'Contrary to popular belief, Lorem Ipsum is not simply random text. ', + emailContent: `

Hello Andrew,

+

Lorem ipsum dolor sit amet, consectetur adipiscing elit. Quisque bibendum hendrerit lobortis. Nullam ut lacus eros. Sed at luctus urna, eu fermentum diam. In et tristique mauris.

+

Ut id ornare metus, sed auctor enim. Pellentesque nisi magna, laoreet a augue eget, + tempor volutpat diam.

+

Regards,
James Smith

+ `, + unread: true, + attachment: false, + starred: true, + important: false, + inbox: true, + sent: false, + draft: false, + spam: false, + trash: false, + label: 'Promotional', + attchments: [ + { + id: '#1Attach', + image: adobe, + title: 'adobe.pdf', + fileSize: '2MB', + }, + { + id: '#2Attach', + image: chrome, + title: 'abouts.html', + fileSize: '2MB', + }, + { + id: '#3Attach', + image: zip, + title: 'cheese.zip', + fileSize: '2MB', + }, + ], + }, + { + id: 2, + from: 'Michael Smith', + thumbnail: user2, + subject: 'Fact that a reader will be distracted.', + time: sub(new Date(), { days: 0, hours: 3, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'It has roots in a piece of classical Latin literature from 45 BC', + emailContent: `

Hello Andrew,

+

Lorem ipsum dolor sit amet, consectetur adipiscing elit. Quisque bibendum hendrerit lobortis. Nullam ut lacus eros. Sed at luctus urna, eu fermentum diam. In et tristique mauris.

+

Ut id ornare metus, sed auctor enim. Pellentesque nisi magna, laoreet a augue eget, + tempor volutpat diam.

+

Regards,
Michael Smith

+ `, + unread: true, + attachment: false, + starred: true, + important: false, + inbox: false, + sent: false, + draft: true, + spam: false, + trash: false, + label: 'Social', + attchments: [], + }, + { + id: 3, + from: 'Robert Smith', + thumbnail: user3, + subject: 'The point of using Lorem Ipsum is that it has a more-or-less normal', + time: sub(new Date(), { days: 0, hours: 11, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'Richard McClintock, a Latin professor at Hampden-Sydney', + emailContent: + '

Dummy text is also used to demonstrate the appearance of different typefaces and layouts, and in general the content of dummy text is nonsensical. ', + unread: false, + attachment: false, + starred: false, + important: true, + inbox: false, + sent: true, + draft: false, + spam: false, + trash: false, + label: 'Promotional', + attchments: [ + { + id: '#4Attach', + image: figma, + title: 'service.fig', + fileSize: '2MB', + }, + { + id: '#5Attach', + image: java, + title: 'abouts.js', + fileSize: '2MB', + }, + ], + }, + { + id: 4, + from: 'Maria Garcia', + thumbnail: user4, + subject: 'Contrary to popular belief, Lorem Ipsum is.', + time: sub(new Date(), { days: 1, hours: 2, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'Lorem Ipsum passage, and going through', + emailContent: + '

Furthermore, it is advantageous when the dummy text is relatively realistic so that the layout impression of the final publication is not compromised.

', + unread: false, + attachment: true, + starred: true, + important: false, + inbox: false, + sent: false, + draft: true, + spam: false, + trash: false, + label: 'Social', + attchments: [], + }, + { + id: 5, + from: 'David Smith', + thumbnail: user5, + subject: 'Literature from 45 BC, making', + time: sub(new Date(), { days: 1, hours: 8, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'The standard chunk of Lorem Ipsum used since the 1500s', + emailContent: + '

One disadvantage of Lorum Ipsum is that in Latin certain letters appear more frequently than others which creates a distinct visual impression.

', + unread: false, + attachment: false, + starred: false, + important: true, + inbox: true, + sent: false, + draft: false, + spam: false, + trash: false, + label: 'Social', + attchments: [], + }, + { + id: 6, + from: 'Maria Rodriguez', + thumbnail: user6, + subject: 'Latin professor at Hampden-Sydney College.', + time: sub(new Date(), { days: 1, hours: 10, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'Cicero are also reproduced in their exact original form', + emailContent: + '

Thus, Lorem Ipsum has only limited suitability as a visual filler for German texts. If the fill text is intended to illustrate the characteristics of different typefaces.

', + unread: false, + attachment: true, + starred: false, + important: true, + inbox: true, + sent: false, + draft: false, + spam: false, + trash: false, + label: 'Health', + attchments: [], + }, + { + id: 7, + from: 'Mary Smith', + thumbnail: user7, + subject: 'the cites of the word in classical.', + time: sub(new Date(), { days: 1, hours: 11, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'There are many variations of passages of Lorem Ipsum available', + emailContent: + '

There is now an abundance of readable dummy texts. These are usually used when a text is required purely to fill a space.These alternatives to the classic Lorem Ipsum texts are often amusing and tell short, funny or nonsensical stories.

', + unread: true, + attachment: true, + starred: false, + important: false, + inbox: true, + sent: false, + draft: false, + spam: false, + trash: false, + label: 'Social', + attchments: [], + }, + { + id: 8, + from: 'Maria Hernandez', + thumbnail: user8, + subject: ' This book is a treatise on the theory of ethics.', + time: sub(new Date(), { days: 2, hours: 1, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'the majority have suffered alteration in some form, by injected ', + emailContent: + '

According to most sources, Lorum Ipsum can be traced back to a text composed by Cicero in 45 BC. Allegedly, a Latin scholar established the origin of the text.

', + unread: false, + attachment: true, + starred: false, + important: true, + inbox: false, + sent: false, + draft: false, + spam: true, + trash: false, + label: 'Social', + attchments: [], + }, + { + id: 9, + from: 'Maria Martinez', + thumbnail: user1, + subject: 'Lorem Ipsum used since the 1500s is reproduced.', + time: sub(new Date(), { days: 2, hours: 3, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'If you are going to use a passage of Lorem Ipsum', + emailContent: + '

It seems that only fragments of the original text remain in the Lorem Ipsum texts used today. One may speculate that over the course of time certain letters.

', + unread: false, + attachment: true, + starred: false, + important: false, + inbox: false, + sent: false, + draft: false, + spam: false, + trash: true, + label: 'Promotional', + attchments: [], + }, + { + id: 10, + from: 'James Johnson', + thumbnail: user2, + subject: 'accompanied by English versions from the 1914 translation.', + time: sub(new Date(), { days: 2, hours: 8, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: "you need to be sure there isn't anything", + emailContent: + '

This might also explain why one can now find slightly different versions. Due to the age of the Lorem Ipsum text there are no copyright issues to contend with.

', + unread: false, + attachment: true, + starred: true, + important: false, + inbox: false, + sent: true, + draft: false, + spam: false, + trash: false, + label: 'Health', + attchments: [], + }, + { + id: 11, + from: 'James Smith', + thumbnail: user3, + subject: 'All the Lorem Ipsum generators on the Internet.', + time: sub(new Date(), { days: 2, hours: 9, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'All the Lorem Ipsum generators on the Internet tend to repeat predefined', + emailContent: + '

The spread of computers and layout programmes thus made dummy text better known. While in earlier times several lines of the Lorem Ipsum text were repeated in the creation of dummy texts.

', + unread: false, + attachment: false, + starred: true, + important: false, + inbox: true, + sent: false, + draft: false, + spam: false, + trash: false, + label: 'Promotional', + attchments: [], + }, + { + id: 12, + from: 'Michael Smith', + thumbnail: user1, + subject: 'Latin words, combined with a handful.', + time: sub(new Date(), { days: 2, hours: 11, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'combined with a handful of model sentence structures', + emailContent: + "

basis for many dummy text or Lorem Ipsum generators. Based on 'De finibus', these generators automatically create longer sections of the Lorem Ipsum text or various other filler texts.

", + unread: false, + attachment: false, + starred: false, + important: false, + inbox: true, + sent: false, + draft: true, + spam: false, + trash: true, + label: 'Social', + attchments: [], + }, + { + id: 13, + from: 'Robert Smith', + thumbnail: user2, + subject: 'If you are going to use a passage.', + time: sub(new Date(), { days: 3, hours: 2, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'Lorem Ipsum is therefore always free from repetition, injected humour', + emailContent: + '

The phrasal sequence of the Lorem Ipsum text is now so widespread and commonplace that many DTP programmes can generate dummy text using the starting sequence.

', + unread: false, + attachment: true, + starred: true, + important: true, + inbox: false, + sent: true, + draft: false, + spam: false, + trash: false, + label: 'Health', + attchments: [], + }, + { + id: 14, + from: 'Maria Garcia', + thumbnail: user3, + subject: 'piece of classical Latin literature.', + time: sub(new Date(), { days: 3, hours: 11, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'Lorem Ipsum passage, and going through the cites', + emailContent: + '

now recognized by electronic pre-press systems and, when found, an alarm can be raised. This avoids a publication going to print with overlooked dummy text.

', + unread: false, + attachment: false, + starred: true, + important: false, + inbox: false, + sent: false, + draft: false, + spam: false, + trash: true, + label: 'Social', + attchments: [], + }, + { + id: 15, + from: 'David Smith', + thumbnail: user4, + subject: 'first true generator on the Internet.', + time: sub(new Date(), { days: 3, hours: 4, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'Lorem Ipsum is simply dummy text of the printing and typesetting industry.', + emailContent: + '

Certain internet providers exploit the fact that fill text cannot be recognized by automatic search engines - meaningful information cannot be distinguished from meaningless.

', + unread: false, + attachment: true, + starred: false, + important: false, + inbox: false, + sent: false, + draft: false, + spam: false, + trash: true, + label: 'Promotional', + attchments: [], + }, + { + id: 16, + from: 'Maria Rodriguez', + thumbnail: user5, + subject: 'combined with a handful of model sentence structure.', + time: sub(new Date(), { days: 4, hours: 1, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: "Lorem Ipsum has been the industry's standard dummy text ever since the 1500s", + emailContent: + "

Target-generated dummy text mixed with a certain combination of search terms can lead to an increased frequency of visits by search machine users. As a consequence, advertising revenues, which rely on website 'hits', are increased.

", + unread: true, + attachment: false, + starred: false, + important: true, + inbox: true, + sent: false, + draft: false, + spam: false, + trash: true, + label: 'Social', + attchments: [], + }, + { + id: 17, + from: 'Mary Smith', + thumbnail: user6, + subject: "randomised words which don't look even.", + time: sub(new Date(), { days: 4, hours: 1, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'when an unknown printer took a galley of type', + emailContent: + '

Vitae purus faucibus ornare suspendisse sed nisi lacus sed viverra. Amet nisl suscipit adipiscing bibendum est ultricies integer.

', + unread: true, + attachment: false, + starred: false, + important: false, + inbox: false, + sent: false, + draft: false, + spam: true, + trash: false, + label: 'Health', + attchments: [], + }, + { + id: 18, + from: 'Maria Hernandez', + thumbnail: user7, + subject: 'Lorem Ipsum generators on the Internet tend.', + time: sub(new Date(), { days: 4, hours: 1, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'scrambled it to make a type specimen book', + emailContent: + '

Volutpat diam ut venenatis tellus in metus vulputate eu. Id aliquet lectus proin nibh nisl condimentum id venenatis. Risus quis varius quam quisque id diam vel. Pulvinar pellentesque habitant morbi tristique senectus et netus et.

', + unread: false, + attachment: false, + starred: false, + important: true, + inbox: false, + sent: true, + draft: false, + spam: false, + trash: false, + label: 'Promotional', + attchments: [], + }, + { + id: 19, + from: 'Maria Martinez', + thumbnail: user8, + subject: 'combined with a handful of model.', + time: sub(new Date(), { days: 4, hours: 1, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'It has survived not only five centuries', + emailContent: + '

Scelerisque purus semper eget duis at. Tempus imperdiet nulla malesuada pellentesque elit. Vitae semper quis lectus nulla at volutpat. Ac tortor vitae purus faucibus ornare suspendisse.

', + unread: true, + attachment: false, + starred: false, + important: false, + inbox: false, + sent: false, + draft: true, + spam: false, + trash: false, + label: 'Health', + attchments: [], + }, + { + id: 20, + from: 'James Johnson', + thumbnail: user1, + subject: 'The Extremes of Good and Evil.', + time: sub(new Date(), { days: 4, hours: 1, minutes: 45 }), + To: 'abc@company.com', + emailExcerpt: 'the 1960s with the release of Letraset sheets containings', + emailContent: + '

Ultrices in iaculis nunc sed augue lacus viverra. Tellus cras adipiscing enim eu turpis egestas. Libero enim sed faucibus turpis in eu mi bibendum neque. Consectetur adipiscing elit ut aliquam. Mattis nunc sed blandit libero volutpat sed cras.

', + unread: false, + attachment: true, + starred: true, + important: true, + inbox: true, + sent: false, + draft: false, + spam: false, + trash: false, + label: 'Social', + attchments: [], + }, +]; + +mock.onGet('/api/data/email/EmailData').reply(() => { + const emails = EmailData; + + return [200, JSON.parse(JSON.stringify(emails))]; +}); + +export default EmailData; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/index.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/index.ts new file mode 100644 index 0000000..913e3d4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/index.ts @@ -0,0 +1,14 @@ +import mock from './mock'; +import './blog/blogData'; +import './contacts/ContactsData'; +import './chat/Chatdata'; +import './notes/NotesData'; +import './ticket/TicketData'; +import './eCommerce/ProductsData'; +import './email/EmailData'; +import './userprofile/PostData'; +import './userprofile/UsersData'; +import './invoice/invoceLists'; +import './kanban/KanbanData'; + +mock.onAny().passThrough(); diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/invoice/invoceLists.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/invoice/invoceLists.tsx new file mode 100644 index 0000000..fe6a1d8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/invoice/invoceLists.tsx @@ -0,0 +1,241 @@ +import { InvoiceList } from 'src/types/apps/invoice'; +import mock from '../mock'; + +export const invoceLists: InvoiceList[] = [ + { + id: 101, + billFrom: 'PineappleInc.', + billFromEmail: 'first@xabz.com', + billFromAddress: 'Ganesh glory,Godrej garden city,Ahmedabad.', + billFromPhone: 979796786, + billFromFax: 13, + billTo: 'Redq Inc.', + billToEmail: 'toFirst@agth.com', + billToAddress: 'Godrej garden city,Ahmedabad.', + billToPhone: 757575233, + billToFax: 76, + orders: [ + { + itemName: 'Courge', + unitPrice: 10, + units: 9, + unitTotalPrice: 90, + }, + ], + orderDate: new Date(), + totalCost: 90, + vat: 9, + grandTotal: 99, + status: 'Shipped', + completed: false, + isSelected: false, + }, + { + id: 102, + billFrom: 'Pineapple.', + billFromEmail: 'first@xabz.com', + billFromAddress: 'Ganesh glory,Godrej garden city,Ahmedabad.', + billFromPhone: 979796786, + billFromFax: 13, + billTo: 'ME Inc.', + billToEmail: 'toFirst@agth.com', + billToAddress: 'Godrej garden city,Ahmedabad.', + billToPhone: 757575233, + billToFax: 76, + orders: [ + { + itemName: 'Courge', + unitPrice: 10, + units: 9, + unitTotalPrice: 90, + }, + ], + orderDate: new Date(), + totalCost: 90, + vat: 9, + grandTotal: 99, + status: 'Delivered', + completed: false, + isSelected: false, + }, + { + id: 103, + billFrom: 'Incorporation.', + billFromEmail: 'first@xabz.com', + billFromAddress: 'Ahmedabad.', + billFromPhone: 979796786, + billFromFax: 13, + billTo: 'Redirwed.', + billToEmail: 'toFirst@agth.com', + billToAddress: 'Godrej garden city,Ahmedabad.', + billToPhone: 757575233, + billToFax: 76, + orders: [ + { + itemName: 'Courge', + unitPrice: 10, + units: 9, + unitTotalPrice: 90, + }, + ], + orderDate: new Date(), + totalCost: 90, + vat: 9, + grandTotal: 99, + status: 'Pending', + completed: false, + isSelected: false, + }, + { + id: 104, + billFrom: 'PineappleTimes.', + billFromEmail: 'first@xabz.com', + billFromAddress: 'Ganesh glory,Godrej garden city,Ahmedabad.', + billFromPhone: 979796786, + billFromFax: 13, + billTo: 'RFc.', + billToEmail: 'toFirst@agth.com', + billToAddress: 'Godrej garden city,Ahmedabad.', + billToPhone: 757575233, + billToFax: 76, + orders: [ + { + itemName: 'Courge', + unitPrice: 10, + units: 9, + unitTotalPrice: 90, + }, + ], + orderDate: new Date(), + totalCost: 90, + vat: 9, + grandTotal: 99, + status: 'Shipped', + completed: false, + isSelected: false, + }, + { + id: 105, + billFrom: 'FortuneCreation', + billFromEmail: 'first@xabz.com', + billFromAddress: 'Ganesh glory,Godrej garden city,Ahmedabad.', + billFromPhone: 979796786, + billFromFax: 13, + billTo: 'Soft solution.', + billToEmail: 'toFirst@agth.com', + billToAddress: 'Godrej garden city,Ahmedabad.', + billToPhone: 757575233, + billToFax: 76, + orders: [ + { + itemName: 'Courge', + unitPrice: 10, + units: 9, + unitTotalPrice: 90, + }, + ], + orderDate: new Date('2020-10-15'), + totalCost: 90, + vat: 9, + grandTotal: 99, + status: 'Delivered', + completed: false, + isSelected: false, + }, + { + id: 106, + billFrom: 'PineappleTimes.', + billFromEmail: 'first@xabz.com', + billFromAddress: 'Ganesh glory,Godrej garden city,Ahmedabad.', + billFromPhone: 979796786, + billFromFax: 13, + billTo: 'RFc.', + billToEmail: 'toFirst@agth.com', + billToAddress: 'Godrej garden city,Ahmedabad.', + billToPhone: 757575233, + billToFax: 76, + orders: [ + { + itemName: 'Courge', + unitPrice: 10, + units: 9, + unitTotalPrice: 90, + }, + ], + orderDate: new Date(), + totalCost: 90, + vat: 9, + grandTotal: 99, + status: 'Shipped', + completed: false, + isSelected: false, + }, + { + id: 107, + billFrom: 'FortuneCreation', + billFromEmail: 'first@xabz.com', + billFromAddress: 'Ganesh glory,Godrej garden city,Ahmedabad.', + billFromPhone: 979796786, + billFromFax: 13, + billTo: 'Soft solution.', + billToEmail: 'toFirst@agth.com', + billToAddress: 'Godrej garden city,Ahmedabad.', + billToPhone: 757575233, + billToFax: 76, + orders: [ + { + itemName: 'Courge', + unitPrice: 10, + units: 9, + unitTotalPrice: 90, + }, + ], + orderDate: new Date('2020-10-15'), + totalCost: 90, + vat: 9, + grandTotal: 99, + status: 'Delivered', + completed: false, + isSelected: false, + }, +]; + +mock.onGet('/api/data/invoicedata').reply(() => { + return [200, invoceLists]; +}); + +mock.onDelete('/api/data/invoicedata/deleteinvoice').reply((config) => { + const { invoiceId } = JSON.parse(config.data); + const invoiceIndex = invoceLists.findIndex(invoice => invoice.id === invoiceId); + if (invoiceIndex !== -1) { + invoceLists.splice(invoiceIndex, 1); + return [200, invoceLists]; + } else { + return [404, { message: 'invoice not found' }]; + } +}) +// Function to find the next available ID +const getNextId = () => { + const maxId = Math.max(...invoceLists.map(invoice => invoice.id)); + return maxId + 1; +}; +// New endpoint to add an invoice +mock.onPost('/api/data/invoicedata/addinvoice').reply((config) => { + const newInvoice = JSON.parse(config.data); + newInvoice.id = getNextId(); + invoceLists.push(newInvoice); + return [201, newInvoice]; +}); + +// Mock API endpoint to update an invoice +mock.onPut('/api/data/invoicedata/updateinvoice').reply((config) => { + const updatedInvoice = JSON.parse(config.data); + const invoiceIndex = invoceLists.findIndex((invoice) => invoice.id === updatedInvoice.id); + + if (invoiceIndex !== -1) { + invoceLists[invoiceIndex] = { ...updatedInvoice }; + return [200, invoceLists[invoiceIndex]]; + } else { + return [404, { message: 'Invoice not found' }]; + } +}); \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/kanban/KanbanData.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/kanban/KanbanData.tsx new file mode 100644 index 0000000..16770f7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/kanban/KanbanData.tsx @@ -0,0 +1,234 @@ +import { TodoCategory } from '../../types/apps/kanban'; +import mock from '../mock'; +import img1 from '../../assets/images/kanban/kanban-img-1.jpg'; +import img2 from '../../assets/images/kanban/kanban-img-2.jpg'; +import img3 from '../../assets/images/kanban/kanban-img-3.jpg'; +import img4 from '../../assets/images/kanban/kanban-img-4.jpg'; + +const KanbanData: TodoCategory[] = [ + { + id: '1', + name: 'Todo', + child: [ + { + id: '101', + task: 'This is first task', + taskImage: img1, + taskText: '', + date: '24 july', + taskProperty: 'Design', + }, + { + id: '102', + task: 'lets do some task on pd', + taskImage: '', + taskText: + 'Lorem ipsum dolor sit amet, consectetur adipisicing elit, o eiusmod tempor incid.', + date: '24 july', + taskProperty: 'Mobile', + }, + { + id: '103', + task: 'Do some projects on React Native with Flutter', + taskImage: '', + taskText: '', + date: '24 july', + taskProperty: 'Mobile', + }, + ], + }, + { + id: '2', + name: 'Progress', + child: [ + { + id: '104', + task: 'Design navigation changes', + taskImage: '', + taskText: '', + date: '24 july', + taskProperty: 'Mobile', + category: '', + }, + { + id: '105', + task: 'Battle with fire', + taskImage: img2, + taskText: '', + date: '24 july', + taskProperty: 'Design', + category: '', + }, + { + id: '106', + task: 'First design concept', + taskImage: '', + taskText: '', + date: '24 july', + taskProperty: 'Mobile', + category: '', + }, + ], + }, + { + id: '3', + name: 'Pending', + child: [ + { + id: '107', + task: 'Persona development', + taskImage: '', + taskText: + 'Create user personas based on the research data to represent different user groups and their characteristics, gols, and behaviors..', + date: '24 july', + taskProperty: 'UX Stage', + category: 'Pending', + }, + { + id: '108', + task: 'Redesign overview', + taskImage: img3, + taskText: '', + date: '14 july', + taskProperty: 'Design', + category: 'Pending', + }, + ], + }, + { + id: '4', + name: 'Done', + child: [ + { + id: '109', + task: 'Usability testing', + taskImage: img4, + taskText: '', + date: '24 july', + taskProperty: 'Research', + category: 'Done', + }, + { + id: '110', + task: 'Introduce new navigation', + taskImage: '', + taskText: '', + date: '24 july', + taskProperty: 'Data Science', + category: 'Done', + }, + { + id: '111', + task: 'Branding visual identity', + taskImage: '', + taskText: '', + date: '4 july', + taskProperty: 'Branding', + category: 'Done', + }, + { + id: '112', + task: 'Competitor research', + taskImage: '', + taskText: + 'research competitors and identify weakness and strengths each of them. comparing their product features, quelity...', + date: '14 july', + taskProperty: 'UX Stage', + category: 'Done', + }, + ], + }, +]; + +// Extracting unique task properties from TodoData +const taskPropertiesSet = new Set(); + +// Using forEach loops instead of flatMap +KanbanData.forEach((category) => { + category.child.forEach((task) => { + taskPropertiesSet.add(task.taskProperty); + }); +}); + +// Convert Set to array +export const TaskProperties = Array.from(taskPropertiesSet); + +// Mock API endpoint to fetch TodoData +mock.onGet('/api/TodoData').reply(200, KanbanData); + +// Mock API endpoint to delete a category +mock.onDelete('/api/TodoData').reply((config) => { + const { id } = JSON.parse(config.data); + const updatedTodoData = KanbanData.filter((category) => category.id !== id); + return [200, updatedTodoData]; +}); + +// Mock API endpoint to clear all tasks from a category +mock.onDelete('/api/TodoData/clearTasks').reply((config) => { + const { categoryId } = JSON.parse(config.data); + const updatedTodoData = KanbanData.map((category) => { + if (category.id === categoryId) { + return { ...category, child: [] }; + } + return category; + }); + return [200, updatedTodoData]; +}); + +// Mock API endpoint to add a new task +mock.onPost('/api/TodoData/addTask').reply((config) => { + const { categoryId, newTaskData } = JSON.parse(config.data); + const updatedTodoData = KanbanData.map((category) => { + if (category.id === categoryId) { + return { ...category, child: [...category.child, newTaskData] }; + } + return category; + }); + return [200, updatedTodoData]; +}); + +// Mock API endpoint to add a new category +mock.onPost('/api/TodoData/addCategory').reply((config) => { + const { categoryName } = JSON.parse(config.data); + const newCategory = { + id: Math.random(), + name: categoryName, + child: [], + }; + KanbanData.push(newCategory); + return [200, newCategory]; +}); + +// Mock API endpoint to update the name of a category +mock.onPost('/api/TodoData/updateCategory').reply((config) => { + const { categoryId, categoryName } = JSON.parse(config.data); + const updatedTodoData = KanbanData.map((category) => { + if (category.id === categoryId) { + return { ...category, name: categoryName }; + } + return category; + }); + return [200, updatedTodoData]; +}); + +// Mock API endpoint to edit a task +mock.onPut('/api/TodoData/editTask').reply((config) => { + const { taskId, newData } = JSON.parse(config.data); + KanbanData.forEach((category) => { + category.child.forEach((task) => { + if (task.id === taskId) { + Object.assign(task, newData); + } + }); + }); + return [200, KanbanData]; +}); + +// Mock API endpoint to delete a task +mock.onDelete('/api/TodoData/deleteTask').reply((config) => { + const { taskId } = JSON.parse(config.data); + const updatedTodoData = KanbanData.filter((task) => task.id !== taskId); + return [200, updatedTodoData]; +}); + +export default KanbanData; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/language/LanguageData.js b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/language/LanguageData.js new file mode 100644 index 0000000..3641526 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/language/LanguageData.js @@ -0,0 +1,40 @@ +import mock from '../mock'; + +import FlagEn from 'src/assets/images/svgs/icon-flag-en.svg'; +import FlagFr from 'src/assets/images/svgs/icon-flag-fr.svg'; +import FlagCn from 'src/assets/images/svgs/icon-flag-cn.svg'; +import FlagSa from 'src/assets/images/svgs/icon-flag-sa.svg'; +import FlagVn from 'src/assets/images/svgs/icon-flag-vn.svg'; + +const LanguageData = [ + { + id: 1, + flagname: 'English', + icon: FlagEn, + }, + { + id: 2, + flagname: 'French', + icon: FlagFr, + }, + { + id: 3, + flagname: 'Vietnamese', + icon: FlagVn, + }, + { + id: 4, + flagname: 'Chinese', + icon: FlagCn, + }, + { + id: 5, + flagname: 'Arabic (Sudan)', + icon: FlagSa, + }, +]; + +mock.onGet('/api/data/language/LanguageData').reply(() => { + return [200, LanguageData]; +}); +export default LanguageData; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/mock.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/mock.ts new file mode 100644 index 0000000..2d26725 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/mock.ts @@ -0,0 +1,5 @@ +import AxiosMockAdapter from 'axios-mock-adapter'; +import axios from '../utils/axios'; + +const mock = new AxiosMockAdapter(axios, { delayResponse: 0 }); +export default mock; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/notes/NotesData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/notes/NotesData.ts new file mode 100644 index 0000000..7475fb7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/notes/NotesData.ts @@ -0,0 +1,48 @@ +import mock from '../mock'; + +interface notesType { + id: number; + color: string; + title: string; + datef: string; + deleted: boolean; +} + +const NotesData: notesType[] = [ + { + id: 1, + color: 'info', + title: + 'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.', + datef: '2023-06-03T23:28:56.782Z', + deleted: false, + }, + { + id: 2, + color: 'error', + title: + 'Sed ut perspiciatis unde omnis iste natus error sit voluptatem accusantium doloremque laudantium, totam rem aperiam, eaque ipsa quae ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit,', + datef: '2023-06-02T23:28:56.782Z', + deleted: false, + }, + { + id: 3, + color: 'warning', + title: + 'consectetur, adipisci velit, sed quia non numquam eius modi tempora incidunt ut labore et dolore magnam aliquam quaerat voluptatem. Ut enim ad minima veniam, quis nostrum exercitationem ullam corporis suscipit laboriosam, nisi ut aliquid ex ea commodi consequatur?', + datef: '2023-06-01T23:28:56.782Z', + deleted: false, + }, + { + id: 4, + color: 'success', + title: + 'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.', + datef: '2023-06-03T23:28:56.782Z', + deleted: false, + }, +]; +mock.onGet('/api/data/notes/NotesData').reply(() => { + return [200, NotesData]; +}); +export default NotesData; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/ticket/TicketData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/ticket/TicketData.ts new file mode 100644 index 0000000..897db0d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/ticket/TicketData.ts @@ -0,0 +1,114 @@ +import mock from '../mock'; +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; +import user4 from 'src/assets/images/profile/user-4.jpg'; +import user5 from 'src/assets/images/profile/user-5.jpg'; +import { Chance } from 'chance'; +import { TicketType } from 'src/types/apps/ticket'; + +const chance = new Chance(); + +const TicketData: TicketType[] = [ + { + Id: 1, + ticketTitle: 'Sed ut perspiciatis unde omnis iste', + ticketDescription: + 'ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos', + Status: 'Closed', + Label: 'error', + thumb: user1, + AgentName: 'Liam', + Date: chance.date(), + deleted: false, + }, + { + Id: 2, + ticketTitle: 'Consequuntur magni dolores eos qui ratione', + ticketDescription: + 'ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos', + Status: 'Pending', + Label: 'warning', + thumb: user2, + AgentName: 'Steve', + Date: chance.date(), + deleted: false, + }, + { + Id: 3, + ticketTitle: 'Exercitationem ullam corporis', + ticketDescription: + 'ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos', + Status: 'Open', + Label: 'success', + thumb: user3, + AgentName: 'Jack', + Date: chance.date(), + deleted: false, + }, + { + Id: 4, + ticketTitle: 'Sed ut perspiciatis unde omnis iste', + ticketDescription: + 'ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos', + Status: 'Closed', + Label: 'error', + thumb: user4, + AgentName: 'Steve', + Date: chance.date(), + deleted: false, + }, + { + Id: 5, + ticketTitle: 'Exercitationem ullam corporis', + ticketDescription: + 'ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos', + Status: 'Closed', + Label: 'error', + thumb: user5, + AgentName: 'Liam', + Date: chance.date(), + deleted: false, + }, + { + Id: 6, + ticketTitle: 'Consequuntur magni dolores eos qui ratione', + ticketDescription: + 'ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos', + Status: 'Pending', + Label: 'warning', + thumb: user1, + AgentName: 'Jack', + Date: chance.date(), + deleted: false, + }, + { + Id: 7, + ticketTitle: 'Sed ut perspiciatis unde omnis iste', + ticketDescription: + 'ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos', + Status: 'Open', + Label: 'success', + thumb: user2, + AgentName: 'Steve', + Date: chance.date(), + deleted: false, + }, + { + Id: 8, + ticketTitle: 'Consequuntur magni dolores eos qui ratione', + ticketDescription: + 'ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos', + Status: 'Closed', + Label: 'error', + thumb: user3, + AgentName: 'John', + Date: chance.date(), + deleted: false, + }, +]; + +mock.onGet('/api/data/ticket/TicketData').reply(() => { + return [200, TicketData]; +}); +export default TicketData; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/userprofile/PostData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/userprofile/PostData.ts new file mode 100644 index 0000000..8cef15c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/userprofile/PostData.ts @@ -0,0 +1,262 @@ +import mock from '../mock'; +import image1 from 'src/assets/images/products/s1.jpg'; +import image2 from 'src/assets/images/products/s2.jpg'; +import image4 from 'src/assets/images/products/s4.jpg'; + +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; +import user4 from 'src/assets/images/profile/user-4.jpg'; +import user5 from 'src/assets/images/profile/user-5.jpg'; +import user6 from 'src/assets/images/profile/user-1.jpg'; +import { Chance } from 'chance'; +import { PostType } from 'src/types/apps/userProfile'; + +const chance = new Chance(); + +// social profile +const posts: PostType[] = [ + { + id: chance.integer({ min: 1, max: 2000 }), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user1, + name: 'Mathew Anderson', + time: '15 min ago', + }, + data: { + content: chance.paragraph({ sentences: 2 }), + images: [ + { + img: image1, + featured: true, + }, + ], + likes: { + like: true, + value: 67, + }, + comments: [ + { + id: chance.integer({ min: 1, max: 2000 }), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user3, + name: 'Deran Mac', + time: '8 min ago ', + }, + data: { + comment: chance.paragraph({ sentences: 2 }), + likes: { + like: true, + value: 55, + }, + replies: [], + }, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user4, + name: 'Jonathan Bg', + time: '5 min ago ', + }, + data: { + comment: chance.paragraph({ sentences: 2 }), + likes: { + like: false, + value: 68, + }, + replies: [ + { + id: chance.integer({ min: 1, max: 2000 }), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user5, + name: 'Carry minati', + time: 'just now ', + }, + data: { + comment: chance.paragraph({ sentences: 2 }), + likes: { + like: true, + value: 10, + }, + }, + }, + ], + }, + }, + ], + }, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user5, + name: 'Carry Minati', + time: 'now', + }, + data: { + content: chance.paragraph({ sentences: 2 }), + images: [], + likes: { + like: true, + value: 1, + }, + comments: [], + }, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user2, + name: 'Genelia Desouza', + time: '15 min ago ', + }, + data: { + content: chance.paragraph({ sentences: 2 }), + images: [ + { + img: image2, + title: 'Image Title', + }, + { + img: image4, + title: 'Painter', + }, + ], + likes: { + like: false, + value: 320, + }, + comments: [ + { + id: chance.integer({ min: 1, max: 2000 }), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user3, + name: 'Ritesh Deshmukh', + time: '15 min ago ', + }, + data: { + comment: chance.paragraph({ sentences: 2 }), + likes: { + like: true, + value: 65, + }, + replies: [], + }, + }, + ], + }, + }, + { + id: chance.integer({ min: 1, max: 2000 }), + profile: { + id: chance.integer({ min: 1, max: 2000 }), + avatar: user6, + name: 'Mathew Anderson', + time: '15 min ago ', + }, + data: { + content: chance.paragraph({ sentences: 2 }), + images: [], + video: 'd1-FRj20WBE', + likes: { + like: true, + value: 129, + }, + }, + }, +]; + +mock.onGet('/api/data/postData').reply(() => { + return [200, posts]; +}); + +mock.onPost('/api/data/posts/like').reply((config) => { + try { + const { postId } = JSON.parse(config.data); + const postIndex = posts.findIndex((x) => x.id === postId); + const post = { ...posts[postIndex] }; + post.data = { ...post.data }; + post.data.likes = { ...post.data.likes }; + post.data.likes.like = !post.data.likes.like; + post.data.likes.value = post.data.likes.like + ? post.data.likes.value + 1 + : post.data.likes.value - 1; + posts[postIndex] = post; + + return [200, { posts: [...posts] }]; + } catch (err) { + console.error(err); + + return [500, { message: 'Internal server error' }]; + } +}); + +mock.onPost('/api/data/posts/comments/add').reply((config) => { + try { + const { postId, comment } = JSON.parse(config.data); + const postIndex = posts.findIndex((x) => x.id === postId); + const post = posts[postIndex]; + const cComments = post.data.comments || []; + post.data.comments = [...cComments, comment]; + + return [200, { posts: [...posts] }]; + } catch (err) { + console.error(err); + + return [500, { message: 'Internal server error' }]; + } +}); + +mock.onPost('/api/data/posts/replies/add').reply((config) => { + try { + const { postId, commentId, reply } = JSON.parse(config.data); + const postIndex = posts.findIndex((x) => x.id === postId); + const post = posts[postIndex]; + const cComments = post.data.comments || []; + const commentIndex = cComments.findIndex((x) => x.id === commentId); + const comment = cComments[commentIndex]; + if (comment && comment.data && comment.data.replies) + comment.data.replies = [...comment.data.replies, reply]; + + return [200, { posts: [...posts] }]; + } catch (err) { + console.error(err); + + return [500, { message: 'Internal server error' }]; + } +}); + +mock.onPost('/api/data/posts/replies/like').reply((config) => { + try { + const { postId, commentId } = JSON.parse(config.data); + const postIndex = posts.findIndex((x) => x.id === postId); + const post = posts[postIndex]; + const cComments = post.data.comments || []; + const commentIndex = cComments.findIndex((x) => x.id === commentId); + const comment = { ...cComments[commentIndex] }; + + if (comment && comment.data && comment.data.likes) + comment.data.likes.like = !comment.data.likes.like; + if (comment && comment.data && comment.data.likes) + comment.data.likes.value = comment.data.likes.like + ? comment.data.likes.value + 1 + : comment.data.likes.value - 1; + if (post && post.data && post.data.comments) post.data.comments[commentIndex] = comment; + + return [200, { posts: [...posts] }]; + } catch (err) { + console.error(err); + + return [500, { message: 'Internal server error' }]; + } +}); + +export default posts; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/userprofile/UsersData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/userprofile/UsersData.ts new file mode 100644 index 0000000..59d29ce --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/_mockApis/userprofile/UsersData.ts @@ -0,0 +1,276 @@ +import mock from '../mock'; +import { sub } from 'date-fns'; +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; +import user4 from 'src/assets/images/profile/user-4.jpg'; +import user5 from 'src/assets/images/profile/user-5.jpg'; +import user6 from 'src/assets/images/profile/user-6.jpg'; +import user7 from 'src/assets/images/profile/user-7.jpg'; +import user8 from 'src/assets/images/profile/user-8.jpg'; +import user9 from 'src/assets/images/profile/user-9.jpg'; +import user10 from 'src/assets/images/profile/user-10.jpg'; + +import s1 from 'src/assets/images/products/s1.jpg'; +import s2 from 'src/assets/images/products/s2.jpg'; +import s3 from 'src/assets/images/products/s3.jpg'; +import s4 from 'src/assets/images/products/s4.jpg'; +import s5 from 'src/assets/images/products/s5.jpg'; +import s6 from 'src/assets/images/products/s6.jpg'; +import s7 from 'src/assets/images/products/s7.jpg'; +import s8 from 'src/assets/images/products/s8.jpg'; +import s9 from 'src/assets/images/products/s9.jpg'; +import s10 from 'src/assets/images/products/s10.jpg'; +import s11 from 'src/assets/images/products/s11.jpg'; +import s12 from 'src/assets/images/products/s12.jpg'; +import { Chance } from 'chance'; +import { uniqueId } from 'lodash'; +import type { userType } from 'src/types/apps/users'; + +const chance = new Chance(); + +const users: userType[] = [ + { + id: uniqueId('#follow_'), + avatar: user1, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user2, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user3, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user4, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user5, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user6, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user7, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user8, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user9, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user10, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user1, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user2, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user3, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user4, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user5, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user6, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user7, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user8, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user9, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, + { + id: uniqueId('#follow_'), + avatar: user10, + name: chance.name(), + role: chance.profession(), + country: chance.country({ full: true }), + isFollowed: chance.bool(), + }, +]; + +const gallery = [ + { + id: uniqueId('#gallery_'), + cover: s1, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 8, hours: 6, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s2, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 8, hours: 4, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s3, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 8, hours: 3, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s4, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 8, hours: 2, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s5, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 8, hours: 1, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s6, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 7, hours: 6, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s7, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 6, hours: 6, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s8, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 5, hours: 6, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s9, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 4, hours: 6, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s10, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 3, hours: 6, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s11, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 2, hours: 6, minutes: 20 }), + }, + { + id: uniqueId('#gallery_'), + cover: s12, + name: chance.sentence({ words: 3 }), + time: sub(new Date(), { days: 1, hours: 6, minutes: 20 }), + }, +]; + +mock.onGet('/api/data/users').reply(() => { + return [200, users]; +}); + +mock.onGet('/api/data/gallery').reply(() => { + return [200, gallery]; +}); diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/bronze.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/bronze.png new file mode 100644 index 0000000..d0e5bfa Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/bronze.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/errorimg.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/errorimg.svg new file mode 100644 index 0000000..178f6b1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/errorimg.svg @@ -0,0 +1,44 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/gold.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/gold.png new file mode 100644 index 0000000..bdc7ede Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/gold.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/login-bg.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/login-bg.svg new file mode 100644 index 0000000..b5b43a4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/login-bg.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/maintenance.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/maintenance.svg new file mode 100644 index 0000000..ab81275 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/maintenance.svg @@ -0,0 +1,57 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/piggy.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/piggy.png new file mode 100644 index 0000000..c8dcbfd Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/piggy.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/profilebg.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/profilebg.jpg new file mode 100644 index 0000000..1b318aa Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/profilebg.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/silver.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/silver.png new file mode 100644 index 0000000..818e736 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/silver.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/track-bg.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/track-bg.png new file mode 100644 index 0000000..429ffee Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/track-bg.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/unlimited-bg.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/unlimited-bg.png new file mode 100644 index 0000000..501f5bb Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/unlimited-bg.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/welcome-bg.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/welcome-bg.svg new file mode 100644 index 0000000..266d921 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/welcome-bg.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/welcome-bg2.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/welcome-bg2.png new file mode 100644 index 0000000..9b9ea3c Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/backgrounds/welcome-bg2.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img1.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img1.jpg new file mode 100644 index 0000000..393391d Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img1.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img10.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img10.jpg new file mode 100644 index 0000000..f7df3d1 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img10.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img11.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img11.jpg new file mode 100644 index 0000000..4cc927e Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img11.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img2.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img2.jpg new file mode 100644 index 0000000..61ba89b Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img2.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img3.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img3.jpg new file mode 100644 index 0000000..3713c89 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img3.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img4.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img4.jpg new file mode 100644 index 0000000..ac2c76f Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img4.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img5.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img5.jpg new file mode 100644 index 0000000..f4b421d Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img5.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img6.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img6.jpg new file mode 100644 index 0000000..c34a46e Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img6.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img8.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img8.jpg new file mode 100644 index 0000000..b37c64d Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img8.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img9.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img9.jpg new file mode 100644 index 0000000..e59a50d Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/blog/blog-img9.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/breadcrumb/ChatBc.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/breadcrumb/ChatBc.png new file mode 100644 index 0000000..14823bd Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/breadcrumb/ChatBc.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/breadcrumb/emailSv.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/breadcrumb/emailSv.png new file mode 100644 index 0000000..72fea6f Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/breadcrumb/emailSv.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-adobe.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-adobe.svg new file mode 100644 index 0000000..1a9a798 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-adobe.svg @@ -0,0 +1,11 @@ + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-chrome.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-chrome.svg new file mode 100644 index 0000000..137149b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-chrome.svg @@ -0,0 +1,13 @@ + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-figma.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-figma.svg new file mode 100644 index 0000000..4af30a0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-figma.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-javascript.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-javascript.svg new file mode 100644 index 0000000..1b94f93 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-javascript.svg @@ -0,0 +1,11 @@ + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-zip-folder.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-zip-folder.svg new file mode 100644 index 0000000..b0c714a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/chat/icon-zip-folder.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-cn.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-cn.svg new file mode 100644 index 0000000..a1a7acb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-cn.svg @@ -0,0 +1,10 @@ + + + ic_flag_cn + + + + + + + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-en.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-en.svg new file mode 100644 index 0000000..485ad5c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-en.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-fr.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-fr.svg new file mode 100644 index 0000000..2ae63a1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-fr.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-sa.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-sa.svg new file mode 100644 index 0000000..4b5c2e6 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-sa.svg @@ -0,0 +1,10 @@ + + + ic_flag_sa + + + + + + + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-vn.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-vn.svg new file mode 100644 index 0000000..f4fd397 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/flag/icon-flag-vn.svg @@ -0,0 +1,10 @@ + + + ic_flag_vn + + + + + + + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/contact/map.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/contact/map.jpg new file mode 100644 index 0000000..e35a76f Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/contact/map.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/contact/shape1.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/contact/shape1.png new file mode 100644 index 0000000..9d60a61 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/contact/shape1.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/accordian1.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/accordian1.jpg new file mode 100644 index 0000000..d13def2 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/accordian1.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/banner-top-left.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/banner-top-left.svg new file mode 100644 index 0000000..02298fa --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/banner-top-left.svg @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/banner-top-left2.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/banner-top-left2.svg new file mode 100644 index 0000000..d08edfd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/banner-top-left2.svg @@ -0,0 +1,30 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/banner-top-right.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/banner-top-right.svg new file mode 100644 index 0000000..a2dab5d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/banner-top-right.svg @@ -0,0 +1,28 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/bottom-part.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/bottom-part.svg new file mode 100644 index 0000000..50a56ae --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/bottom-part.svg @@ -0,0 +1,18 @@ + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/design-collection.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/design-collection.png new file mode 100644 index 0000000..2886a14 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/design-collection.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/feature-apps.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/feature-apps.png new file mode 100644 index 0000000..fef18c5 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/feature-apps.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/icon-play.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/icon-play.svg new file mode 100644 index 0000000..2df536b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/icon-play.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/notification-left.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/notification-left.png new file mode 100644 index 0000000..beb7e3f Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/notification-left.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/notification-right.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/notification-right.png new file mode 100644 index 0000000..b90a1ce Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/notification-right.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/notification-top-right.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/notification-top-right.png new file mode 100644 index 0000000..ad24da4 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/notification-top-right.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/screen1.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/screen1.png new file mode 100644 index 0000000..afd642a Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/screen1.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user1.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user1.jpg new file mode 100644 index 0000000..eb505b5 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user1.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user2.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user2.jpg new file mode 100644 index 0000000..f8aa6af Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user2.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user3.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user3.jpg new file mode 100644 index 0000000..6478013 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user3.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user4.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user4.jpg new file mode 100644 index 0000000..e599b2a Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user4.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user5.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user5.jpg new file mode 100644 index 0000000..494e402 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/homepage/user5.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-chart.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-chart.svg new file mode 100644 index 0000000..eba41cf --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-chart.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-check.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-check.svg new file mode 100644 index 0000000..99a1a14 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-check.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-close.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-close.svg new file mode 100644 index 0000000..32e0a89 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-close.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-color.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-color.svg new file mode 100644 index 0000000..54f3e3f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-color.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-components.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-components.svg new file mode 100644 index 0000000..fea1eb6 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-components.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-customize.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-customize.svg new file mode 100644 index 0000000..d8e22cd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-customize.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-facebook.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-facebook.svg new file mode 100644 index 0000000..5b6e0bf --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-facebook.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-framework.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-framework.svg new file mode 100644 index 0000000..56b7149 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-framework.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-icons.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-icons.svg new file mode 100644 index 0000000..fd291f7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-icons.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-instagram.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-instagram.svg new file mode 100644 index 0000000..8233691 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-instagram.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-mui.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-mui.svg new file mode 100644 index 0000000..1d126b1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-mui.svg @@ -0,0 +1,3 @@ + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-next.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-next.svg new file mode 100644 index 0000000..d2fb657 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-next.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-pages.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-pages.svg new file mode 100644 index 0000000..a4a6c9d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-pages.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-react.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-react.svg new file mode 100644 index 0000000..652cf9f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-react.svg @@ -0,0 +1,13 @@ + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-redux.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-redux.svg new file mode 100644 index 0000000..dfebddb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-redux.svg @@ -0,0 +1,3 @@ + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-responsive.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-responsive.svg new file mode 100644 index 0000000..91c6a1e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-responsive.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-sass.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-sass.svg new file mode 100644 index 0000000..01b04cf --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-sass.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-sidebar.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-sidebar.svg new file mode 100644 index 0000000..0c75fe3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-sidebar.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-support.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-support.svg new file mode 100644 index 0000000..d490163 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-support.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-table.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-table.svg new file mode 100644 index 0000000..c62ca1c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-table.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-tabler.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-tabler.svg new file mode 100644 index 0000000..b8c0316 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-tabler.svg @@ -0,0 +1,3 @@ + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-ts.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-ts.svg new file mode 100644 index 0000000..759fb1a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-ts.svg @@ -0,0 +1,3 @@ + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-twitter.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-twitter.svg new file mode 100644 index 0000000..3c75e8d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-twitter.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-update.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-update.svg new file mode 100644 index 0000000..8174bbc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/icons/icon-update.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-american-express.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-american-express.svg new file mode 100644 index 0000000..a85d2c1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-american-express.svg @@ -0,0 +1,31 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-diners.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-diners.svg new file mode 100644 index 0000000..b8ed54a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-diners.svg @@ -0,0 +1,87 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-discover.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-discover.svg new file mode 100644 index 0000000..bc7f2a8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-discover.svg @@ -0,0 +1,38 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-jcb.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-jcb.svg new file mode 100644 index 0000000..1acd146 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-jcb.svg @@ -0,0 +1,46 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-masetro.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-masetro.svg new file mode 100644 index 0000000..05cad42 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-masetro.svg @@ -0,0 +1,29 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-mastercard.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-mastercard.svg new file mode 100644 index 0000000..da003c7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-mastercard.svg @@ -0,0 +1,33 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-paypal.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-paypal.svg new file mode 100644 index 0000000..031e9ba --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-paypal.svg @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-visa.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-visa.svg new file mode 100644 index 0000000..8c23323 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/frontend-pages/payments/icon-visa.svg @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-1.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-1.jpg new file mode 100644 index 0000000..c08ff5c Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-1.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-2.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-2.jpg new file mode 100644 index 0000000..c1b79bb Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-2.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-3.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-3.jpg new file mode 100644 index 0000000..0a44600 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-3.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-4.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-4.jpg new file mode 100644 index 0000000..9d89edd Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/kanban/kanban-img-4.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-blog-detail.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-blog-detail.jpg new file mode 100644 index 0000000..55d154f Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-blog-detail.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-blog.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-blog.jpg new file mode 100644 index 0000000..eb5bd21 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-blog.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-calendar.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-calendar.jpg new file mode 100644 index 0000000..69f3194 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-calendar.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-chat.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-chat.jpg new file mode 100644 index 0000000..8919532 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-chat.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-contact.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-contact.jpg new file mode 100644 index 0000000..a9d2acb Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-contact.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-checkout.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-checkout.jpg new file mode 100644 index 0000000..918ed33 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-checkout.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-detail.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-detail.jpg new file mode 100644 index 0000000..d0f97e1 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-detail.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-list.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-list.jpg new file mode 100644 index 0000000..ce00d73 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-list.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-shop.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-shop.jpg new file mode 100644 index 0000000..7e7911f Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ecommerce-shop.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-email.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-email.jpg new file mode 100644 index 0000000..45483d2 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-email.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-invoice.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-invoice.jpg new file mode 100644 index 0000000..0e98e16 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-invoice.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-kanban.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-kanban.jpg new file mode 100644 index 0000000..bc4d389 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-kanban.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-note.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-note.jpg new file mode 100644 index 0000000..9863705 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-note.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ticket.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ticket.jpg new file mode 100644 index 0000000..aa677d0 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-ticket.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-user-profile.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-user-profile.jpg new file mode 100644 index 0000000..2530cab Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/apps/app-user-profile.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/background/c2a.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/background/c2a.png new file mode 100644 index 0000000..6a3bb3b Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/background/c2a.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/background/slider-group.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/background/slider-group.png new file mode 100644 index 0000000..34c4096 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/background/slider-group.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/banner-bg.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/banner-bg.png new file mode 100644 index 0000000..87d2156 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/banner-bg.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/banner-img.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/banner-img.png new file mode 100644 index 0000000..1543ef3 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/banner-img.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/bannerimg1.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/bannerimg1.svg new file mode 100644 index 0000000..bf71033 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/bannerimg1.svg @@ -0,0 +1,162 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/bannerimg2.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/bannerimg2.svg new file mode 100644 index 0000000..f3f5b55 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/bannerimg2.svg @@ -0,0 +1,118 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-dark.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-dark.jpg new file mode 100644 index 0000000..b2eb48e Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-dark.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-firebase.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-firebase.jpg new file mode 100644 index 0000000..d983be7 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-firebase.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-horizontal.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-horizontal.jpg new file mode 100644 index 0000000..be0a733 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-horizontal.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-main.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-main.jpg new file mode 100644 index 0000000..7420d4b Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-main.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-rtl.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-rtl.jpg new file mode 100644 index 0000000..80672ae Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/demos/demo-rtl.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-about.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-about.jpg new file mode 100644 index 0000000..9a75fdd Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-about.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-homepage.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-homepage.jpg new file mode 100644 index 0000000..c8c4f0c Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-homepage.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-portfolio.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-portfolio.jpg new file mode 100644 index 0000000..fdf86e5 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-portfolio.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-pricing.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-pricing.jpg new file mode 100644 index 0000000..e3c6f49 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/f-pages/page-pricing.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/favicon.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/favicon.png new file mode 100644 index 0000000..80ba642 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/favicon.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-apex.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-apex.svg new file mode 100644 index 0000000..e26155e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-apex.svg @@ -0,0 +1,9 @@ + + New Project + + + + + + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-figma.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-figma.svg new file mode 100644 index 0000000..bd2fa74 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-figma.svg @@ -0,0 +1,9 @@ + + New Project + + + + + + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-js.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-js.svg new file mode 100644 index 0000000..4962da9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-js.svg @@ -0,0 +1,11 @@ + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-mui.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-mui.svg new file mode 100644 index 0000000..a3af858 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-mui.svg @@ -0,0 +1,13 @@ + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-react.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-react.svg new file mode 100644 index 0000000..2979308 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-react.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-redux.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-redux.svg new file mode 100644 index 0000000..674e961 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-redux.svg @@ -0,0 +1,3 @@ + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-ts.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-ts.svg new file mode 100644 index 0000000..7c0a72c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/frameworks/logo-ts.svg @@ -0,0 +1,12 @@ + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/testimonial1.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/testimonial1.png new file mode 100644 index 0000000..959e55b Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/testimonial1.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/testimonial2.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/testimonial2.png new file mode 100644 index 0000000..b332e26 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/testimonial2.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/testimonial3.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/testimonial3.png new file mode 100644 index 0000000..bd5aaa9 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/testimonial3.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/user1.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/user1.png new file mode 100644 index 0000000..fbed268 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/user1.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/user2.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/user2.png new file mode 100644 index 0000000..ade53d2 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/user2.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/user3.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/user3.png new file mode 100644 index 0000000..461d710 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/profile/user3.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/badge.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/badge.png new file mode 100644 index 0000000..50cd545 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/badge.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/badge.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/badge.svg new file mode 100644 index 0000000..7618272 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/badge.svg @@ -0,0 +1,3 @@ + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg-2.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg-2.png new file mode 100644 index 0000000..3009f41 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg-2.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg-2.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg-2.svg new file mode 100644 index 0000000..31f3168 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg-2.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg.png new file mode 100644 index 0000000..eb8e7f8 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg.svg new file mode 100644 index 0000000..01025a1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/line-bg.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-1.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-1.png new file mode 100644 index 0000000..423f3e7 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-1.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-1.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-1.svg new file mode 100644 index 0000000..cc8ccf0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-1.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-2.png b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-2.png new file mode 100644 index 0000000..eb22a82 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-2.png differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-2.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-2.svg new file mode 100644 index 0000000..c55bce0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/landingpage/shape/shape-2.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/dark-logo.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/dark-logo.svg new file mode 100644 index 0000000..f7cdd12 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/dark-logo.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/dark-rtl-logo.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/dark-rtl-logo.svg new file mode 100644 index 0000000..f7d0102 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/dark-rtl-logo.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/light-logo-rtl.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/light-logo-rtl.svg new file mode 100644 index 0000000..b6e8f0c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/light-logo-rtl.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/light-logo.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/light-logo.svg new file mode 100644 index 0000000..adf4ecb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/light-logo.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/logoIcon.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/logoIcon.svg new file mode 100644 index 0000000..8c5e0df --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/logos/logoIcon.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/empty-shopping-cart.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/empty-shopping-cart.svg new file mode 100644 index 0000000..dfe6f20 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/empty-shopping-cart.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/payment-complete.gif b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/payment-complete.gif new file mode 100644 index 0000000..05b78d8 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/payment-complete.gif differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/payment.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/payment.svg new file mode 100644 index 0000000..1304019 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/payment.svg @@ -0,0 +1,1085 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-1.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-1.jpg new file mode 100644 index 0000000..32e1a5c Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-1.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-2.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-2.jpg new file mode 100644 index 0000000..2601e45 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-2.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-3.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-3.jpg new file mode 100644 index 0000000..bb202c3 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-3.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-4.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-4.jpg new file mode 100644 index 0000000..e13e01c Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/product-4.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s1.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s1.jpg new file mode 100644 index 0000000..144d0e8 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s1.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s10.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s10.jpg new file mode 100644 index 0000000..cf64bc3 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s10.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s11.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s11.jpg new file mode 100644 index 0000000..8980089 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s11.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s12.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s12.jpg new file mode 100644 index 0000000..88a6dbc Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s12.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s2.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s2.jpg new file mode 100644 index 0000000..9bc8e62 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s2.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s3.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s3.jpg new file mode 100644 index 0000000..6413e06 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s3.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s4.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s4.jpg new file mode 100644 index 0000000..803e397 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s4.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s5.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s5.jpg new file mode 100644 index 0000000..c40751b Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s5.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s6.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s6.jpg new file mode 100644 index 0000000..3ca15a9 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s6.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s7.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s7.jpg new file mode 100644 index 0000000..d819743 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s7.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s8.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s8.jpg new file mode 100644 index 0000000..ba04626 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s8.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s9.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s9.jpg new file mode 100644 index 0000000..18c7623 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/products/s9.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-1.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-1.jpg new file mode 100644 index 0000000..e19df67 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-1.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-10.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-10.jpg new file mode 100644 index 0000000..7d4531f Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-10.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-2.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-2.jpg new file mode 100644 index 0000000..52d8f1f Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-2.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-3.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-3.jpg new file mode 100644 index 0000000..2a541d7 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-3.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-4.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-4.jpg new file mode 100644 index 0000000..e9312df Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-4.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-5.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-5.jpg new file mode 100644 index 0000000..ff2e6f0 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-5.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-6.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-6.jpg new file mode 100644 index 0000000..867b150 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-6.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-7.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-7.jpg new file mode 100644 index 0000000..df8e3fb Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-7.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-8.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-8.jpg new file mode 100644 index 0000000..facea41 Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-8.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-9.jpg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-9.jpg new file mode 100644 index 0000000..9de110f Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/profile/user-9.jpg differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/cart-icon.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/cart-icon.svg new file mode 100644 index 0000000..faed879 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/cart-icon.svg @@ -0,0 +1,13 @@ + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/facebook-icon.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/facebook-icon.svg new file mode 100644 index 0000000..c24d6ba --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/facebook-icon.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/google-icon.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/google-icon.svg new file mode 100644 index 0000000..4675691 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/google-icon.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-account.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-account.svg new file mode 100644 index 0000000..4ab551a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-account.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-bars.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-bars.svg new file mode 100644 index 0000000..4d4afce --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-bars.svg @@ -0,0 +1,13 @@ + + + + + + + + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-briefcase.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-briefcase.svg new file mode 100644 index 0000000..6bbd6d4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-briefcase.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-connect.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-connect.svg new file mode 100644 index 0000000..0adb3ea --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-connect.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-application.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-application.svg new file mode 100644 index 0000000..57ecf88 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-application.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-cart.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-cart.svg new file mode 100644 index 0000000..16a44b6 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-cart.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-chat.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-chat.svg new file mode 100644 index 0000000..77a31cd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-chat.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-date.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-date.svg new file mode 100644 index 0000000..be64c30 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-date.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-invoice.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-invoice.svg new file mode 100644 index 0000000..9bec7ae --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-invoice.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-lifebuoy.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-lifebuoy.svg new file mode 100644 index 0000000..37e24dd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-lifebuoy.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-message-box.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-message-box.svg new file mode 100644 index 0000000..98ed5fc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-message-box.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-mobile.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-mobile.svg new file mode 100644 index 0000000..e43bd42 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-dd-mobile.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-favorites.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-favorites.svg new file mode 100644 index 0000000..84fedaa --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-favorites.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-inbox.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-inbox.svg new file mode 100644 index 0000000..889187b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-inbox.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-mailbox.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-mailbox.svg new file mode 100644 index 0000000..a4a3aa3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-mailbox.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-master-card-2.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-master-card-2.svg new file mode 100644 index 0000000..cc90255 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-master-card-2.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-master-card.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-master-card.svg new file mode 100644 index 0000000..8eee2da --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-master-card.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-office-bag-2.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-office-bag-2.svg new file mode 100644 index 0000000..06b24c8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-office-bag-2.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-office-bag.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-office-bag.svg new file mode 100644 index 0000000..470a34d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-office-bag.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-paypal.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-paypal.svg new file mode 100644 index 0000000..1828703 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-paypal.svg @@ -0,0 +1,4 @@ + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-pie.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-pie.svg new file mode 100644 index 0000000..f79ca56 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-pie.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-speech-bubble.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-speech-bubble.svg new file mode 100644 index 0000000..2e1f2bd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-speech-bubble.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-tasks.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-tasks.svg new file mode 100644 index 0000000..d645cdd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-tasks.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-user-male.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-user-male.svg new file mode 100644 index 0000000..2832c4f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/icon-user-male.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/mastercard.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/mastercard.svg new file mode 100644 index 0000000..3fdc683 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/mastercard.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/no-data.webp b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/no-data.webp new file mode 100644 index 0000000..efda6cb Binary files /dev/null and b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/no-data.webp differ diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/paypal.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/paypal.svg new file mode 100644 index 0000000..41e02d5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/images/svgs/paypal.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/assets/react.svg b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/react.svg new file mode 100644 index 0000000..6c87de9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/assets/react.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/BlogCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/BlogCard.tsx new file mode 100644 index 0000000..dfc032e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/BlogCard.tsx @@ -0,0 +1,126 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; + +// third-party +import { format } from 'date-fns'; +import { Link } from 'react-router'; +import { useDispatch } from 'src/store/Store'; +import { + CardContent, + Stack, + Avatar, + Typography, + CardMedia, + Chip, + Grid2 as Grid, + Tooltip, + Box, + Skeleton +} from '@mui/material'; +import { IconEye, IconMessage2, IconPoint } from '@tabler/icons-react'; +import { fetchBlogPost } from 'src/store/apps/blog/BlogSlice'; +import BlankCard from '../../shared/BlankCard'; +import { BlogPostType } from 'src/types/apps/blog'; + +interface Btype { + post: BlogPostType; + index?: number; +} + +const BlogCard = ({ post }: Btype) => { + const dispatch = useDispatch(); + const { coverImg, title, view, comments, category, author, createdAt }: any = post; + const linkTo = title + .toLowerCase() + .replace(/ /g, '-') + .replace(/[^\w-]+/g, ''); + + // skeleton + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 700); + + return () => clearTimeout(timer); + }, []); + + return ( + ( + {isLoading ? ( + <> + theme.shape.borderRadius / 5 }} + > + + ) : ( + + <> + dispatch(fetchBlogPost(linkTo))} + > + + + + + + + + theme.palette.mode === 'dark' ? theme.palette.background.default : 'white', }} + label="2 min Read" + size="small" + > + + + + dispatch(fetchBlogPost(linkTo))} + > + {title} + + + + + {view} + + + {comments?.length} + + + + + {format(new Date(createdAt), 'E, MMM d')} + + + + + + )} + ) + ); +}; + +export default BlogCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/BlogFeaturedCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/BlogFeaturedCard.tsx new file mode 100644 index 0000000..bb980fb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/BlogFeaturedCard.tsx @@ -0,0 +1,168 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { Link } from 'react-router'; +import { useDispatch } from 'src/store/Store'; +import { + CardContent, + Stack, + Avatar, + Typography, + Chip, + Grid2 as Grid, + Tooltip, + Box, + alpha, + styled, + Skeleton +} from '@mui/material'; +import { IconEye, IconMessage2, IconPoint } from '@tabler/icons-react'; +import { format } from 'date-fns'; +import { fetchBlogPost } from 'src/store/apps/blog/BlogSlice'; +import BlankCard from '../../shared/BlankCard'; +import { BlogPostType } from 'src/types/apps/blog'; + +const CoverImgStyle = styled(CardContent)({ + position: 'absolute', + top: '0', + left: '0', + zIndex: 1, + width: '100%', + height: '100%', + color: 'white', +}); +const CoverBox = styled(Box)({ + top: 0, + content: "''", + width: '100%', + height: '100%', + position: 'absolute', +}); + +interface Btype { + post: BlogPostType; + index: number; +} + +const BlogFeaturedCard = ({ post, index }: Btype) => { + const dispatch = useDispatch(); + const { coverImg, title, view, comments, category, author, createdAt }: any = post; + const linkTo = title + .toLowerCase() + .replace(/ /g, '-') + .replace(/[^\w-]+/g, ''); + const mainPost = index === 0; + + const CoverImgBg = styled(BlankCard)({ + p: 0, + height: '400px', + position: 'relative', + background: `url(${coverImg}) no-repeat center`, + backgroundSize: 'cover', + }); + + // skeleton + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 700); + + return () => clearTimeout(timer); + }, []); + + return (<> + {post ? ( + + {isLoading ? ( + <> + theme.shape.borderRadius / 5 }} + > + + ) : ( + + <> + dispatch(fetchBlogPost(linkTo))} + > + alpha(theme.palette.grey[900], 0.6) }} + /> + + + + + + + + + + + + + + dispatch(fetchBlogPost(linkTo))} + > + {title} + + + + + {view} + + + {comments?.length} + + + + + {format(new Date(createdAt), 'E, MMM d')} + + + + + + + + )} + + ) : ( + '' + )} + ); +}; + +export default BlogFeaturedCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/BlogListing.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/BlogListing.tsx new file mode 100644 index 0000000..132c00b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/BlogListing.tsx @@ -0,0 +1,72 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { Grid2 as Grid, Pagination } from '@mui/material'; +import BlogCard from './BlogCard'; +import { orderBy } from 'lodash'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { fetchBlogPosts } from 'src/store/apps/blog/BlogSlice'; +import BlogFeaturedCard from './BlogFeaturedCard'; +import { BlogPostType } from 'src/types/apps/blog'; + +const BlogListing = () => { + const dispatch = useDispatch(); + + useEffect(() => { + dispatch(fetchBlogPosts()); + }, [dispatch]); + + // eslint-disable-next-line @typescript-eslint/no-unused-vars + const filterBlogs = (posts: BlogPostType[], sortBy: string, _cSearch: string) => { + // SORT BY + + if (sortBy === 'newest') { + posts = orderBy(posts, ['createdAt'], ['desc']); + } + if (sortBy === 'oldest') { + posts = orderBy(posts, ['createdAt'], ['asc']); + } + if (sortBy === 'popular') { + posts = orderBy(posts, ['view'], ['desc']); + } + if (posts) { + return (posts = posts.filter((t) => t.featured === false)); + } + + return posts; + }; + + const filterFeaturedpost = (posts: BlogPostType[]) => { + return (posts = posts.filter((t) => t.featured)); + }; + + const blogPosts = useSelector((state) => + filterBlogs( + state.blogReducer.blogposts, + state.blogReducer.sortBy, + state.blogReducer.blogSearch, + ), + ); + const featuredPost = useSelector((state) => filterFeaturedpost(state.blogReducer.blogposts)); + + return ( + ( + {featuredPost.map((post, index) => { + return ; + })} + {blogPosts.map((post) => { + return ; + })} + + + + ) + ); +}; + +export default BlogListing; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/detail/BlogComment.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/detail/BlogComment.tsx new file mode 100644 index 0000000..b9d95f7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/detail/BlogComment.tsx @@ -0,0 +1,83 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Stack, Avatar, Box, Typography, Tooltip, Fab, TextField, Button } from '@mui/material'; +import { IconArrowBackUp, IconCircle } from '@tabler/icons-react'; +import { BlogType } from 'src/types/apps/blog'; + +const BlogComment = ({ comment }: BlogType | any) => { + const [showReply, setShowReply] = React.useState(false); + + return ( + <> + + + + {comment?.profile.name} + + <> + {' '} + {comment?.profile.time} + + + + + {comment?.comment} + + + + setShowReply(!showReply)}> + + + + + + {comment?.replies ? ( + <> + {comment?.replies.map((reply: BlogType | any) => { + return ( + + + + + {reply.profile.name} + + {' '} + {reply.profile.time} + + + + {reply.comment} + + + + ); + })} + + ) : ( + '' + )} + {showReply ? ( + + + + + + + + ) : ( + '' + )} + + ); +}; + +export default BlogComment; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/detail/BlogDetail.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/detail/BlogDetail.tsx new file mode 100644 index 0000000..9db7678 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/blog/detail/BlogDetail.tsx @@ -0,0 +1,230 @@ +/* eslint-disable react-hooks/exhaustive-deps */ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { fetchBlogPost } from 'src/store/apps/blog/BlogSlice'; +import { useLocation } from 'react-router'; +import { + CardContent, + Stack, + Avatar, + Typography, + CardMedia, + Chip, + Tooltip, + Box, + Divider, + TextField, + Button, + Skeleton, +} from '@mui/material'; +import { IconEye, IconMessage2, IconPoint, IconQuote } from '@tabler/icons-react'; +import { format } from 'date-fns'; +import BlogComment from './BlogComment'; +import { uniqueId } from 'lodash'; +import { addComment } from 'src/store/apps/blog/BlogSlice'; +import BlankCard from '../../../shared/BlankCard'; +import { AppState, useDispatch, useSelector } from 'src/store/Store'; +import type { BlogPostType, BlogType } from 'src/types/apps/blog'; + +const BlogDetail = () => { + const dispatch = useDispatch(); + const title = useLocation(); + const getTitle: any = title.pathname.split('/').pop(); + const [replyTxt, setReplyTxt] = React.useState(''); + + useEffect(() => { + dispatch(fetchBlogPost(getTitle)); + }, [dispatch]); + + // Get post + const post: BlogPostType | any = useSelector((state: AppState) => state.blogReducer.selectedPost); + + const onSubmit = async (id: number, reply: string) => { + const replyId: string = uniqueId('#comm_'); + const newReply = { + id: replyId, + profile: { + id: uniqueId('#REPLY_'), + avatar: post?.author.avatar, + name: post?.author.name, + time: 'now', + }, + comment: reply, + replies: [], + }; + dispatch(addComment(id, newReply)); + dispatch(fetchBlogPost(getTitle)); + setReplyTxt(''); + }; + + // skeleton + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 700); + + return () => clearTimeout(timer); + }, []); + + return ( + + + <> + {isLoading ? ( + <> + theme.shape.borderRadius / 5 }} + > + + ) : ( + + )} + + + + + + + theme.palette.mode === 'dark' ? theme.palette.background.default : 'white', + }} + label="2 min Read" + size="small" + > + + + + + {post?.title} + + + + + {post?.view} + + + {post?.comments.length} + + + + + {post ? <>{format(new Date(post.createdAt), 'E, MMM d')} : ''} + + + + + + Title of the paragraph +

+ But you cannot figure out what it is or what it can do. MTA web directory is the + simplest way in which one can bid on a link, or a few links if they wish to do so. The + link directory on MTA displays all of the links it currently has, and does so in + alphabetical order, which makes it much easier for someone to find what they are + looking for if it is something specific and they do not want to go through all the + other sites and links as well. It allows you to start your bid at the bottom and + slowly work your way to the top of the list. +

+

+ Gigure out what it is or what it can do. MTA web directory is the simplest way in + which one can bid on a link, or a few links if they wish to do so. The link directory + on MTA displays all of the links it currently has, and does so in alphabetical order, + which makes it much easier for someone to find what they are looking for if it is + something specific and they do not want to go through all the other sites and links as + well. It allows you to start your bid at the bottom and slowly work your way to the + top of the +

+ This is strong text. + This is italic text. + + + + Unorder list. +
    +
  • Gigure out what it is or
  • +
  • The links it currently
  • +
  • It allows you to start your bid
  • +
  • Gigure out what it is or
  • +
  • The links it currently
  • +
  • It allows you to start your bid
  • +
+ + + + Order list. +
    +
  1. Gigure out what it is or
  2. +
  3. The links it currently
  4. +
  5. It allows you to start your bid
  6. +
  7. Gigure out what it is or
  8. +
  9. The links it currently
  10. +
  11. It allows you to start your bid
  12. +
+ + + + Quotes + + + Life is short, Smile while you still have teeth! + + +
+ +
+ + + + Post Comments + +
+ setReplyTxt(e.target.value)} + > +
+
+ + + + + Comments + + + + {post?.comments.length} + + + + + {post?.comments?.map((comment: BlogType | any) => { + return ; + })} + +
+
+
+ ); +}; + +export default BlogDetail; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatContent.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatContent.tsx new file mode 100644 index 0000000..5f169db --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatContent.tsx @@ -0,0 +1,221 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Typography, + Divider, + Avatar, + ListItem, + ListItemText, + ListItemAvatar, + IconButton, + Box, + Stack, + Badge, + useMediaQuery, + Theme +} from '@mui/material'; +import { IconDotsVertical, IconMenu2, IconPhone, IconVideo } from '@tabler/icons-react'; +import { useSelector } from 'src/store/Store'; + +import { ChatsType } from 'src/types/apps/chat'; +import { formatDistanceToNowStrict } from 'date-fns'; +import ChatInsideSidebar from './ChatInsideSidebar'; +import Scrollbar from 'src/components/custom-scroll/Scrollbar'; + + +interface ChatContentProps { + toggleChatSidebar: () => void; +} + + const ChatContent: React.FC = ({ toggleChatSidebar }) => { + const [open, setOpen] = React.useState(true); + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + + const chatDetails: ChatsType = useSelector( + (state) => state.chatReducer.chats[state.chatReducer.chatContent - 1], + ); + + return ( + + {chatDetails ? ( + + {/* ------------------------------------------- */} + {/* Header Part */} + {/* ------------------------------------------- */} + + + + + + + + + + + + {chatDetails.name}} + secondary={chatDetails.status} + /> + + + + + + + + + setOpen(!open)}> + + + + + + + {/* ------------------------------------------- */} + {/* Chat Content */} + {/* ------------------------------------------- */} + + + {/* ------------------------------------------- */} + {/* Chat msges */} + {/* ------------------------------------------- */} + + + + + {chatDetails.messages.map((chat) => { + return ( + + {chatDetails.id === chat.senderId ? ( + <> + + + + + + {chat.createdAt ? ( + + {chatDetails.name},{' '} + {formatDistanceToNowStrict(new Date(chat.createdAt), { + addSuffix: false, + })}{' '} + ago + + ) : null} + {chat.type === 'text' ? ( + + {chat.msg} + + ) : null} + {chat.type === 'image' ? ( + + attach + + ) : null} + + + + ) : ( + + + {chat.createdAt ? ( + + ago + + ) : null} + {chat.type === 'text' ? ( + + {chat.msg} + + ) : null} + {chat.type === 'image' ? ( + + attach + + ) : null} + + + )} + + ); + })} + + + + + {/* ------------------------------------------- */} + {/* Chat right sidebar Content */} + {/* ------------------------------------------- */} + + + + ) : ( + + {/* ------------------------------------------- */} + {/* if No Chat Content */} + {/* ------------------------------------------- */} + + + + Select Chat + + )} + + ); +}; + +export default ChatContent; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatInsideSidebar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatInsideSidebar.tsx new file mode 100644 index 0000000..7c3b901 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatInsideSidebar.tsx @@ -0,0 +1,143 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Box, + Theme, + useMediaQuery, + Typography, + Stack, + Avatar, + Grid2 as Grid, + Alert, + IconButton, + styled, +} from '@mui/material'; +import { ChatsType } from 'src/types/apps/chat'; +import { uniq, flatten } from 'lodash'; +import { IconDownload } from '@tabler/icons-react'; + +interface chatType { + isInSidebar?: boolean; + chat?: ChatsType; +} + +const drawerWidth = 320; + +const ChatInsideSidebar = ({ isInSidebar, chat }: chatType) => { + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + const totalAttachment = uniq(flatten(chat?.messages.map((item) => item.attachment))).length; + const totalMedia = + uniq(flatten(chat?.messages.map((item) => (item?.type === 'image' ? item.msg : null)))).length - + 1; + + const StyledStack = styled(Stack)(() => ({ + '.showOnHover': { + display: 'none', + }, + '&:hover .showOnHover': { + display: 'block', + }, + })); + + return (<> + {isInSidebar ? ( + theme.palette.background.paper, + boxShadow: lgUp ? null : (theme) => theme.shadows[8], + position: lgUp ? 'relative' : 'absolute', + borderColor: (theme) => theme.palette.divider, + }} + p={3} + > + + Media ({totalMedia}) + + + {chat?.messages.map((c) => { + return ( + ( + {c?.type === 'image' ? ( + + ) : ( + '' + )} + ) + ); + })} + + {totalMedia === 0 ? No Media Found! : null} + + + + + Attachments ({totalAttachment}) + + + {chat?.messages.map((c, index) => { + return ( + + {c?.attachment?.map((a, index) => { + return ( + + theme.palette.grey[100], + }} + > + + + + + {a.file} + + {a.fileSize} + + + + + + + + ); + })} + + ); + })} + {totalAttachment === 0 ? No Attachment Found! : null} + + + ) : null} + ); +}; + +export default ChatInsideSidebar; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatListing.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatListing.tsx new file mode 100644 index 0000000..ece3eef --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatListing.tsx @@ -0,0 +1,215 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { + Avatar, + List, + ListItemText, + ListItemAvatar, + TextField, + Box, + Alert, + Badge, + ListItemButton, + Typography, + InputAdornment, + Button, + Menu, + MenuItem, +} from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import Scrollbar from '../../custom-scroll/Scrollbar'; +import { SelectChat, fetchChats, SearchChat } from '../../../store/apps/chat/ChatSlice'; +import { ChatsType } from 'src/types/apps/chat'; +import { last } from 'lodash'; +import { formatDistanceToNowStrict } from 'date-fns'; +import { IconChevronDown, IconSearch } from '@tabler/icons-react'; +import user1 from 'src/assets/images/profile/user-1.jpg'; + +const ChatListing = () => { + const dispatch = useDispatch(); + const activeChat = useSelector((state) => state.chatReducer.chatContent); + + useEffect(() => { + dispatch(fetchChats()); + }, [dispatch]); + + const filterChats = (chats: ChatsType[], cSearch: string) => { + if (chats) + return chats.filter((t) => t.name.toLocaleLowerCase().includes(cSearch.toLocaleLowerCase())); + + return chats; + }; + + const chats = useSelector((state) => + filterChats(state.chatReducer.chats, state.chatReducer.chatSearch), + ); + + const getDetails = (conversation: ChatsType) => { + let displayText = ''; + + const lastMessage = conversation.messages[conversation.messages.length - 1]; + if (lastMessage) { + const sender = lastMessage.senderId === conversation.id ? 'You: ' : ''; + const message = lastMessage.type === 'image' ? 'Sent a photo' : lastMessage.msg; + displayText = `${sender}${message}`; + } + + return displayText; + }; + + const lastActivity = (chat: ChatsType) => last(chat.messages)?.createdAt; + + const [anchorEl, setAnchorEl] = React.useState(null); + const open = Boolean(anchorEl); + const handleClick = (event: React.MouseEvent) => { + setAnchorEl(event.currentTarget); + }; + const handleClose = () => { + setAnchorEl(null); + }; + + return ( +
+ {/* ------------------------------------------- */} + {/* Profile */} + {/* ------------------------------------------- */} + + + + + + + John Deo + + Marketing Manager + + + {/* ------------------------------------------- */} + {/* Search */} + {/* ------------------------------------------- */} + + + + + ), + }} + fullWidth + onChange={(e) => dispatch(SearchChat(e.target.value))} + /> + + {/* ------------------------------------------- */} + {/* Contact List */} + {/* ------------------------------------------- */} + + + + + Sort By Time + Sort By Unread + Mark as all Read + + + + {chats && chats.length ? ( + chats.map((chat) => ( + dispatch(SelectChat(chat.id))} + sx={{ + mb: 0.5, + py: 2, + px: 3, + alignItems: 'start', + }} + selected={activeChat === chat.id} + > + + + + + + + {chat.name} + + } + secondary={getDetails(chat)} + secondaryTypographyProps={{ + noWrap: true, + }} + sx={{ my: 0 }} + /> + + + {formatDistanceToNowStrict(new Date(lastActivity(chat)), { + addSuffix: false, + })} + + + + )) + ) : ( + + + No Contacts Found! + + + )} + + +
+ ); +}; + +export default ChatListing; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatMsgSent.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatMsgSent.tsx new file mode 100644 index 0000000..009d66d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatMsgSent.tsx @@ -0,0 +1,83 @@ +import React from "react"; +import { useSelector, useDispatch } from 'src/store/Store'; +import Box from "@mui/material/Box"; +import IconButton from "@mui/material/IconButton"; +import InputBase from "@mui/material/InputBase"; + +import { + IconPaperclip, + IconPhoto, + IconSend, +} from "@tabler/icons-react"; +import { sendMsg } from "src/store/apps/chat/ChatSlice"; + +const ChatMsgSent = () => { + const [msg, setMsg] = React.useState(""); + const dispatch = useDispatch(); + + + + + + + const id = useSelector((state: any) => state.chatReducer.chatContent); + + const handleChatMsgChange = (e: React.ChangeEvent) => { + setMsg(e.target.value); + }; + + const newMsg = { id, msg }; + + const onChatMsgSubmit = (e: any) => { + e.preventDefault(); + e.stopPropagation(); + dispatch(sendMsg(newMsg)); + setMsg(""); + }; + + return ( + + {/* ------------------------------------------- */} + {/* sent chat */} + {/* ------------------------------------------- */} +
+ {/* ------------------------------------------- */} + {/* Emoji picker */} + {/* ------------------------------------------- */} + + + { + dispatch(sendMsg(newMsg)); + setMsg(""); + }} + disabled={!msg} + color="primary" + > + + + + + + + + + +
+ ); +}; + +export default ChatMsgSent; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatSidebar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatSidebar.tsx new file mode 100644 index 0000000..52a04f9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/chats/ChatSidebar.tsx @@ -0,0 +1,34 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Drawer, Theme, useMediaQuery } from '@mui/material'; +import ChatListing from './ChatListing'; + +interface chatType { + isMobileSidebarOpen: boolean; + onSidebarClose: (event: React.MouseEvent) => void; +} + +const drawerWidth = 320; + +const ChatSidebar = ({ isMobileSidebarOpen, onSidebarClose }: chatType) => { + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + + return ( + + + + ); +}; + +export default ChatSidebar; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactAdd.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactAdd.tsx new file mode 100644 index 0000000..10f3297 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactAdd.tsx @@ -0,0 +1,234 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Box, + Button, + Dialog, + DialogTitle, + TextField, + FormLabel, + DialogContent, + DialogContentText, + Grid2 as Grid, +} from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { addContact } from '../../../store/apps/contacts/ContactSlice'; +import user1 from '../../../assets/images/profile/user-1.jpg'; + +const ContactAdd = () => { + const dispatch = useDispatch(); + const id = useSelector((state) => state.contactsReducer.contacts.length + 1); + const [modal, setModal] = React.useState(false); + + const toggle = () => { + setModal(!modal); + }; + + const [values, setValues] = React.useState({ + firstname: '', + lastname: '', + department: '', + company: '', + phone: '', + email: '', + address: '', + notes: '', + }); + + const handleSubmit = (e: any) => { + e.preventDefault(); + dispatch( + addContact( + id, + values.firstname, + values.lastname, + user1, + values.department, + values.company, + values.phone, + values.email, + values.address, + values.notes, + ), + ); + setModal(!modal); + }; + + return (<> + + + + + + {'Add New Contact'} + + + + Lets add new contact for your application. fill the all field and +
click on submit button. +
+ +
+ + + FirstName + setValues({ ...values, firstname: e.target.value })} + /> + + + LastName + setValues({ ...values, lastname: e.target.value })} + /> + + + Department + setValues({ ...values, department: e.target.value })} + /> + + + Company + setValues({ ...values, company: e.target.value })} + /> + + + Phone + setValues({ ...values, phone: e.target.value })} + /> + + + Email + setValues({ ...values, email: e.target.value })} + /> + + + Address + setValues({ ...values, address: e.target.value })} + /> + + + Notes + setValues({ ...values, notes: e.target.value })} + /> + + + + + + +
+
+
+
+ ); +}; + +export default ContactAdd; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactDetails.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactDetails.tsx new file mode 100644 index 0000000..06e135a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactDetails.tsx @@ -0,0 +1,319 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { + Box, + Button, + TextField, + Typography, + Avatar, + Divider, + IconButton, + Stack, + Grid2 as Grid, + Tooltip, + useTheme +} from '@mui/material'; +import { + isEdit, + UpdateContact, + DeleteContact, + toggleStarredContact, +} from 'src/store/apps/contacts/ContactSlice'; +import BlankCard from '../../shared/BlankCard'; +import { ContactType } from 'src/types/apps/contact'; +import { IconPencil, IconStar, IconTrash, IconDeviceFloppy } from '@tabler/icons-react'; +import Scrollbar from 'src/components/custom-scroll/Scrollbar'; +import emailIcon from 'src/assets/images/breadcrumb/emailSv.png'; + +const ContactDetails = () => { + const contactDetail: ContactType = useSelector( + (state) => state.contactsReducer.contacts[state.contactsReducer.contactContent - 1], + ); + const editContact = useSelector((state) => state.contactsReducer.editContact); + const dispatch = useDispatch(); + const theme = useTheme(); + + const warningColor = theme.palette.warning.main; + + const tableData = [ + { + id: 1, + title: 'Firstname', + alias: 'firstname', + gdata: contactDetail ? contactDetail.firstname : '', + type: 'text', + }, + { + id: 2, + title: 'Lastname', + alias: 'lastname', + gdata: contactDetail ? contactDetail.lastname : '', + type: 'text', + }, + { + id: 3, + title: 'Company', + alias: 'company', + gdata: contactDetail ? contactDetail.company : '', + type: 'text', + }, + { + id: 4, + title: 'Department', + alias: 'department', + gdata: contactDetail ? contactDetail.department : '', + type: 'text', + }, + { + id: 5, + title: 'Email', + alias: 'email', + gdata: contactDetail ? contactDetail.email : '', + type: 'email', + }, + { + id: 6, + title: 'Phone', + alias: 'phone', + gdata: contactDetail ? contactDetail.phone : '', + type: 'phone', + }, + { + id: 7, + title: 'Address', + alias: 'address', + gdata: contactDetail ? contactDetail.address : '', + type: 'text', + }, + { + id: 8, + title: 'Notes', + alias: 'notes', + gdata: contactDetail ? contactDetail.notes : '', + type: 'text', + }, + ]; + + return (<> + {/* ------------------------------------------- */} + {/* Contact Detail Part */} + {/* ------------------------------------------- */} + {contactDetail && !contactDetail.deleted ? ( + <> + {/* ------------------------------------------- */} + {/* Header Part */} + {/* ------------------------------------------- */} + + Contact Details + + + dispatch(toggleStarredContact(contactDetail.id))}> + + + + + dispatch(isEdit())}> + {!editContact ? ( + + ) : ( + + )} + + + + dispatch(DeleteContact(contactDetail.id))}> + + + + + + + {/* ------------------------------------------- */} + {/* Contact Table Part */} + {/* ------------------------------------------- */} + + {!editContact ? ( + + + + + + + {contactDetail.firstname} {contactDetail.lastname} + + + {contactDetail.department} + + + {contactDetail.company} + + + + + + + Phone Number + + + {contactDetail.phone} + + + + + Email address + + + {contactDetail.email} + + + + + Address + + + {contactDetail.address} + + + + + Department + + + {contactDetail.department} + + + + + Company + + + {contactDetail.company} + + + + + Notes + + + {contactDetail.notes} + + + + + + + + + + + ) : ( + <> + + + + {tableData.map((data) => ( + + + {data.title} + + + dispatch(UpdateContact(contactDetail.id, data.alias, e.target.value)) + } + /> + + ))} + + + + + + + + )} + + + ) : ( + + {/* ------------------------------------------- */} + {/* If no Contact */} + {/* ------------------------------------------- */} + + Please Select a Contact +
+ {emailIcon} +
+
+ )} + ); +}; + +export default ContactDetails; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactFilter.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactFilter.tsx new file mode 100644 index 0000000..b03a5b8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactFilter.tsx @@ -0,0 +1,128 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useDispatch, useSelector } from 'src/store/Store'; +import { + ListItemText, + ListItemButton, + List, + Divider, + ListItemIcon, + Typography, +} from '@mui/material'; +import { setVisibilityFilter } from '../../../store/apps/contacts/ContactSlice'; +import Scrollbar from 'src/components/custom-scroll/Scrollbar'; +import { IconMail, IconSend, IconBucket, IconFolder } from '@tabler/icons-react'; +import ContactAdd from './ContactAdd'; + +interface DataType { + id: number; + name?: string; + sort?: string; + icon?: any; + filterbyTitle?: string; + devider?: boolean; + color?: string; +} + +const ContactFilter = () => { + const dispatch = useDispatch(); + const active = useSelector((state) => state.contactsReducer.currentFilter); + const customizer = useSelector((state) => state.customizer); + const br = `${customizer.borderRadius}px`; + + const filterData: DataType[] = [ + { + id: 2, + name: 'All', + sort: 'show_all', + icon: IconMail, + }, + { + id: 3, + name: 'Frequent', + sort: 'frequent_contact', + icon: IconSend, + }, + { + id: 4, + name: 'Starred', + sort: 'starred_contact', + icon: IconBucket, + }, + { + id: 6, + devider: true, + }, + { + id: 5, + filterbyTitle: 'Categories', + }, + + { + id: 7, + name: 'Engineering', + sort: 'engineering_department', + icon: IconFolder, + color: 'primary.main', + }, + { + id: 8, + name: 'Support', + sort: 'support_department', + icon: IconFolder, + color: 'error.main', + }, + { + id: 9, + name: 'Sales', + sort: 'sales_department', + icon: IconFolder, + color: 'success.main', + }, + ]; + + return ( + <> + + + + {filterData.map((filter) => { + if (filter.filterbyTitle) { + return ( + + {filter.filterbyTitle} + + ); + } else if (filter.devider) { + return ; + } + + return ( + dispatch(setVisibilityFilter(`${filter.sort}`))} + key={filter.id} + > + + + + {filter.name} + + ); + })} + + + + ); +}; + +export default ContactFilter; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactList.tsx new file mode 100644 index 0000000..7319abb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactList.tsx @@ -0,0 +1,106 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { List } from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { + SelectContact, + fetchContacts, + DeleteContact, + toggleStarredContact, +} from '../../../store/apps/contacts/ContactSlice'; + +import Scrollbar from 'src/components/custom-scroll/Scrollbar'; +import ContactListItem from './ContactListItem'; +import type { ContactType } from 'src/types/apps/contact'; + +type Props = { + showrightSidebar: () => void; +}; + +const ContactList = ({ showrightSidebar }: Props) => { + const dispatch = useDispatch(); + useEffect(() => { + dispatch(fetchContacts()); + }, [dispatch]); + + const getVisibleContacts = (contacts: ContactType[], filter: string, contactSearch: string) => { + switch (filter) { + case 'show_all': + return contacts.filter( + (c) => !c.deleted && c.firstname.toLocaleLowerCase().includes(contactSearch), + ); + + case 'frequent_contact': + return contacts.filter( + (c) => + !c.deleted && + c.frequentlycontacted && + c.firstname.toLocaleLowerCase().includes(contactSearch), + ); + + case 'starred_contact': + return contacts.filter( + (c) => !c.deleted && c.starred && c.firstname.toLocaleLowerCase().includes(contactSearch), + ); + + case 'engineering_department': + return contacts.filter( + (c) => + !c.deleted && + c.department === 'Engineering' && + c.firstname.toLocaleLowerCase().includes(contactSearch), + ); + + case 'support_department': + return contacts.filter( + (c) => + !c.deleted && + c.department === 'Support' && + c.firstname.toLocaleLowerCase().includes(contactSearch), + ); + + case 'sales_department': + return contacts.filter( + (c) => + !c.deleted && + c.department === 'Sales' && + c.firstname.toLocaleLowerCase().includes(contactSearch), + ); + + default: + throw new Error(`Unknown filter: ${filter}`); + } + }; + const contacts = useSelector((state) => + getVisibleContacts( + state.contactsReducer.contacts, + state.contactsReducer.currentFilter, + state.contactsReducer.contactSearch, + ), + ); + + const active = useSelector((state) => state.contactsReducer.contactContent); + + return ( + + + {contacts.map((contact) => ( + { + dispatch(SelectContact(contact.id)); + showrightSidebar(); + }} + onDeleteClick={() => dispatch(DeleteContact(contact.id))} + onStarredClick={() => dispatch(toggleStarredContact(contact.id))} + /> + ))} + + + ); +}; + +export default ContactList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactListItem.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactListItem.tsx new file mode 100644 index 0000000..616dc1d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactListItem.tsx @@ -0,0 +1,86 @@ +/* eslint-disable @typescript-eslint/no-unused-vars */ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +import { useSelector } from 'src/store/Store'; +import { + ListItemText, + Box, + Avatar, + ListItemButton, + Typography, + Stack, + ListItemAvatar, + useTheme, +} from '@mui/material'; + +import { IconStar, IconTrash } from '@tabler/icons-react'; + +type Props = { + onContactClick: (event: React.MouseEvent) => void; + onStarredClick: React.MouseEventHandler; + onDeleteClick: React.MouseEventHandler; + id: string | number; + firstname: string; + lastname: string; + image: string; + department: string; + starred: boolean; + active: any; +}; + +const ContactListItem = ({ + onContactClick, + onStarredClick, + onDeleteClick, + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + id, + firstname, + lastname, + image, + department, + starred, + active, +}: Props) => { + const customizer = useSelector((state) => state.customizer); + + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const br = `${customizer.borderRadius}px`; + + const theme = useTheme(); + + const warningColor = theme.palette.warning.main; + + return ( + + + + + + + + + {firstname} {lastname} + + + {department} + + + + + + + + ); +}; + + +export default ContactListItem; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactSearch.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactSearch.tsx new file mode 100644 index 0000000..9e8886f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/contacts/ContactSearch.tsx @@ -0,0 +1,48 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useSelector, useDispatch, AppState } from 'src/store/Store'; +import { Box, Fab, TextField, InputAdornment } from '@mui/material'; + +import { SearchContact } from '../../../store/apps/contacts/ContactSlice'; +import { IconMenu2, IconSearch } from '@tabler/icons-react'; + +type Props = { + onClick: (event: React.MouseEvent) => void; +}; + +const ContactSearch = ({ onClick }: Props) => { + const searchTerm = useSelector((state: AppState) => state.contactsReducer.contactSearch); + const dispatch = useDispatch(); + + return ( + + + + + + + + ), + }} + fullWidth + size="small" + value={searchTerm} + placeholder="Search Contacts" + variant="outlined" + onChange={(e) => dispatch(SearchContact(e.target.value))} + /> + + ); +}; + +export default ContactSearch; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/ProductTableList/ProductTableList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/ProductTableList/ProductTableList.tsx new file mode 100644 index 0000000..da86125 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/ProductTableList/ProductTableList.tsx @@ -0,0 +1,463 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { alpha, useTheme } from '@mui/material/styles'; +import { format } from 'date-fns'; +import { + Box, + Table, + TableBody, + TableCell, + TableContainer, + TableHead, + TablePagination, + TableRow, + TableSortLabel, + Toolbar, + IconButton, + Tooltip, + FormControlLabel, + Typography, + Avatar, + TextField, + InputAdornment, + Paper, +} from '@mui/material'; +import { visuallyHidden } from '@mui/utils'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { fetchProducts } from 'src/store/apps/eCommerce/ECommerceSlice'; +import CustomCheckbox from '../../../forms/theme-elements/CustomCheckbox'; +import CustomSwitch from '../../../forms/theme-elements/CustomSwitch'; +import { IconDotsVertical, IconFilter, IconSearch, IconTrash } from '@tabler/icons-react'; +import { ProductType } from 'src/types/apps/eCommerce'; + +function descendingComparator(a: T, b: T, orderBy: keyof T) { + if (b[orderBy] < a[orderBy]) { + return -1; + } + if (b[orderBy] > a[orderBy]) { + return 1; + } + + return 0; +} + +type Order = 'asc' | 'desc'; + +function getComparator( + order: Order, + orderBy: Key, +): (a: { [key in Key]: number | string }, b: { [key in Key]: number | string }) => number { + return order === 'desc' + ? (a, b) => descendingComparator(a, b, orderBy) + : (a, b) => -descendingComparator(a, b, orderBy); +} + +function stableSort(array: T[], comparator: (a: T, b: T) => number) { + const stabilizedThis = array.map((el, index) => [el, index] as [T, number]); + stabilizedThis.sort((a, b) => { + const order = comparator(a[0], b[0]); + if (order !== 0) { + return order; + } + + return a[1] - b[1]; + }); + + return stabilizedThis.map((el) => el[0]); +} + +interface HeadCell { + disablePadding: boolean; + id: string; + label: string; + numeric: boolean; +} + +const headCells: readonly HeadCell[] = [ + { + id: 'name', + numeric: false, + disablePadding: false, + label: 'Products', + }, + { + id: 'pname', + numeric: false, + disablePadding: false, + label: 'Date', + }, + + { + id: 'status', + numeric: false, + disablePadding: false, + label: 'Status', + }, + { + id: 'price', + numeric: false, + disablePadding: false, + label: 'Price', + }, + { + id: 'action', + numeric: false, + disablePadding: false, + label: 'Action', + }, +]; + +interface EnhancedTableProps { + numSelected: number; + onRequestSort: (event: React.MouseEvent, property: any) => void; + onSelectAllClick: (event: React.ChangeEvent) => void; + order: Order; + orderBy: string; + rowCount: number; +} + +function EnhancedTableHead(props: EnhancedTableProps) { + const { onSelectAllClick, order, orderBy, numSelected, rowCount, onRequestSort } = props; + const createSortHandler = (property: any) => (event: React.MouseEvent) => { + onRequestSort(event, property); + }; + + return ( + + + + 0 && numSelected === rowCount} + onChange={onSelectAllClick} + inputProps={{ + 'aria-label': 'select all desserts', + }} + /> + + {headCells.map((headCell) => ( + + + {headCell.label} + {orderBy === headCell.id ? ( + + {order === 'desc' ? 'sorted descending' : 'sorted ascending'} + + ) : null} + + + ))} + + + ); +} + +interface EnhancedTableToolbarProps { + numSelected: number; + handleSearch: React.ChangeEvent | any; + search: string; +} + +const EnhancedTableToolbar = (props: EnhancedTableToolbarProps) => { + const { numSelected, handleSearch, search } = props; + + return ( + 0 && { + bgcolor: (theme) => + alpha(theme.palette.primary.main, theme.palette.action.activatedOpacity), + }), + }} + > + {numSelected > 0 ? ( + + {numSelected} selected + + ) : ( + + + + + ), + }} + placeholder="Search Product" + size="small" + onChange={handleSearch} + value={search} + /> + + )} + + {numSelected > 0 ? ( + + + + + + ) : ( + + + + + + )} + + ); +}; + +const ProductTableList = () => { + const [order, setOrder] = React.useState('asc'); + const [orderBy, setOrderBy] = React.useState('calories'); + const [selected, setSelected] = React.useState([]); + const [page, setPage] = React.useState(0); + const [dense, setDense] = React.useState(false); + const [rowsPerPage, setRowsPerPage] = React.useState(5); + + const dispatch = useDispatch(); + + //Fetch Products + React.useEffect(() => { + dispatch(fetchProducts()); + }, [dispatch]); + + const getProducts: ProductType[] = useSelector((state) => state.ecommerceReducer.products); + + const [rows, setRows] = React.useState(getProducts); + const [search, setSearch] = React.useState(''); + + React.useEffect(() => { + setRows(getProducts); + }, [getProducts]); + + const handleSearch = (event: React.ChangeEvent) => { + const filteredRows: ProductType[] = getProducts.filter((row) => { + return row.title.toLowerCase().includes(event.target.value); + }); + setSearch(event.target.value); + setRows(filteredRows); + }; + + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const handleRequestSort = (event: React.MouseEvent, property: any) => { + const isAsc = orderBy === property && order === 'asc'; + setOrder(isAsc ? 'desc' : 'asc'); + setOrderBy(property); + }; + + // This is for select all the row + const handleSelectAllClick = (event: React.ChangeEvent) => { + if (event.target.checked) { + const newSelecteds = rows.map((n: any) => n.title); + setSelected(newSelecteds); + + return; + } + setSelected([]); + }; + + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const handleClick = (event: React.MouseEvent, name: string) => { + const selectedIndex = selected.indexOf(name); + let newSelected: readonly string[] = []; + + if (selectedIndex === -1) { + newSelected = newSelected.concat(selected, name); + } else if (selectedIndex === 0) { + newSelected = newSelected.concat(selected.slice(1)); + } else if (selectedIndex === selected.length - 1) { + newSelected = newSelected.concat(selected.slice(0, -1)); + } else if (selectedIndex > 0) { + newSelected = newSelected.concat( + selected.slice(0, selectedIndex), + selected.slice(selectedIndex + 1), + ); + } + + setSelected(newSelected); + }; + + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const handleChangePage = (event: unknown, newPage: number) => { + setPage(newPage); + }; + + const handleChangeRowsPerPage = (event: React.ChangeEvent) => { + setRowsPerPage(parseInt(event.target.value, 10)); + setPage(0); + }; + + const handleChangeDense = (event: React.ChangeEvent) => { + setDense(event.target.checked); + }; + + const isSelected = (name: string) => selected.indexOf(name) !== -1; + + // Avoid a layout jump when reaching the last page with empty rows. + const emptyRows = page > 0 ? Math.max(0, (1 + page) * rowsPerPage - rows.length) : 0; + + const theme = useTheme(); + const borderColor = theme.palette.divider; + + return ( + + + handleSearch(event)} + /> + + + + + + {stableSort(rows, getComparator(order, orderBy)) + .slice(page * rowsPerPage, page * rowsPerPage + rowsPerPage) + .map((row: any, index) => { + const isItemSelected = isSelected(row.title); + const labelId = `enhanced-table-checkbox-${index}`; + + return ( + handleClick(event, row.title)} + role="checkbox" + aria-checked={isItemSelected} + tabIndex={-1} + key={row.title} + selected={isItemSelected} + > + + + + + + + + + + {row.title} + + + {row.category} + + + + + + {format(new Date(row.created), 'E, MMM d yyyy')} + + + + + theme.palette.success.main + : (theme) => theme.palette.error.main, + borderRadius: '100%', + height: '10px', + width: '10px', + }} + /> + + {row.stock ? 'InStock' : 'Out of Stock'} + + + + + + + ${row.price} + + + + + + + + + + + ); + })} + {emptyRows > 0 && ( + + + + )} + +
+
+ +
+ + } + label="Dense padding" + /> + +
+
+ ); +}; + +export default ProductTableList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/GeneralCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/GeneralCard.tsx new file mode 100644 index 0000000..a02adab --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/GeneralCard.tsx @@ -0,0 +1,43 @@ +import Box from '@mui/material/Box'; +import { Typography } from '@mui/material'; +import Grid from '@mui/material/Grid2'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import TiptapEdit from 'src/views/forms/from-tiptap/TiptapEdit'; + +const GeneralCard = () => { + return ( + ( + General + + {/* 1 */} + + + Product Name{' '} + + * + + + + + + + A product name is required and recommended to be unique. + + + + + Description + + + + + Set a description to the product for better visibility. + + + + ) + ); +}; + +export default GeneralCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Media.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Media.tsx new file mode 100644 index 0000000..d7775b5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Media.tsx @@ -0,0 +1,58 @@ + +import Box from "@mui/material/Box"; +import { Chip, Typography, useTheme } from "@mui/material"; +import { useDropzone } from "react-dropzone"; + +const MediaCard = () => { + const theme = useTheme(); + + const { acceptedFiles, getRootProps, getInputProps } = useDropzone(); + + const files = acceptedFiles.map((file: any) => ( + + + {file.path}{" "} + + + + )); + + return ( + + Media + + + +

Drag 'n' drop some files here, or click to select files

+
+ + + Files : + + {files} + +
+ ); +}; + +export default MediaCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Pricing.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Pricing.tsx new file mode 100644 index 0000000..85bc9b5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Pricing.tsx @@ -0,0 +1,186 @@ + +import React, { useState } from 'react'; +import Box from '@mui/material/Box'; +import { Typography, FormControlLabel, RadioGroup, Stack, useTheme } from '@mui/material'; +import Grid from '@mui/material/Grid2'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; +import { MenuItem } from '@mui/material'; +import CustomRadio from 'src/components/forms/theme-elements/CustomRadio'; +import CustomSlider from 'src/components/forms/theme-elements/CustomSlider'; + +const PricingCard = () => { + const theme = useTheme(); + + const [age, setAge] = React.useState('0'); + const handleChange = (event: any) => { + setAge(event.target.value); + }; + + const [selectedValue, setSelectedValue] = useState(''); + + const handleValue = (event: any) => { + setSelectedValue(event.target.value); + }; + + const [value3, setValue3] = React.useState(30); + const handleChange6 = (newValue: any) => { + setValue3(newValue); + }; + + return ( + ( + + Pricing + + + {/* 1 */} + + + Base Price{' '} + + * + + + + Set the product price. + + + + Discount Type{' '} + + * + + + + + + } + label="No Discount" + /> + + + } + label="Percentage %" + /> + + + } label="Fixed Price" /> + + + + + {selectedValue === 'no_discount' && null} + + {selectedValue === 'percentage' && ( + <> + + Set Discount Percentage{' '} + + * + + + + + Set a percentage discount to be applied on this product. + + + )} + + {selectedValue === 'fixed' && ( + <> + + Fixed Discounted Price{' '} + + * + + + + + Set the discounted product price. The product will be reduced at the determined + fixed price. + + + )} + + + + Tax Class{' '} + + * + + + + Select an option + Tax Free + Taxable Goods + Downloadable Products + + Set the product tax class. + + + + VAT Amount (%){' '} + + * + + + + Set the product VAT about. + + + ) + ); +}; + +export default PricingCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/ProductDetails.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/ProductDetails.tsx new file mode 100644 index 0000000..9cb936c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/ProductDetails.tsx @@ -0,0 +1,84 @@ + +import Box from "@mui/material/Box"; +import { Autocomplete, Button, Grid2 as Grid, Typography } from "@mui/material"; +import CustomFormLabel from "src/components/forms/theme-elements/CustomFormLabel"; +import CustomTextField from "src/components/forms/theme-elements/CustomTextField"; +import { IconPlus } from "@tabler/icons-react"; + +const new_category = [ + { label: "Computer" }, + { label: "Watches" }, + { label: "Headphones" }, + { label: "Beauty" }, + { label: "Fashion" }, + { label: "Footwear" }, +]; + +const new_tags = [ + { label: "New" }, + { label: "Trending" }, + { label: "Footwear" }, + { label: "Latest" }, +]; + +const ProductDetails = () => { + return ( + ( + Product Details + + {/* 1 */} + + + Categories + + + + option.label} + filterSelectedOptions + renderInput={(params) => ( + + )} + /> + + {/* */} + + Add product to a category. + + + + + + {/* 1 */} + + Tags + + + option.label} + filterSelectedOptions + renderInput={(params) => ( + + )} + /> + {/* */} + + Add product to a category. + + + + ) + ); +}; + +export default ProductDetails; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/ProductTemplate.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/ProductTemplate.tsx new file mode 100644 index 0000000..8f16146 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/ProductTemplate.tsx @@ -0,0 +1,39 @@ + +import { useState } from 'react'; +import Box from '@mui/material/Box'; +import { Grid2 as Grid, MenuItem, Typography } from '@mui/material'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; + +const ProductTemplate = () => { + const [age, setAge] = useState('0'); + const handleChange = (event: any) => { + setAge(event.target.value); + }; + + return ( + ( + + Product Template + + + + + Select a product template + + + Default Template + Fashion + Office Stationary + Electronics + + + Assign a template from your current theme to define how a single product is displayed. + + + + ) + ); +}; + +export default ProductTemplate; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Status.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Status.tsx new file mode 100644 index 0000000..e64c470 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Status.tsx @@ -0,0 +1,53 @@ + +import { useState } from 'react'; +import Box from '@mui/material/Box'; +import { Grid2 as Grid, Typography } from '@mui/material'; +import { MenuItem, Avatar } from '@mui/material'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; + +const StatusCard = () => { + const [status, setStatus] = useState(0); + const handleChange = (event: any) => { + setStatus(event.target.value); + console.log('test'); + }; + + return ( + ( + + Status + + + + + + + Published + Draft + Scheduled + In active + + Set the product status. + + + ) + ); +}; + +export default StatusCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Thumbnail.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Thumbnail.tsx new file mode 100644 index 0000000..b81dd58 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/Thumbnail.tsx @@ -0,0 +1,62 @@ + +import Box from "@mui/material/Box"; +import { Typography, useTheme, Chip } from "@mui/material"; +import { useDropzone } from "react-dropzone"; + +const Thumbnail = () => { + const theme = useTheme(); + + const { acceptedFiles, getRootProps, getInputProps } = useDropzone(); + + const files = acceptedFiles.map((file: File, i) => ( + + + {file.name}{" "} + + + + )); + + return ( + + Thumbnail + + + +

Drag 'n' drop some files here, or click to select files

+
+ + Set the product thumbnail image. Only *.png, *.jpg and *.jpeg image + files are accepted. + + + + Files + + {files} + +
+ ); +}; + +export default Thumbnail; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/VariationCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/VariationCard.tsx new file mode 100644 index 0000000..a1bd11d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productAdd/VariationCard.tsx @@ -0,0 +1,64 @@ + +import { useState } from 'react'; +import Box from '@mui/material/Box'; +import { Button, Grid2 as Grid, Tooltip, MenuItem } from '@mui/material'; +import { Typography } from '@mui/material'; + +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import { IconX } from '@tabler/icons-react'; +import { IconPlus } from '@tabler/icons-react'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; + +const VariationCard = () => { + const [age, setAge] = useState('0'); + const handleChange = (event: any) => { + setAge(event.target.value); + }; + + return ( + ( + Variation + Add Product Variations + + + + Size + XS + SM + MD + LG + XL + + + + + + + + + + + + + ) + ); +}; + +export default VariationCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCart/AddToCart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCart/AddToCart.tsx new file mode 100644 index 0000000..363e081 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCart/AddToCart.tsx @@ -0,0 +1,125 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Box, + Typography, + Avatar, + Stack, + ButtonGroup, + Button, + Table, + TableContainer, + TableHead, + TableRow, + TableCell, + TableBody, + IconButton, +} from '@mui/material'; +import { Link } from 'react-router'; +import { IconMinus, IconPlus, IconTrash } from '@tabler/icons-react'; +import { useSelector, useDispatch } from 'src/store/Store'; +import emptyCart from 'src/assets/images/products/empty-shopping-cart.svg'; +import { increment, deleteCart, decrement } from '../../../../store/apps/eCommerce/ECommerceSlice'; +import { ProductType } from 'src/types/apps/eCommerce'; + +const AddToCart = () => { + const dispatch = useDispatch(); + + // Get Products + const Cartproduct: ProductType[] = useSelector((state) => state.ecommerceReducer.cart); + console.log(Cartproduct); + const Increase = (productId: number | string) => { + dispatch(increment(productId)); + }; + + const Decrease = (productId: number | string) => { + dispatch(decrement(productId)); + }; + + return ( + + {Cartproduct.length > 0 ? ( + <> + + + + + + Product + + Quantity + Price + + + + + {Cartproduct.map((product) => ( + + {/* ------------------------------------------- */} + {/* Product Image & Title */} + {/* ------------------------------------------- */} + + + + + {product.title}{' '} + + {product.category} + + dispatch(deleteCart(product.id))} + > + + + + + + + + + + + + + + + ${product.price * product.qty} + + + ))} + +
+
+
+ + ) : ( + + cart + + Cart is Empty + + + + )} +
+ ); +}; + +export default AddToCart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCart/AlertCart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCart/AlertCart.tsx new file mode 100644 index 0000000..56ffb7f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCart/AlertCart.tsx @@ -0,0 +1,28 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import * as React from 'react'; +import { Snackbar, Alert } from '@mui/material'; + +interface Props { + handleClose: (event: React.SyntheticEvent | any) => void; + openCartAlert: boolean; +} + +const AlertCart = ({ handleClose, openCartAlert }: Props) => { + return ( + + + + Item Added to the Cart!!! + + + + ); +}; + +export default AlertCart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/FinalStep.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/FinalStep.tsx new file mode 100644 index 0000000..4317bb5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/FinalStep.tsx @@ -0,0 +1,26 @@ +import { Box, Typography } from '@mui/material'; +import payment from 'src/assets/images/products/payment-complete.gif'; + +const FinalStep = () => { + return ( + <> + + + Thank you for your purchase! + + Your order id: 3fa7-69e1-79b4-dbe0d35f5f5d + + payment +
+
+ + We will send you a notification
+ within 2 days when it ships. +
+
+
+ + ); +}; + +export default FinalStep; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/FirstStep.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/FirstStep.tsx new file mode 100644 index 0000000..ef2ba46 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/FirstStep.tsx @@ -0,0 +1,58 @@ +import { Box, Typography, Stack } from '@mui/material'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import ChildCard from '../../../shared/ChildCard'; + +interface Props { + total: number; + Discount: number; +} + +const FirstStep = ({ total, Discount }: Props) => { + return ( + <> + + + + + Order Summary + + {/* Sub Total */} + + + Sub Total + + ${total} + + {/* Discount */} + + + Discount 5% + + + -${Discount} + + + {/* Sub Total */} + + + Shipping + + Free + + {/* Sub Total */} + + Total + + ${total - Discount} + + + + + + + ); +}; + +export default FirstStep; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/HorizontalStepper.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/HorizontalStepper.tsx new file mode 100644 index 0000000..a620ba9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/HorizontalStepper.tsx @@ -0,0 +1,57 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import * as React from 'react'; +import Box from '@mui/material/Box'; +import Stepper from '@mui/material/Stepper'; +import Step from '@mui/material/Step'; +import StepLabel from '@mui/material/StepLabel'; +import Button from '@mui/material/Button'; +import { Link } from 'react-router'; + +interface Props { + children: any | any[] + steps: any[]; + activeStep: number; + handleReset: (event: React.SyntheticEvent | Event) => void; + finalStep: any | any[] +} + + + +const HorizontalStepper = ({ children, steps, activeStep, handleReset, finalStep }: Props) => { + return ( + + + {steps.map((label) => { + const stepProps = {}; + const labelProps = {}; + + return ( + + {label} + + ); + })} + + {activeStep === steps.length ? ( + + {finalStep} + + + + + + + + ) : ( + + {children} + + )} + + ); +}; + +export default HorizontalStepper; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/ProductCheckout.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/ProductCheckout.tsx new file mode 100644 index 0000000..cb2db7a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/ProductCheckout.tsx @@ -0,0 +1,113 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { sum } from 'lodash'; +import { Box, Stack, Button } from '@mui/material'; +import AddToCart from '../productCart/AddToCart'; + +import { IconArrowBack } from '@tabler/icons-react'; +import { useSelector } from 'src/store/Store'; +import HorizontalStepper from './HorizontalStepper'; +import FirstStep from './FirstStep'; +import SecondStep from './SecondStep'; +import ThirdStep from './ThirdStep'; +import FinalStep from './FinalStep'; +import { ProductType } from 'src/types/apps/eCommerce'; + +const ProductChecout = () => { + const checkout = useSelector((state) => state.ecommerceReducer.cart); + const steps = ['Cart', 'Billing & address', 'Payment']; + const [activeStep, setActiveStep] = React.useState(0); + const handleNext = () => { + setActiveStep((prevActiveStep) => prevActiveStep + 1); + }; + + const handleBack = () => { + setActiveStep((prevActiveStep) => prevActiveStep - 1); + }; + const handleReset = () => { + setActiveStep(0); + }; + + const total = sum(checkout.map((product: ProductType) => product.price * product.qty)); + const Discount = Math.round(total * (5 / 100)); + + return ( + + } + > + {/* ------------------------------------------- */} + {/* Step1 */} + {/* ------------------------------------------- */} + {activeStep === 0 ? ( + <> + + + + {checkout.length > 0 ? ( + <> + {/* ------------------------------------------- */} + {/* Cart Total */} + {/* ------------------------------------------- */} + + + + + + + ) : ( + '' + )} + + ) : activeStep === 1 ? ( + <> + {/* ------------------------------------------- */} + {/* Step2 */} + {/* ------------------------------------------- */} + + + + + + + + ) : ( + <> + {/* ------------------------------------------- */} + {/* Step3 */} + {/* ------------------------------------------- */} + + + + + + + + )} + + + ); +}; + +export default ProductChecout; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/SecondStep.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/SecondStep.tsx new file mode 100644 index 0000000..c1593cd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/SecondStep.tsx @@ -0,0 +1,66 @@ +import { Typography, Grid2 as Grid, Button, Paper } from '@mui/material'; +import { IconDeviceMobile } from '@tabler/icons-react'; + +interface addressType { + id: number; + name: string; + address: string; + mobile: string; +} + +const Myaddress: addressType[] = [ + { + id: 1, + name: 'Johnathan Doe', + address: 'E601 Vrundavan Heights, godrej garden city - 382481', + mobile: '9999501050', + }, + { + id: 2, + name: 'ParleG Doe', + address: 'D201 Galexy Heights, godrej garden city - 382481', + mobile: '9999501050', + }, + { + id: 3, + name: 'Guddu Bhaiya', + address: 'Mumbai khao gali, Behind shukan, godrej garden city - 382481', + mobile: '9999501050', + }, +]; + +interface Props { + nexStep: (event: React.SyntheticEvent | Event) => void; +} + +const SecondStep = ({ nexStep }: Props) => { + return (<> + + {Myaddress.map((address) => ( + + + + {address.name} + + + {address.address} + + + {address.mobile} + + + + + ))} + + ); +}; + +export default SecondStep; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/ThirdStep.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/ThirdStep.tsx new file mode 100644 index 0000000..862b2ba --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productCheckout/ThirdStep.tsx @@ -0,0 +1,168 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, Grid2 as Grid, Paper, Radio, Stack, Typography } from '@mui/material'; +import Paypal from 'src/assets/images/svgs/paypal.svg'; +import payment from 'src/assets/images/products/payment.svg'; +import mastercard from 'src/assets/images/svgs/mastercard.svg'; + +interface deliveryType { + id: number; + title: string; + description: string; +} + +interface paymentType { + value: string; + title: string; + description: string; + icons: string; +} + +const Delivery: deliveryType[] = [ + { + id: 1, + title: 'Free delivery', + description: 'Delivered on Firday, May 10', + }, + { + id: 2, + title: 'Fast delivery ($2,00)', + description: 'Delivered on Wednesday, May 8', + }, +]; + +const Payment: paymentType[] = [ + { + value: 'paypal', + title: 'Pay with Paypal', + description: 'You will be redirected to PayPal website to complete your purchase securely.', + icons: Paypal, + }, + { + value: 'credit_card', + title: 'Credit / Debit Card', + description: 'We support Mastercard, Visa, Discover and Stripe.', + icons: mastercard, + }, + { + value: 'cash', + title: 'Cash on Delivery', + description: 'Pay with cash when your order is delivered.', + icons: '', + }, +]; + +const ThirdStep = () => { + const [selectedValue, setSelectedValue] = React.useState('Free delivery'); + + const handleDChange = (event: React.ChangeEvent) => { + setSelectedValue(event.target.value); + }; + const [selectedPyament, setSelectedPyament] = React.useState('paypal'); + + const handlePChange = (event: React.ChangeEvent) => { + setSelectedPyament(event.target.value); + }; + + return (<> + {/* ------------------------------------------- */} + {/* Delivery Option */} + {/* ------------------------------------------- */} + + Delivery Option + + {Delivery.map((option) => ( + + + + + + {option.title} + {option.description} + + + + + ))} + + + {/* ------------------------------------------- */} + {/* Payment Option */} + {/* ------------------------------------------- */} + + Payment Option + + + + {Payment.map((option) => ( + + + + + + {option.title} + {option.description} + + + {option.icons ? payment : ''} + + + + + ))} + + + + payment + + + + ); +}; + +export default ThirdStep; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/Carousel.css b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/Carousel.css new file mode 100644 index 0000000..b06daf5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/Carousel.css @@ -0,0 +1,13 @@ +.centerThumb .slick-current img{ + border:2px solid rgba(0,0,0,1); +} +.slick-prev:before, .slick-next:before{ + color:#2b2b2b +} +.slick-next{ + right:15px +} +.slick-prev{ + left:15px; + z-index: 1; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductCarousel.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductCarousel.tsx new file mode 100644 index 0000000..a77c553 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductCarousel.tsx @@ -0,0 +1,101 @@ +import React, { useEffect, useRef } from 'react'; +import { Box } from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { useParams } from 'react-router'; + +//Carousel slider for product +import Slider from 'react-slick'; +import 'slick-carousel/slick/slick.css'; +import 'slick-carousel/slick/slick-theme.css'; +import './Carousel.css'; + +//Carousel slider data +import SliderData from './SliderData'; + +//fetch product +import { fetchProducts } from 'src/store/apps/eCommerce/ECommerceSlice'; +import { ProductType } from 'src/types/apps/eCommerce'; + +const ProductCarousel = () => { + const [state, setState] = React.useState({ nav1: null, nav2: null }); + const slider1 = useRef(null); + const slider2 = useRef(null); + const dispatch = useDispatch(); + const Id: any = useParams(); + + // Get Product + useEffect(() => { + dispatch(fetchProducts()); + }, [dispatch]); + + // Get Products + const product: ProductType = useSelector((state) => state.ecommerceReducer.products[Id.id - 1]); + const getProductImage = product ? product.photo : ''; + + useEffect(() => { + setState({ + nav1: slider1.current, + nav2: slider2.current, + }); + }, []); + + const { nav1, nav2 } = state; + const settings = { + focusOnSelect: true, + infinite: true, + slidesToShow: 5, + arrows: false, + swipeToSlide: true, + slidesToScroll: 1, + centerMode: true, + className: 'centerThumb', + speed: 500, + }; + + return ( + + (slider1.current = slider)}> + + {getProductImage} + + {SliderData.map((step) => ( + + {step.imgPath} + + ))} + + (slider2.current = slider)} {...settings}> + + {getProductImage} + + {SliderData.map((step) => ( + + {step.imgPath} + + ))} + + + ); +}; + +export default ProductCarousel; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductDesc.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductDesc.tsx new file mode 100644 index 0000000..e2fac3f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductDesc.tsx @@ -0,0 +1,202 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +import { + Box, + Typography, + LinearProgress, + Tabs, + Tab, + Grid2 as Grid, + Stack, + Rating, + Button, + Paper, +} from '@mui/material'; +import { IconPencil } from '@tabler/icons-react'; +import ChildCard from 'src/components/shared/ChildCard'; + +interface ProductCardProps { + like: number; + star: number; + value?: number; +} + +interface TabProps { + children: React.ReactNode; + index: number; + value?: number; +} + +// progress +function ProgressBar({ like, star, value, ...others }: ProductCardProps) { + return ( + + + {`${Math.round(star)} Stars`} + + + + + + {`(${Math.round(like)})`} + + + ); +} + +const TabPanel = (props: TabProps) => { + const { children, value, index, ...other } = props; + + return ( + + ); +}; + +const a11yProps = (index: number) => { + return { + id: `simple-tab-${index}`, + 'aria-controls': `simple-tabpanel-${index}`, + }; +}; + +const ProductDesc = () => { + const [value, setValue] = React.useState(0); + + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const handleChange = (event: React.SyntheticEvent, newValue: number) => { + setValue(newValue); + }; + + return ( + ( + + + + + + + + {/* ------------------------------------------- */} + {/* Decription */} + {/* ------------------------------------------- */} + + + Sed at diam elit. Vivamus tortor odio, pellentesque eu tincidunt a, aliquet sit amet + lorem pellentesque eu tincidunt a, aliquet sit amet lorem. + + + Cras eget elit semper, congue sapien id, pellentesque diam. Nulla faucibus diam nec + fermentum ullamcorper. Praesent sed ipsum ut augue vestibulum malesuada. Duis vitae + volutpat odio. Integer sit amet elit ac justo sagittis dignissim. + + + Vivamus quis metus in nunc semper efficitur eget vitae diam. Proin justo diam, venenatis + sit amet eros in, iaculis auctor magna. Pellentesque sit amet accumsan urna, sit amet + pretium ipsum. Fusce condimentum venenatis mauris et luctus. Vestibulum ante ipsum + primis in faucibus orci luctus et ultrices posuere cubilia curae; + + + {/* ------------------------------------------- */} + {/* Reviews Tab */} + {/* ------------------------------------------- */} + + + {/* ------------------------------------------- */} + {/* Average Rate Tab */} + {/* ------------------------------------------- */} + + + + Average Rating + + 4/5 + + + + + + {/* ------------------------------------------- */} + {/* Progrees Rate Tab */} + {/* ------------------------------------------- */} + + + + + + + + + + + + + + + + + + + + + + {/* ------------------------------------------- */} + {/* Button */} + {/* ------------------------------------------- */} + + + + + + + + + + + ) + ); +}; + +export default ProductDesc; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductDetail.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductDetail.tsx new file mode 100644 index 0000000..3cef873 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductDetail.tsx @@ -0,0 +1,214 @@ +import React, { useEffect, useState } from 'react'; +import { useParams } from 'react-router'; +import { Link } from 'react-router'; + +// MUI Elements +import { + Box, + Grid2 as Grid, + Typography, + Chip, + Button, + Rating, + Divider, + Stack, + useTheme, + Fab, + ButtonGroup, +} from '@mui/material'; + +import { useSelector, useDispatch } from 'src/store/Store'; +import { fetchProducts, addToCart } from '../../../../store/apps/eCommerce/ECommerceSlice'; +import { IconCheck, IconMinus, IconPlus } from '@tabler/icons-react'; +import AlertCart from '../productCart/AlertCart'; +import { ProductType } from 'src/types/apps/eCommerce'; + +const ProductDetail = () => { + const theme = useTheme(); + const dispatch = useDispatch(); + const Id: any = useParams(); + + // Get Product + useEffect(() => { + dispatch(fetchProducts()); + }, [dispatch]); + + // Get Products + const product: ProductType = useSelector((state) => state.ecommerceReducer.products[Id.id - 1]); + + /// select colors on click + const [scolor, setScolor] = useState(product ? product.colors[0] : ''); + const setColor = (e: string) => { + setScolor(e); + }; + + //set qty + const [count, setCount] = useState(1); + + // for alert when added something to cart + const [cartalert, setCartalert] = React.useState(false); + + const handleClick = () => { + setCartalert(true); + }; + + const handleClose = (reason: string) => { + if (reason === 'clickaway') { + return; + } + setCartalert(false); + }; + + return ( + ( + {product ? ( + <> + + {/* ------------------------------------------- */} + {/* Badge and category */} + {/* ------------------------------------------- */} + + + {product.category} + + + {/* ------------------------------------------- */} + {/* Title and description */} + {/* ------------------------------------------- */} + + {product.title} + + + Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed ex arcu, tincidunt bibendum + felis. + + {/* ------------------------------------------- */} + {/* Price */} + {/* ------------------------------------------- */} + + + ${product.salesPrice} + {' '} + ${product.price} + + {/* ------------------------------------------- */} + {/* Ratings */} + {/* ------------------------------------------- */} + + + + (236 reviews) + + + + {/* ------------------------------------------- */} + {/* Colors */} + {/* ------------------------------------------- */} + + + Colors: + + + {product.colors.map((color) => ( + setColor(color)} + > + {scolor === color ? : ''} + + ))} + + + {/* ------------------------------------------- */} + {/* Qty */} + {/* ------------------------------------------- */} + + + QTY: + + + + + + + + + + + {/* ------------------------------------------- */} + {/* Buttons */} + {/* ------------------------------------------- */} + + + + + + + + + + Dispatched in 2-3 weeks + + + Why the longer time for delivery? + + {/* ------------------------------------------- */} + {/* Alert When click on add to cart */} + {/* ------------------------------------------- */} + + + ) : ( + 'No product' + )} + ) + ); +}; + +export default ProductDetail; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductRelated.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductRelated.tsx new file mode 100644 index 0000000..b3b2d5c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/ProductRelated.tsx @@ -0,0 +1,86 @@ +import React, { useEffect } from 'react'; +import { Box, Stack, Typography, CardContent, Grid2 as Grid, Rating, Skeleton } from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { fetchProducts } from 'src/store/apps/eCommerce/ECommerceSlice'; +import { Link } from 'react-router'; +import BlankCard from '../../../shared/BlankCard'; +import { ProductType } from 'src/types/apps/eCommerce'; + +const ProductRelated = () => { + const dispatch = useDispatch(); + + // Get Product + React.useEffect(() => { + dispatch(fetchProducts()); + }, [dispatch]); + + const filterRelatedProduct = (products: ProductType[]) => { + if (products) return products.filter((t) => t.related); + + return products; + }; + + // Get Products + const Relatedproducts = useSelector((state) => + filterRelatedProduct(state.ecommerceReducer.products), + ); + + // skeleton + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 700); + + return () => clearTimeout(timer); + }, []); + + return ( + ( + + Related Products + + + {Relatedproducts.map((product) => ( + + {/* ------------------------------------------- */} + {/* Product Card */} + {/* ------------------------------------------- */} + + + {isLoading ? ( + + ) : ( + img + )} + + + {product.title} + + + ${product.price} + + ${product.salesPrice} + + + + + + + + ))} + + ) + ); +}; + +export default ProductRelated; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/SliderData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/SliderData.ts new file mode 100644 index 0000000..0c92d52 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productDetail/SliderData.ts @@ -0,0 +1,45 @@ +import img1 from 'src/assets/images/products/s1.jpg'; +import img2 from 'src/assets/images/products/s2.jpg'; +import img3 from 'src/assets/images/products/s3.jpg'; +import img4 from 'src/assets/images/products/s4.jpg'; +import img5 from 'src/assets/images/products/s5.jpg'; +import img6 from 'src/assets/images/products/s6.jpg'; +import img7 from 'src/assets/images/products/s7.jpg'; + +interface DataType { + id: number; + imgPath: string; +} + +const SliderData: DataType[] = [ + { + imgPath: img1, + id: 1, + }, + { + imgPath: img2, + id: 2, + }, + { + imgPath: img3, + id: 3, + }, + { + imgPath: img4, + id: 4, + }, + { + imgPath: img5, + id: 5, + }, + { + imgPath: img6, + id: 6, + }, + { + imgPath: img7, + id: 7, + }, +]; + +export default SliderData; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/CustomersReviews.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/CustomersReviews.tsx new file mode 100644 index 0000000..2fe7e21 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/CustomersReviews.tsx @@ -0,0 +1,161 @@ + +import { + Typography, + Box, + Table, + TableBody, + TableCell, + TableHead, + TableRow, + Avatar, + TableContainer, + Stack, + Rating, +} from '@mui/material'; + +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; +import user4 from 'src/assets/images/profile/user-4.jpg'; +import user5 from 'src/assets/images/profile/user-5.jpg'; +import user6 from 'src/assets/images/profile/user-6.jpg'; +import user7 from 'src/assets/images/profile/user-7.jpg'; +import user8 from 'src/assets/images/profile/user-8.jpg'; + +const performers = [ + { + id: '1', + imgsrc: user1, + name: 'Sunil Joshi', + rating: 4, + reviews: 'I like this design', + date: '1 day ago', + }, + { + id: '2', + imgsrc: user2, + name: 'Mark Richard', + rating: 5, + reviews: 'Awesome quality with great materials used, but could be more comfortable', + date: '11:20 PM', + }, + { + id: '3', + imgsrc: user3, + name: 'Hanry Lord', + rating: 2, + reviews: 'This is the best product I have ever used.', + date: 'Today', + }, + { + id: '4', + imgsrc: user4, + name: 'Britny Cox', + rating: 3, + reviews: 'Beautifully crafted. Worth every penny.', + date: 'Today', + }, + { + id: '5', + imgsrc: user5, + name: 'Olvin wild', + rating: 4, + reviews: 'Beautifully crafted. Worth every penny.', + date: 'Yesterday', + }, + { + id: '6', + imgsrc: user6, + name: 'Dan wilsed', + rating: 4.5, + reviews: 'Beautifully crafted. Worth every penny.', + date: '12:00 PM', + }, + { + id: '7', + imgsrc: user7, + name: 'Jon Miller', + rating: 4, + reviews: 'Beautifully crafted. Worth every penny.', + date: '1 May 2024', + }, + { + id: '8', + imgsrc: user8, + name: 'Anaa Crown', + rating: 4, + reviews: 'Beautifully crafted. Worth every penny.', + date: '25 April 2024', + }, +]; + +const CustomersReviews = () => { + return ( + + + Customer Reviews + + + + + + + + + Customer + + + + + Comment + + + + + Date + + + + + + {performers.map((basic) => ( + + + + + + + {basic.name} + + + + + + + {basic.reviews} + + + + + {basic.date} + + + + ))} + +
+
+
+ ); +}; + +export default CustomersReviews; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/GeneralCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/GeneralCard.tsx new file mode 100644 index 0000000..728ceb5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/GeneralCard.tsx @@ -0,0 +1,48 @@ +import Box from '@mui/material/Box'; +import { Typography } from '@mui/material'; +import Grid from '@mui/material/Grid2'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import TiptapEdit from 'src/views/forms/from-tiptap/TiptapEdit'; + +const GeneralCard = () => { + return ( + ( + General + + {/* 1 */} + + + Product Name{' '} + + * + + + + + + + A product name is required and recommended to be unique. + + + + + Description + + + + + Set a description to the product for better visibility. + + + + ) + ); +}; + +export default GeneralCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Media.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Media.tsx new file mode 100644 index 0000000..d7775b5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Media.tsx @@ -0,0 +1,58 @@ + +import Box from "@mui/material/Box"; +import { Chip, Typography, useTheme } from "@mui/material"; +import { useDropzone } from "react-dropzone"; + +const MediaCard = () => { + const theme = useTheme(); + + const { acceptedFiles, getRootProps, getInputProps } = useDropzone(); + + const files = acceptedFiles.map((file: any) => ( + + + {file.path}{" "} + + + + )); + + return ( + + Media + + + +

Drag 'n' drop some files here, or click to select files

+
+ + + Files : + + {files} + +
+ ); +}; + +export default MediaCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Pricing.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Pricing.tsx new file mode 100644 index 0000000..8187b0c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Pricing.tsx @@ -0,0 +1,183 @@ + +import React, { useState } from 'react'; +import Box from '@mui/material/Box'; +import { Typography, FormControlLabel, RadioGroup, Stack, useTheme } from '@mui/material'; +import Grid from '@mui/material/Grid2'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; +import { MenuItem } from '@mui/material'; +import CustomRadio from 'src/components/forms/theme-elements/CustomRadio'; +import CustomSlider from 'src/components/forms/theme-elements/CustomSlider'; + +const PricingCard = () => { + const theme = useTheme(); + + const [age, setAge] = React.useState('1'); + const handleChange = (event: any) => { + setAge(event.target.value); + }; + + const [selectedValue, setSelectedValue] = useState('percentage'); + + const handleValue = (event: any) => { + setSelectedValue(event.target.value); + }; + + const [value3, setValue3] = React.useState(30); + const handleChange6 = (newValue: any) => { + setValue3(newValue); + }; + + return ( + ( + + Pricing + + + {/* 1 */} + + + Base Price{' '} + + * + + + + Set the product price. + + + + Discount Type{' '} + + * + + + + + + } + label="No Discount" + /> + + + } + label="Percentage %" + /> + + + } label="Fixed Price" /> + + + + + {selectedValue === 'no_discount' && null} + + {selectedValue === 'percentage' && ( + <> + + Set Discount Percentage{' '} + + * + + + + + Set a percentage discount to be applied on this product. + + + )} + + {selectedValue === 'fixed' && ( + <> + + Fixed Discounted Price{' '} + + * + + + + + Set the discounted product price. The product will be reduced at the determined + fixed price. + + + )} + + + + Tax Class{' '} + + * + + + + Select an option + Tax Free + Taxable Goods + Downloadable Products + + Set the product tax class. + + + + VAT Amount (%){' '} + + * + + + + Set the product VAT about. + + + ) + ); +}; + +export default PricingCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/ProductAvgSales.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/ProductAvgSales.tsx new file mode 100644 index 0000000..4785dee --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/ProductAvgSales.tsx @@ -0,0 +1,110 @@ + +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import Box from '@mui/material/Box'; +import { Chip, Typography } from '@mui/material'; + +const ProductAvgSales = () => { + const theme = useTheme(); + const primary = theme.palette.primary.main; + + // chart + const optionsPrdAvgSaleschart: any = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 85, + resize: true, + barColor: '#fff', + sparkline: { + enabled: true, + }, + }, + colors: [primary], + grid: { + show: false, + }, + plotOptions: { + bar: { + horizontal: false, + startingShape: 'flat', + endingShape: 'flat', + columnWidth: '60%', + barHeight: '20%', + borderRadius: 3, + }, + }, + dataLabels: { + enabled: false, + }, + stroke: { + show: true, + width: 2.5, + colors: ['rgba(0,0,0,0.01)'], + }, + xaxis: { + axisBorder: { + show: false, + }, + axisTicks: { + show: false, + }, + labels: { + show: false, + }, + }, + yaxis: { + labels: { + show: false, + }, + }, + axisBorder: { + show: false, + }, + fill: { + opacity: 1, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + x: { + show: false, + }, + }, + }; + const seriesPrdAvgSaleschart = [ + { + name: '', + data: [4, 10, 9, 7, 9, 10, 11, 8, 10], + }, + ]; + + return ( + + + $2,420 + + + + Average Daily Sales{' '} + + + + + + + + + ); +}; + +export default ProductAvgSales; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/ProductDetails.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/ProductDetails.tsx new file mode 100644 index 0000000..a796e22 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/ProductDetails.tsx @@ -0,0 +1,82 @@ + +import Box from '@mui/material/Box'; +import { Autocomplete, Button, Grid2 as Grid, Typography } from '@mui/material'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import { IconPlus } from '@tabler/icons-react'; + +const new_category = [ + { label: 'Computer' }, + { label: 'Watches' }, + { label: 'Headphones' }, + { label: 'Beauty' }, + { label: 'Fashion' }, + { label: 'Footwear' }, +]; + +const new_tags = [ + { label: 'New' }, + { label: 'Trending' }, + { label: 'Footwear' }, + { label: 'Latest' }, +]; + +const ProductDetails = () => { + return ( + ( + Product Details + + {/* 1 */} + + + Categories + + + + option.label} + defaultValue={[new_category[0], new_category[1]]} + filterSelectedOptions + renderInput={(params) => } + /> + + {/* */} + + Add product to a category. + + + + + + {/* 1 */} + + Tags + + + option.label} + defaultValue={[new_tags[1], new_category[2]]} + filterSelectedOptions + renderInput={(params) => } + /> + {/* */} + + Add product to a category. + + + + ) + ); +}; + +export default ProductDetails; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/ProductTemplate.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/ProductTemplate.tsx new file mode 100644 index 0000000..a30d6a6 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/ProductTemplate.tsx @@ -0,0 +1,39 @@ + +import { useState } from 'react'; +import Box from '@mui/material/Box'; +import { Grid2 as Grid, MenuItem, Typography } from '@mui/material'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; + +const ProductTemplate = () => { + const [age, setAge] = useState('1'); + const handleChange = (event: any) => { + setAge(event.target.value); + }; + + return ( + ( + + Product Template + + + + + Select a product template + + + Default Template + Fashion + Office Stationary + Electronics + + + Assign a template from your current theme to define how a single product is displayed. + + + + ) + ); +}; + +export default ProductTemplate; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Status.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Status.tsx new file mode 100644 index 0000000..013cc91 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Status.tsx @@ -0,0 +1,53 @@ + +import { useState } from 'react'; +import Box from '@mui/material/Box'; +import { Grid2 as Grid, Typography } from '@mui/material'; +import { MenuItem, Avatar } from '@mui/material'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; + +const StatusCard = () => { + const [status, setStatus] = useState(2); + const handleChange = (event: any) => { + setStatus(event.target.value); + console.log('test'); + }; + + return ( + ( + + Status + + + + + + + Published + Draft + Scheduled + In active + + Set the product status. + + + ) + ); +}; + +export default StatusCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Thumbnail.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Thumbnail.tsx new file mode 100644 index 0000000..3ec9ffd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/Thumbnail.tsx @@ -0,0 +1,76 @@ + +import React, { useState, useRef } from 'react'; +import Box from '@mui/material/Box'; +import { Typography } from '@mui/material'; + +import img4 from 'src/assets/images/blog/blog-img1.jpg'; + +const Thumbnail = () => { + const [imageFile, setImageFile] = useState(null); + const [imageUrl, setImageUrl] = useState(img4); + const fileInputRef = useRef(null); + + // Open file input dialog on image click + const handleImageClick = () => { + fileInputRef.current?.click(); + }; + + const handleFileChange = (event: React.ChangeEvent) => { + const file = event.target.files?.[0]; + + if (!file) return; + + // Validate file size and type (optional) + if (file.size > 1024 * 1024 * 5) { + alert('File size is too large! Max 5MB allowed.'); + return; + } + + // Read and display image preview + const reader = new FileReader(); + reader.onload = (e: any) => { + setImageUrl(e.target?.result as string); + }; + reader.readAsDataURL(file); + + // Set the image file for upload + setImageFile(file); + console.log(imageFile); + }; + + return ( + + Thumbnail + + + + {imageUrl ? ( + + Preview + + ) : null} + + + Click on image to change + + + + ); +}; + +export default Thumbnail; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/VariationCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/VariationCard.tsx new file mode 100644 index 0000000..41e1552 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productEdit/VariationCard.tsx @@ -0,0 +1,64 @@ + +import { useState } from 'react'; +import Box from '@mui/material/Box'; +import { Button, Grid2 as Grid, Tooltip, MenuItem } from '@mui/material'; +import { Typography } from '@mui/material'; + +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import { IconX } from '@tabler/icons-react'; +import { IconPlus } from '@tabler/icons-react'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; + +const VariationCard = () => { + const [age, setAge] = useState('4'); + const handleChange = (event: any) => { + setAge(event.target.value); + }; + + return ( + ( + Variation + Add Product Variations + + + + Size + XS + SM + MD + LG + XL + + + + + + + + + + + + + ) + ); +}; + +export default VariationCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductFilter.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductFilter.tsx new file mode 100644 index 0000000..5c91df4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductFilter.tsx @@ -0,0 +1,299 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useDispatch, useSelector } from 'src/store/Store'; +import { + ListItemText, + ListItemButton, + List, + Divider, + FormGroup, + ListItemIcon, + FormControlLabel, + Radio, + Typography, + Box, + Avatar, + Button, + Stack +} from '@mui/material'; +import { + filterProducts, + sortByProducts, + sortByGender, + sortByColor, + sortByPrice, + filterReset, +} from 'src/store/apps/eCommerce/ECommerceSlice'; +import { + IconHanger, + IconCircles, + IconNotebook, + IconMoodSmile, + IconDeviceLaptop, + IconSortAscending2, + IconSortDescending2, + IconAd2, + IconCheck +} from '@tabler/icons-react'; +import { ProductFiterType } from 'src/types/apps/eCommerce'; + +const ProductFilter = () => { + const dispatch = useDispatch(); + const products = useSelector((state) => state.ecommerceReducer.products); + const active = useSelector((state) => state.ecommerceReducer.filters); + const checkactive = useSelector((state) => state.ecommerceReducer.sortBy); + const customizer = useSelector((state) => state.customizer); + const br = `${customizer.borderRadius}px`; + + const getUniqueData = (data: string[], attr: any) => { + let newVal = data.map((curElem) => { + return curElem[attr]; + }); + if (attr === 'colors') { + newVal = newVal.flat(); + } + + return (newVal = ['All', ...Array.from(new Set(newVal))]); + }; + + const filterbyGender = getUniqueData(products, 'gender'); + const filterbyColors = getUniqueData(products, 'colors'); + + const filterCategory: ProductFiterType[] = [ + { + id: 1, + filterbyTitle: 'Filter by Category', + }, + { + id: 2, + name: 'All', + sort: 'All', + icon: IconCircles, + }, + { + id: 3, + name: 'Fashion', + sort: 'fashion', + icon: IconHanger, + }, + { + id: 9, + name: 'Books', + sort: 'books', + icon: IconNotebook, + }, + { + id: 10, + name: 'Toys', + sort: 'toys', + icon: IconMoodSmile, + }, + { + id: 11, + name: 'Electronics', + sort: 'electronics', + icon: IconDeviceLaptop, + }, + { + id: 6, + devider: true, + }, + ]; + const filterbySort = [ + { id: 1, value: 'newest', label: 'Newest', icon: IconAd2 }, + { id: 2, value: 'priceDesc', label: 'Price: High-Low', icon: IconSortAscending2 }, + { id: 3, value: 'priceAsc', label: 'Price: Low-High', icon: IconSortDescending2 }, + { id: 4, value: 'discount', label: 'Discounted', icon: IconAd2 }, + ]; + const filterbyPrice = [ + { + id: 0, + label: 'All', + value: 'All', + }, + { + id: 1, + label: '0-50', + value: '0-50', + }, + { + id: 3, + label: '50-100', + value: '50-100', + }, + { + id: 4, + label: '100-200', + value: '100-200', + }, + { + id: 5, + label: 'Over 200', + value: '200-99999', + }, + ]; + + const handlerGenderFilter = (value: React.ChangeEvent) => { + if (value.target.checked) { + dispatch(sortByGender({ gender: value.target.value })); + } + }; + const handlerPriceFilter = (value: React.ChangeEvent) => { + if (value.target.checked) { + dispatch(sortByPrice({ price: value.target.value })); + } + }; + + return ( + <> + + {/* ------------------------------------------- */} + {/* Category filter */} + {/* ------------------------------------------- */} + {filterCategory.map((filter) => { + if (filter.filterbyTitle) { + return ( + + {filter.filterbyTitle} + + ); + } else if (filter.devider) { + return ; + } + + return ( + dispatch(filterProducts({ category: `${filter.sort}` }))} + key={filter.id} + > + + + + {filter.name} + + ); + })} + {/* ------------------------------------------- */} + {/* Sort by */} + {/* ------------------------------------------- */} + + Sort By + + {filterbySort.map((filter) => { + return ( + dispatch(sortByProducts(`${filter.value}`))} + key={filter.id + filter.label + filter.value} + > + + + + {filter.label} + + ); + })} + + {/* ------------------------------------------- */} + {/* Filter By Gender */} + {/* ------------------------------------------- */} + + + By Gender + +
+ + {filterbyGender.map((gen) => ( + + } + label={gen} + /> + ))} + +
+ + {/* ------------------------------------------- */} + {/* Filter By Pricing */} + {/* ------------------------------------------- */} + + By Pricing + + + + {filterbyPrice.map((price) => ( + + } + label={price.label} + /> + ))} + + + + + By Colors + + {/* ------------------------------------------- */} + {/* Filter By colors */} + {/* ------------------------------------------- */} + + + {filterbyColors.map((curColor) => { + if (curColor !== 'All') { + return ( + dispatch(sortByColor({ color: 'All' })) + : () => dispatch(sortByColor({ color: curColor })) + } + > + {active.color === curColor ? : ''} + + ); + } else { + return ; + } + })} + + + + {/* ------------------------------------------- */} + {/* Reset */} + {/* ------------------------------------------- */} + + + +
+ + ); +}; + +export default ProductFilter; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductList.tsx new file mode 100644 index 0000000..0432401 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductList.tsx @@ -0,0 +1,251 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { filter, orderBy } from 'lodash'; +import { + Box, + Grid2 as Grid, + Stack, + CardContent, + useMediaQuery, + Typography, + Rating, + Fab, + Tooltip, + Button, + Theme, + Skeleton, +} from '@mui/material'; +import { Link } from 'react-router'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { + fetchProducts, + addToCart, + filterReset, +} from '../../../../store/apps/eCommerce/ECommerceSlice'; +import ProductSearch from './ProductSearch'; +import { IconBasket, IconMenu2 } from '@tabler/icons-react'; +import AlertCart from '../productCart/AlertCart'; +import emptyCart from 'src/assets/images/products/empty-shopping-cart.svg'; +import BlankCard from '../../../shared/BlankCard'; +import { ProductType } from 'src/types/apps/eCommerce'; + +interface Props { + onClick: (event: React.SyntheticEvent | Event) => void; +} + +const ProductList = ({ onClick }: Props) => { + const dispatch = useDispatch(); + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + + useEffect(() => { + dispatch(fetchProducts()); + }, [dispatch]); + + const getVisibleProduct = ( + products: ProductType[], + sortBy: string, + filters: any, + search: string, + ) => { + // SORT BY + if (sortBy === 'newest') { + products = orderBy(products, ['created'], ['desc']); + } + if (sortBy === 'priceDesc') { + products = orderBy(products, ['price'], ['desc']); + } + if (sortBy === 'priceAsc') { + products = orderBy(products, ['price'], ['asc']); + } + if (sortBy === 'discount') { + products = orderBy(products, ['discount'], ['desc']); + } + + // FILTER PRODUCTS + if (filters.category !== 'All') { + //products = filter(products, (_product) => includes(_product.category, filters.category)); + products = products.filter((_product) => _product.category.includes(filters.category)); + } + + //FILTER PRODUCTS BY GENDER + if (filters.gender !== 'All') { + products = filter(products, (_product) => _product.gender === filters.gender); + } + + //FILTER PRODUCTS BY GENDER + if (filters.color !== 'All') { + products = products.filter((_product) => _product.colors.includes(filters.color)); + } + + //FILTER PRODUCTS BY Search + if (search !== '') { + products = products.filter((_product) => + _product.title.toLocaleLowerCase().includes(search.toLocaleLowerCase()), + ); + } + + //FILTER PRODUCTS BY Price + if (filters.price !== 'All') { + const minMax = filters.price ? filters.price.split('-') : ''; + products = products.filter((_product) => + filters.price ? _product.price >= minMax[0] && _product.price <= minMax[1] : true, + ); + } + + return products; + }; + + const getProducts = useSelector((state) => + getVisibleProduct( + state.ecommerceReducer.products, + state.ecommerceReducer.sortBy, + state.ecommerceReducer.filters, + state.ecommerceReducer.productSearch, + ), + ); + + // for alert when added something to cart + const [cartalert, setCartalert] = React.useState(false); + + const handleClick = () => { + setCartalert(true); + }; + + const handleClose = (reason: string) => { + if (reason === 'clickaway') { + return; + } + setCartalert(false); + }; + + // skeleton + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 1000); + + return () => clearTimeout(timer); + }, []); + + return ( + ( + {/* ------------------------------------------- */} + {/* Header Detail page */} + {/* ------------------------------------------- */} + + {lgUp ? ( + Products + ) : ( + + + + )} + + + + + {/* ------------------------------------------- */} + {/* Page Listing product */} + {/* ------------------------------------------- */} + + {getProducts.length > 0 ? ( + <> + {getProducts.map((product) => ( + + {/* ------------------------------------------- */} + {/* Product Card */} + {/* ------------------------------------------- */} + {isLoading ? ( + <> + theme.shape.borderRadius / 5 }} + > + + ) : ( + + + img + + + dispatch(addToCart(product)) && handleClick()} + sx={{ bottom: '75px', right: '15px', position: 'absolute' }} + > + + + + + {product.title} + + + ${product.price} + + ${product.salesPrice} + + + + + + + )} + + {/* ------------------------------------------- */} + {/* Product Card */} + {/* ------------------------------------------- */} + + ))} + + ) : ( + <> + + + cart + There is no Product + + The Product you are searching is no longer available. + + + + + + )} + + ) + ); +}; + +export default ProductList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductSearch.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductSearch.tsx new file mode 100644 index 0000000..a43ef19 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductSearch.tsx @@ -0,0 +1,36 @@ +// material +import { TextField, InputAdornment } from '@mui/material'; +import { IconSearch } from '@tabler/icons-react'; + +// redux +import { useDispatch } from 'src/store/Store'; +import { SearchProduct } from 'src/store/apps/eCommerce/ECommerceSlice'; + +// ---------------------------------------------------------------------- +export default function ProductSearch() { + const dispatch = useDispatch(); + + return ( + <> + {/* ------------------------------------------- */} + {/* Sort Button */} + {/* ------------------------------------------- */} + + + + ), + }} + fullWidth + onChange={(e) => dispatch(SearchProduct(e.target.value))} + /> + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductSidebar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductSidebar.tsx new file mode 100644 index 0000000..a792d40 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/ecommerce/productGrid/ProductSidebar.tsx @@ -0,0 +1,39 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Drawer, Theme, useMediaQuery } from '@mui/material'; + +import ProductFilter from './ProductFilter'; + +const drawerWidth = 250; + +interface Props { + isMobileSidebarOpen: boolean; + onSidebarClose: (event: React.SyntheticEvent | Event) => void; +} + +const ProductSidebar = ({ isMobileSidebarOpen, onSidebarClose }: Props) => { + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + + return ( + + {/* ------------------------------------------- */} + {/* Filter Sidebar */} + {/* ------------------------------------------- */} + + + ); +}; + + +export default ProductSidebar; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailActions.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailActions.tsx new file mode 100644 index 0000000..4ebd13c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailActions.tsx @@ -0,0 +1,28 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, Button, ButtonGroup } from '@mui/material'; +import { IconFolder, IconActivity, IconTag } from '@tabler/icons-react'; + +const EmailActions = () => { + return ( + + + {/* ------------------------------------------- */} + {/* Action buttons */} + {/* ------------------------------------------- */} + + + + + + ); +}; + +export default EmailActions; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailCompose.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailCompose.tsx new file mode 100644 index 0000000..8280364 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailCompose.tsx @@ -0,0 +1,101 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { + Button, + Box, + Dialog, + DialogTitle, + Slide, + TextField, + DialogContent, + DialogActions, + DialogContentText, +} from '@mui/material'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import { TransitionProps } from '@mui/material/transitions'; + +const Transition = React.forwardRef(function Transition( + props: TransitionProps & { + children: React.ReactElement; + }, + ref: React.Ref, +) { + return ; +}); + +const EmailCompose = () => { + const [open, setOpen] = useState(false); + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + + return ( + + {/* ------------------------------------------- */} + {/* Compose Email */} + {/* ------------------------------------------- */} + + + + {/* ------------------------------------------- */} + {/* Dialog for compose */} + {/* ------------------------------------------- */} + + + Compose Mail + + + + To + + Subject + + Message + + Attachment + + + + + + + + + + ); +}; + +export default EmailCompose; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailContent.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailContent.tsx new file mode 100644 index 0000000..99c603c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailContent.tsx @@ -0,0 +1,190 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { + Box, + Avatar, + Typography, + Chip, + Button, + Divider, + Stack, + IconButton, + Grid2 as Grid, + Tooltip, + Paper, + useTheme +} from '@mui/material'; +import { EmailType } from 'src/types/apps/email'; +import { IconStar, IconAlertCircle, IconTrash } from '@tabler/icons-react'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { starEmail, importantEmail, deleteEmail } from '../../../store/apps/email/EmailSlice'; +import emailIcon from 'src/assets/images/breadcrumb/emailSv.png'; + +import TiptapEdit from 'src/views/forms/from-tiptap/TiptapEdit' + + +const EmailContent = () => { + const emailDetails: EmailType = useSelector( + (state) => state.emailReducer.emails[state.emailReducer.emailContent - 1], + ); + + const [show, setShow] = useState(false); + + + const toggleEditor = () => { + setShow(!show); + }; + + const dispatch = useDispatch(); + + const theme = useTheme(); + + const warningColor = theme.palette.warning.main; + const errorColor = theme.palette.error.light; + + return emailDetails && !emailDetails.trash ? ( + + + + dispatch(starEmail(emailDetails.id))}> + + + + + dispatch(importantEmail(emailDetails.id))}> + + + + + dispatch(deleteEmail(emailDetails.id))}> + + + + + + + {/* ------------------------------------------- */} + {/* Email Detail page */} + {/* ------------------------------------------- */} + + + + {emailDetails.from} + {emailDetails.To} + + + + {/* ------------------------------------------- */} + {/* Email Detail page */} + {/* ------------------------------------------- */} + + + {emailDetails.subject} + + + +
+ + + {emailDetails?.attchments?.length == 0 ? null : ( + <> + + + Attachments ({emailDetails?.attchments?.length}) + + + {emailDetails.attchments?.map((attach) => { + return ( + ( + + theme.palette.grey[100] }} + > + + + + + {attach.title} + + {attach.fileSize} + + + ) + ); + })} + + + + + )} + + + + + + + + {/* Editor */} + {show ? ( + + + + + + ) : null} + + + ) : ( + + {/* ------------------------------------------- */} + {/* If no Email */} + {/* ------------------------------------------- */} + + Please Select a Mail +
+ {emailIcon} +
+
+ ); +}; + +export default EmailContent; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailFilter.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailFilter.tsx new file mode 100644 index 0000000..5e6597c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailFilter.tsx @@ -0,0 +1,180 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { + ListItemText, + ListItemButton, + List, + Divider, + ListItemIcon, + Box, + Typography, +} from '@mui/material'; + +import { setVisibilityFilter } from '../../../store/apps/email/EmailSlice'; +import EmailCompose from './EmailCompose'; +import Scrollbar from 'src/components/custom-scroll/Scrollbar'; +import { + IconMail, + IconSend, + IconFlag, + IconTrash, + IconStar, + IconAlertCircle, + IconFolder, + IconNote, +} from '@tabler/icons-react'; +import { GeneralIcon } from 'src/types/apps/icon'; + +interface fitlerType { + id?: number; + filterbyTitle?: string; + icon?: GeneralIcon | any; + name?: string; + divider?: boolean; + color?: string; +} + +const EmailFilter = () => { + const active = useSelector((state) => state.emailReducer.currentFilter); + const customizer = useSelector((state) => state.customizer); + const br = `${customizer.borderRadius}px`; + + const dispatch = useDispatch(); + const filterData: fitlerType[] = [ + { + id: 2, + name: 'inbox', + icon: IconMail, + color: 'inherit', + }, + { + id: 3, + name: 'sent', + icon: IconSend, + color: 'inherit', + }, + { + id: 4, + name: 'draft', + icon: IconNote, + color: 'inherit', + }, + { + id: 4, + name: 'spam', + icon: IconFlag, + color: 'inherit', + }, + { + id: 5, + name: 'trash', + icon: IconTrash, + color: 'inherit', + }, + { + id: 6, + divider: true, + }, + { + id: 1, + filterbyTitle: 'Sort By', + }, + { + id: 7, + name: 'starred', + icon: IconStar, + color: 'inherit', + }, + { + id: 8, + name: 'important', + icon: IconAlertCircle, + color: 'inherit', + }, + { + id: 9, + divider: true, + }, + { + id: 13, + filterbyTitle: 'Labels', + }, + { + id: 10, + name: 'Promotional', + icon: IconFolder, + color: 'primary.main', + }, + { + id: 11, + name: 'Social', + icon: IconFolder, + color: 'error.main', + }, + { + id: 12, + name: 'Health', + icon: IconFolder, + color: 'success.main', + }, + ]; + + return ( + <> + + {/* ------------------------------------------- */} + {/* Email compose */} + {/* ------------------------------------------- */} + + + + + {filterData.map((filter) => { + if (filter.filterbyTitle) { + return ( + + {filter.filterbyTitle} + + ); + } else if (filter.divider) { + return ; + } + + return ( + dispatch(setVisibilityFilter(`${filter.name}`))} + key={`${filter.id}${filter.name}`} + > + {/* ------------------------------------------- */} + {/* If list to filter */} + {/* ------------------------------------------- */} + + + + {filter.name} + + ); + })} + + + + ); +}; + +export default EmailFilter; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailList.tsx new file mode 100644 index 0000000..21bd893 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailList.tsx @@ -0,0 +1,118 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { List } from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import EmailListItem from './EmailListItem'; +import { + fetchEmails, + SelectEmail, + starEmail, + importantEmail, + deleteEmail, + checkEmail, +} from '../../../store/apps/email/EmailSlice'; +import Scrollbar from 'src/components/custom-scroll/Scrollbar'; +import { EmailType } from 'src/types/apps/email'; + +interface Props { + showrightSidebar: React.MouseEventHandler; +} + +const EmailList = ({ showrightSidebar }: Props) => { + const dispatch = useDispatch(); + + useEffect(() => { + dispatch(fetchEmails()); + }, [dispatch]); + + const getVisibleEmail = (emails: EmailType[], filter: string, emailSearch: string) => { + switch (filter) { + case 'inbox': + return emails.filter( + (t) => t.inbox && !t.trash && t.from.toLocaleLowerCase().includes(emailSearch), + ); + case 'sent': + return emails.filter( + (t) => t.sent && !t.trash && t.from.toLocaleLowerCase().includes(emailSearch), + ); + case 'draft': + return emails.filter( + (t) => t.draft && !t.trash && t.from.toLocaleLowerCase().includes(emailSearch), + ); + case 'spam': + return emails.filter( + (t) => t.spam && !t.trash && t.from.toLocaleLowerCase().includes(emailSearch), + ); + case 'trash': + return emails.filter((t) => t.trash && t.from.toLocaleLowerCase().includes(emailSearch)); + case 'starred': + return emails.filter( + (t) => t.starred && !t.trash && t.from.toLocaleLowerCase().includes(emailSearch), + ); + case 'important': + return emails.filter( + (t) => t.important && !t.trash && t.from.toLocaleLowerCase().includes(emailSearch), + ); + case 'Promotional': + return emails.filter( + (t) => + t.label === 'Promotional' && + !t.trash && + t.from.toLocaleLowerCase().includes(emailSearch), + ); + case 'Social': + return emails.filter( + (t) => + t.label === 'Social' && !t.trash && t.from.toLocaleLowerCase().includes(emailSearch), + ); + case 'Health': + return emails.filter( + (t) => + t.label === 'Health' && !t.trash && t.from.toLocaleLowerCase().includes(emailSearch), + ); + default: + throw new Error(`Unknown filter: ${filter}`); + } + }; + + const emails = useSelector((state) => + getVisibleEmail( + state.emailReducer.emails, + state.emailReducer.currentFilter, + state.emailReducer.emailSearch, + ), + ); + + const active = useSelector((state) => state.emailReducer.emailContent); + + return ( + + + {/* ------------------------------------------- */} + {/* Email page */} + {/* ------------------------------------------- */} + {emails.map((email) => ( + { + dispatch(SelectEmail(email.id)); + showrightSidebar; + }} + onDelete={() => dispatch(deleteEmail(email.id))} + isSelected={email.id === active} + onStar={() => dispatch(starEmail(email.id))} + onImportant={() => dispatch(importantEmail(email.id))} + onChange={(e) => { + if (e.target.checked === true) dispatch(checkEmail(email.id)); + else dispatch(checkEmail(email.id)); + }} + /> + ))} + + + ); +}; + +export default EmailList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailListItem.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailListItem.tsx new file mode 100644 index 0000000..46706b4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailListItem.tsx @@ -0,0 +1,120 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +import { + ListItemText, + ListItemIcon, + Chip, + ListItemButton, + Typography, + Stack, + useTheme, +} from '@mui/material'; +import CustomCheckbox from 'src/components/forms/theme-elements/CustomCheckbox'; +import { IconAlertCircle, IconStar, IconTrash } from '@tabler/icons-react'; +import { formatDistanceToNowStrict } from 'date-fns'; + +interface EmailListType { + id: number; + from: string; + subject: string; + time: string; + unread: boolean; + starred: boolean; + important: boolean; + label: string; + onClick: React.MouseEventHandler; + onChange: React.ChangeEventHandler; + onStar: React.MouseEventHandler; + onImportant: React.MouseEventHandler; + onDelete: React.MouseEventHandler; + checked?: boolean; + isSelected: boolean; +} + +const EmailListItem = ({ + id, + onClick, + onChange, + onStar, + onImportant, + from, + subject, + time, + checked, + label, + starred, + onDelete, + important, + isSelected, +}: EmailListType) => { + const theme = useTheme(); + + const warningColor = theme.palette.warning.main; + const errorColor = theme.palette.error.light; + + return ( + + + + + {/* ------------------------------------------- */} + {/* Email page */} + {/* ------------------------------------------- */} + + + + {from} + + + + + {subject} + + {/* ------------------------------------------- */} + {/* Email page */} + {/* ------------------------------------------- */} + + + + + {/* ------------------------------------------- */} + {/* Checked ? */} + {/* ------------------------------------------- */} + {checked ? : ''} + + { } + {formatDistanceToNowStrict(new Date(time), { + addSuffix: false, + })}{' '} + ago + + + + + ); +}; + +export default EmailListItem; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailSearch.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailSearch.tsx new file mode 100644 index 0000000..791d978 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/email/EmailSearch.tsx @@ -0,0 +1,53 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { Box, Fab, TextField, InputAdornment } from '@mui/material'; +import { SearchEmail } from '../../../store/apps/email/EmailSlice'; +import { IconMenu2, IconSearch } from '@tabler/icons-react'; + +interface Props { + onClick: React.MouseEventHandler; +} + +const EmailSearch = ({ onClick }: Props) => { + const searchTerm = useSelector((state) => state.emailReducer.emailSearch); + const dispatch = useDispatch(); + + return ( + + {/* ------------------------------------------- */} + {/* Button toggle sidebar when lgdown */} + {/* ------------------------------------------- */} + + + + {/* ------------------------------------------- */} + {/* Search */} + {/* ------------------------------------------- */} + + + + ), + }} + fullWidth + size="small" + value={searchTerm} + placeholder="Search emails" + variant="outlined" + onChange={(e) => dispatch(SearchEmail(e.target.value))} + /> + + ); +}; + +export default EmailSearch; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Add-invoice/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Add-invoice/index.tsx new file mode 100644 index 0000000..23697a4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Add-invoice/index.tsx @@ -0,0 +1,443 @@ + +import React, { useState, useContext, useEffect } from 'react'; +import { InvoiceContext } from 'src/context/InvoiceContext'; +import { + Alert, + Button, + MenuItem, + Table, + TableBody, + TableCell, + TableContainer, + TableHead, + TableRow, + Paper, + Typography, + IconButton, + Tooltip, + Box, + Stack, + Divider, + Grid2 as Grid, +} from '@mui/material'; +import { useNavigate } from 'react-router'; +import { format, isValid } from 'date-fns'; +import { IconPlus, IconSquareRoundedPlus, IconTrash } from '@tabler/icons-react'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; + +const CreateInvoice = () => { + const { addInvoice, invoices } = useContext(InvoiceContext); + const [showAlert, setShowAlert] = useState(false); + const router = useNavigate(); + const [formData, setFormData] = useState({ + id: 0, + billFrom: '', + billTo: '', + totalCost: 0, + status: 'Pending', + billFromAddress: '', + billToAddress: '', + orders: [{ itemName: '', unitPrice: '', units: '', unitTotalPrice: 0 }], + vat: 0, + grandTotal: 0, + subtotal: 0, + date: new Date().toISOString().split('T')[0], + }); + + useEffect(() => { + if (invoices.length > 0) { + const lastId = invoices[invoices.length - 1].id; + setFormData((prevData: any) => ({ + ...prevData, + id: lastId + 1, + })); + } else { + setFormData((prevData: any) => ({ + ...prevData, + id: 1, + })); + } + }, [invoices]); + + const calculateTotals = (orders: any[]) => { + let subtotal = 0; + + orders.forEach((order) => { + const unitPrice = parseFloat(order.unitPrice) || 0; + const units = parseInt(order.units) || 0; + const totalCost = unitPrice * units; + + subtotal += totalCost; + order.unitTotalPrice = totalCost; + }); + + const vat = subtotal * 0.1; + const grandTotal = subtotal + vat; + + return { subtotal, vat, grandTotal }; + }; + + const handleChange = (e: { target: { name: any; value: any } }) => { + const { name, value } = e.target; + setFormData((prevData) => { + const newFormData = { ...prevData, [name]: value }; + const totals = calculateTotals(newFormData.orders); + return { + ...newFormData, + ...totals, + }; + }); + }; + + const handleOrderChange = (index: number, field: string, value: string) => { + setFormData((prevData) => { + const updatedOrders = [...prevData.orders]; + updatedOrders[index] = { + ...updatedOrders[index], + [field]: value, + }; + const totals = calculateTotals(updatedOrders); + return { + ...prevData, + orders: updatedOrders, + ...totals, + }; + }); + }; + + const handleAddItem = () => { + setFormData((prevData) => { + const updatedOrders = [ + ...prevData.orders, + { itemName: '', unitPrice: '', units: '', unitTotalPrice: 0 }, + ]; + const totals = calculateTotals(updatedOrders); + return { + ...prevData, + orders: updatedOrders, + ...totals, + }; + }); + }; + + const handleDeleteItem = (index: number) => { + setFormData((prevData) => { + const updatedOrders = prevData.orders.filter((_, i) => i !== index); + const totals = calculateTotals(updatedOrders); + return { + ...prevData, + orders: updatedOrders, + ...totals, + }; + }); + }; + + const handleSubmit = async (e: React.FormEvent) => { + e.preventDefault(); + try { + await addInvoice(formData); + setFormData({ + id: 0, + billFrom: '', + billTo: '', + totalCost: 0, + status: 'Pending', + billFromAddress: '', + billToAddress: '', + orders: [{ itemName: '', unitPrice: '', units: '', unitTotalPrice: 0 }], + vat: 0, + grandTotal: 0, + subtotal: 0, + date: new Date().toISOString().split('T')[0], + }); + setShowAlert(true); + setTimeout(() => { + setShowAlert(false); + }, 5000); + router('/apps/invoice/list'); + } catch (error) { + console.error('Error adding invoice:', error); + } + }; + + const parsedDate = isValid(new Date(formData.date)) ? new Date(formData.date) : new Date(); + const formattedOrderDate = format(parsedDate, 'EEEE, MMMM dd, yyyy'); + + return (<> +
+ + + # {formData.id} + + + + + + + + + Order Status + + + Pending + Shipped + Delivered + + + + Order Date + {formattedOrderDate} + + + + + + + Bill From + + + + + Bill To + + + + + + From Address + + + + + + Bill To Address + + + + + {/* Orders Table */} + + Items Details : + + + + + + + + + + + Item Name + + + + + Unit Price + + + + + Units + + + + + Total Cost + + + + + + Actions + + + + + + {formData.orders.map((order, index) => ( + + + + handleOrderChange(index, 'itemName', e.target.value) + } + fullWidth + /> + + + + handleOrderChange(index, 'unitPrice', e.target.value) + } + fullWidth + /> + + + handleOrderChange(index, 'units', e.target.value)} + fullWidth + /> + + + {order.unitTotalPrice} + + + + + + + + + + handleDeleteItem(index)} color="error"> + + + + + + ))} + +
+
+
+ + {/* Totals */} + + + + Sub Total: + + + {formData.subtotal} + + + + + VAT: + + + {formData.vat} + + + + + Grand Total: + + + {formData.grandTotal} + + + + + {showAlert && ( + + Invoice added successfully. + + )} +
+
+ ); +}; + +export default CreateInvoice; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Edit-invoice/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Edit-invoice/index.tsx new file mode 100644 index 0000000..0f016ca --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Edit-invoice/index.tsx @@ -0,0 +1,429 @@ + +import { useContext, useState, useEffect } from 'react'; +import { InvoiceContext } from 'src/context/InvoiceContext/index'; +import { useLocation, useNavigate } from 'react-router'; +import { + Button, + MenuItem, + Typography, + Table, + TableBody, + TableCell, + TableContainer, + TableHead, + TableRow, + Paper, + Alert, + IconButton, + Tooltip, + Box, + Stack, + Divider, + Grid2 as Grid, +} from '@mui/material'; +import { format, isValid } from 'date-fns'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import { IconSquareRoundedPlus, IconTrash } from '@tabler/icons-react'; + +const EditInvoicePage = () => { + const { invoices, updateInvoice } = useContext(InvoiceContext); + const [showAlert, setShowAlert] = useState(false); + const [selectedInvoice, setSelectedInvoice] = useState(null); + const [editing, setEditing] = useState(false); + const [editedInvoice, setEditedInvoice]: any = useState(null); + + const title = useLocation(); + const getTitle = title.pathname.split('/').pop(); + + useEffect(() => { + if (invoices.length > 0) { + // If there's a specific item to edit, use it + if (getTitle) { + const invoice = invoices.find((inv: { billFrom: string }) => inv.billFrom === getTitle); + if (invoice) { + setSelectedInvoice(invoice); + setEditedInvoice({ ...invoice }); + setEditing(true); + } else { + // If specific item not found, fallback to default + setSelectedInvoice(invoices[0]); + setEditedInvoice({ ...invoices[0] }); + setEditing(true); + } + } else { + // No specific item, default to the first invoice + setSelectedInvoice(invoices[0]); + setEditedInvoice({ ...invoices[0] }); + setEditing(true); + } + } + }, [getTitle, invoices]); + + const router = useNavigate(); + + const handleSave = async () => { + try { + await updateInvoice(editedInvoice); + setSelectedInvoice({ ...editedInvoice }); + setEditing(false); // Exit editing mode + setShowAlert(true); + + // Navigate to the list page + router('/apps/invoice/list'); + } catch (error) { + console.error('Error updating invoice:', error); + } + + setTimeout(() => { + setShowAlert(false); + }, 5000); + }; + + const handleCancel = () => { + setEditing(false); + }; + + const handleOrderChange = ( + index: string | number | any, + field: string, + value: string | number, + ) => { + const updatedOrders = [...editedInvoice.orders]; + updatedOrders[index][field] = value; + + // Calculate unitTotalPrice for the changed item + if (field === 'unitPrice' || field === 'units') { + updatedOrders[index].unitTotalPrice = + updatedOrders[index].unitPrice * updatedOrders[index].units; + } + + // Update editedInvoice with updated orders and recalculate totals + const updatedInvoice = { + ...editedInvoice, + orders: updatedOrders, + totalCost: calculateTotalCost(updatedOrders), + vat: calculateVAT(updatedOrders), + grandTotal: calculateGrandTotal( + calculateTotalCost(updatedOrders), + calculateVAT(updatedOrders), + ), + }; + + setEditedInvoice(updatedInvoice); + }; + + const handleAddItem = () => { + const newItem = { + itemName: '', + unitPrice: 0, + units: 0, + unitTotalPrice: 0, + vat: 0, + }; + const updatedOrders = [...editedInvoice.orders, newItem]; + + // Update editedInvoice with updated orders and recalculate totals + const updatedInvoice = { + ...editedInvoice, + orders: updatedOrders, + totalCost: calculateTotalCost(updatedOrders), + vat: calculateVAT(updatedOrders), + grandTotal: calculateGrandTotal( + calculateTotalCost(updatedOrders), + calculateVAT(updatedOrders), + ), + }; + setEditedInvoice(updatedInvoice); + }; + + const handleDeleteItem = (index: any) => { + const updatedOrders = editedInvoice.orders.filter((_: any, i: any) => i !== index); + + const updatedInvoice = { + ...editedInvoice, + orders: updatedOrders, + totalCost: calculateTotalCost(updatedOrders), + vat: calculateVAT(updatedOrders), + grandTotal: calculateGrandTotal( + calculateTotalCost(updatedOrders), + calculateVAT(updatedOrders), + ), + }; + setEditedInvoice(updatedInvoice); + }; + + const calculateTotalCost = (orders: any[]) => { + return orders.reduce((total, order) => total + order.unitTotalPrice, 0); + }; + + const calculateVAT = (orders: any[]) => { + return orders.reduce((totalVAT, order) => totalVAT + order.units, 0); + }; + + const calculateGrandTotal = (totalCost: number, vat: number) => { + return (totalCost += (totalCost * vat) / 100); + }; + + if (!selectedInvoice) { + return
Please select an invoice.
; + } + + const orderDate = selectedInvoice.orderDate; + const parsedDate = isValid(new Date(orderDate)) ? new Date(orderDate) : new Date(); + const formattedOrderDate = format(parsedDate, 'EEEE, MMMM dd, yyyy'); + + return ( + ( + + # {editedInvoice.id} + + {editing ? ( + <> + + + + ) : ( + + )} + + + + + + Order Status + setEditedInvoice({ ...editedInvoice, status: e.target.value })} + > + Pending + Delivered + Shipped + + + + Order Date + {formattedOrderDate} + + + + + + Bill From + setEditedInvoice({ ...editedInvoice, billFrom: e.target.value })} + fullWidth + /> + + + + Bill To + + setEditedInvoice({ ...editedInvoice, billTo: e.target.value })} + fullWidth + /> + + + + From Address + + + setEditedInvoice({ + ...editedInvoice, + billFromAddress: e.target.value, + }) + } + fullWidth + /> + + + + Bill To Address + + + setEditedInvoice({ + ...editedInvoice, + billToAddress: e.target.value, + }) + } + fullWidth + /> + + + + + + + + + + Item Name + + + + + Unit Price + + + + + Units + + + + + Total Cost + + + + + Action + + + + + + {editedInvoice.orders.map((order: any, index: number) => ( + + + handleOrderChange(index, 'itemName', e.target.value)} + fullWidth + /> + + + + handleOrderChange(index, 'unitPrice', parseFloat(e.target.value)) + } + fullWidth + /> + + + + handleOrderChange(index, 'units', parseInt(e.target.value)) + } + fullWidth + /> + + + {order.unitTotalPrice} + + + + + + + + + handleDeleteItem(index)}> + + + + + + ))} + +
+
+
+ + + + Sub Total: + + + {editedInvoice.totalCost} + + + + + VAT: + + + {editedInvoice.vat} + + + + + Grand Total: + + + {editedInvoice.grandTotal} + + + + {showAlert && ( + + Invoice data updated successfully. + + )} +
) + ); +}; + +export default EditInvoicePage; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Invoice-detail/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Invoice-detail/index.tsx new file mode 100644 index 0000000..9079002 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Invoice-detail/index.tsx @@ -0,0 +1,231 @@ + +import React, { useContext, useEffect, useState } from 'react'; +import { InvoiceContext } from 'src/context/InvoiceContext/index'; +import { useLocation } from 'react-router'; +import { + Typography, + Button, + Table, + TableBody, + TableCell, + TableContainer, + TableHead, + TableRow, + Paper, + Box, + Stack, + Chip, + Divider, + Grid2 as Grid, +} from '@mui/material'; +import { format, isValid, parseISO } from 'date-fns'; +import { Link } from 'react-router'; +import Logo from 'src/layouts/full/shared/logo/Logo'; + +const InvoiceDetail = () => { + const { invoices } = useContext(InvoiceContext); + const [selectedInvoice, setSelectedInvoice]: any = useState(null); + + useEffect(() => { + // Set the first invoice as the default selected invoice initially + if (invoices.length > 0) { + setSelectedInvoice(invoices[0]); + } + }, [invoices]); + + // Get the last part of the URL path as the billFrom parameter + const title = useLocation(); + const getTitle = title.pathname.split('/').pop(); + + // Find the invoice that matches the billFrom extracted from the URL + useEffect(() => { + if (getTitle) { + const invoice = invoices.find((p: { billFrom: string }) => p.billFrom === getTitle); + if (invoice) { + setSelectedInvoice(invoice); + } + } + }, [getTitle, invoices]); + + if (!selectedInvoice) { + return
Loading...
; + } + + const orderDate = selectedInvoice.orderDate + ? isValid(parseISO(selectedInvoice.orderDate)) + ? format(parseISO(selectedInvoice.orderDate), 'EEEE, MMMM dd, yyyy') + : 'Invalid Date' + : format(new Date(), 'EEEE, MMMM dd, yyyy'); + + return (<> + + + # {selectedInvoice.id} + + + + + + + + {selectedInvoice.status === 'Shipped' ? ( + + ) : selectedInvoice.status === 'Delivered' ? ( + + ) : selectedInvoice.status === 'Pending' ? ( + + ) : ( + '' + )} + + + + + + + + + From : + + {selectedInvoice.billFrom} + {selectedInvoice.billFromEmail} + {selectedInvoice.billFromAddress} + {selectedInvoice.billFromPhone} + + + + + + + + To : + + {selectedInvoice.billTo} + {selectedInvoice.billToEmail} + {selectedInvoice.billToAddress} + {selectedInvoice.billToPhone} + + + + + + + + + + + + Item Name + + + + + Unit Price + + + + + Unit + + + + + Total Cost + + + + + + {selectedInvoice.orders.map( + ( + order: { + itemName: string; + unitPrice: string; + units: number; + unitTotalPrice: string; + }, + index: React.Key | null | undefined, + ) => ( + + + {order.itemName} + + + {order.unitPrice} + + + {order.units} + + + {order.unitTotalPrice} + + + ), + )} + +
+
+
+ + + + Sub Total: + + + {selectedInvoice.totalCost} + + + + + Vat: + + + {selectedInvoice.vat} + + + + + Grand Total: + + + {selectedInvoice.grandTotal} + + + + + + + + ); +}; + +export default InvoiceDetail; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Invoice-list/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Invoice-list/index.tsx new file mode 100644 index 0000000..d1909fc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/invoice/Invoice-list/index.tsx @@ -0,0 +1,450 @@ + +import { useContext, useState } from "react"; +import { InvoiceContext } from "src/context/InvoiceContext/index"; +import { + Table, + TextField, + Button, + Dialog, + DialogActions, + DialogContent, + DialogTitle, + Tooltip, + IconButton, + TableHead, + TableRow, + TableCell, + TableBody, + Box, + Typography, + Grid2 as Grid, + Stack, + InputAdornment, + Chip, +} from "@mui/material"; +import { + IconEdit, + IconEye, + IconListDetails, + IconSearch, + IconShoppingBag, + IconSortAscending, + IconTrash, + IconTruck, +} from "@tabler/icons-react"; +import CustomCheckbox from "src/components/forms/theme-elements/CustomCheckbox"; +import { Link } from 'react-router'; + +function InvoiceList() { + const { invoices, deleteInvoice } = useContext(InvoiceContext); + const [searchTerm, setSearchTerm] = useState(""); + const [activeTab, setActiveTab] = useState("All"); + const [selectedProducts, setSelectedProducts] = useState([]); + const [selectAll, setSelectAll] = useState(false); + const [openDeleteDialog, setOpenDeleteDialog] = useState(false); + + // Handle status filter change + const handleClick = (status: string) => { + setActiveTab(status); + }; + + // Filter invoices based on search term + const filteredInvoices = invoices.filter( + (invoice: { billFrom: string; billTo: string; status: string }) => { + return ( + (invoice.billFrom.toLowerCase().includes(searchTerm.toLowerCase()) || + invoice.billTo.toLowerCase().includes(searchTerm.toLowerCase())) && + (activeTab === "All" || invoice.status === activeTab) + ); + } + ); + + + + // Calculate the counts for different statuses + const Shipped = invoices.filter( + (t: { status: string }) => t.status === "Shipped" + ).length; + const Delivered = invoices.filter( + (t: { status: string }) => t.status === "Delivered" + ).length; + const Pending = invoices.filter( + (t: { status: string }) => t.status === "Pending" + ).length; + + // Toggle all checkboxes + const toggleSelectAll = () => { + const selectAllValue = !selectAll; + setSelectAll(selectAllValue); + if (selectAllValue) { + setSelectedProducts(invoices.map((invoice: { id: any }) => invoice.id)); + } else { + setSelectedProducts([]); + } + }; + + // Toggle individual product selection + const toggleSelectProduct = (productId: any) => { + const index = selectedProducts.indexOf(productId); + if (index === -1) { + setSelectedProducts([...selectedProducts, productId]); + } else { + setSelectedProducts( + selectedProducts.filter((id: any) => id !== productId) + ); + } + }; + + // Handle opening delete confirmation dialog + const handleDelete = () => { + setOpenDeleteDialog(true); + }; + + // Handle confirming deletion of selected products + const handleConfirmDelete = async () => { + for (const productId of selectedProducts) { + await deleteInvoice(productId); + } + setSelectedProducts([]); + setSelectAll(false); + setOpenDeleteDialog(false); + }; + + // Handle closing delete confirmation dialog + const handleCloseDeleteDialog = () => { + setOpenDeleteDialog(false); + }; + + return ( + ( + + + handleClick("All")} sx={{ cursor: "pointer" }}> + + + + + + + + Total + + {invoices.length} Invoices + + + + + + + handleClick("Shipped")} sx={{ cursor: "pointer" }}> + + + + + + + + Shipped + {Shipped} Invoices + + + + + + handleClick("Delivered")} sx={{ cursor: "pointer" }}> + + + + + + + + Delivered + {Delivered} Invoices + + + + + + handleClick("Pending")} sx={{ cursor: "pointer" }}> + + + + + + + + Pending + {Pending} Invoices + + + + + + + setSearchTerm(e.target.value)} + InputProps={{ + endAdornment: ( + + + + ), + }} + /> + + {selectAll && ( + + )} + + + + + + + + + + + + + Id + + + + + Bill From + + + + + Bill To + + + + + Total Cost + + + + + Status + + + + + Action + + + + + + {filteredInvoices.map( + (invoice: { + id: any; + billFrom: any; + billTo: any; + totalCost: any; + status: any; + }) => ( + + + toggleSelectProduct(invoice.id)} + /> + + + + {invoice.id} + + + + + {invoice.billFrom} + + + + {invoice.billTo} + + + {invoice.totalCost} + + + {invoice.status === "Shipped" ? ( + + ) : invoice.status === "Delivered" ? ( + + ) : invoice.status === "Pending" ? ( + + ) : ( + "" + )} + + + + + + + + + + + + + + { + setSelectedProducts([invoice.id]); + handleDelete(); + }} + > + + + + + + ) + )} + +
+
+ + Confirm Delete + + Are you sure you want to delete selected invoices? + + + + + + +
) + ); +} +export default InvoiceList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/CategoryTaskList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/CategoryTaskList.tsx new file mode 100644 index 0000000..eae6861 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/CategoryTaskList.tsx @@ -0,0 +1,200 @@ + +import { SetStateAction, useContext, useEffect, useState } from 'react'; +import { IconPlus, IconDotsVertical } from '@tabler/icons-react'; +import TaskData from './TaskData'; +import EditCategoryModal from './TaskModal/EditCategoryModal'; +import AddNewTaskModal from './TaskModal/AddNewTaskModal'; +import Menu from '@mui/material/Menu'; +import MenuItem from '@mui/material/MenuItem'; +import { KanbanDataContext } from 'src/context/kanbancontext/index'; +import axios from 'src/utils/axios'; +import { Box, IconButton, Stack, Tooltip, Typography } from '@mui/material'; + +function CategoryTaskList({ id }: any) { + const { todoCategories, deleteCategory, clearAllTasks, deleteTodo } = + useContext(KanbanDataContext); + + const category = todoCategories.find((cat) => cat.id === id) as any; + + const [allTasks, setAllTasks] = useState(category ? category.child : []); + const [showModal, setShowModal] = useState(false); + const [newCategoryName, setNewCategoryName] = useState(category.name); + const [showEditCategoryModal, setShowEditCategoryModal] = useState(false); + const [showContainer, setShowContainer] = useState(true); + const [anchorEl, setAnchorEl] = useState(null); + + const handleClick = (event: any) => { + setAnchorEl(event.currentTarget); + }; + const handleClose = () => { + setAnchorEl(null); + }; + + // Find the category and update tasks + useEffect(() => { + const category = todoCategories.find((cat) => cat.id === id); + if (category) { + setAllTasks(category.child); + } + }, [todoCategories, id]); + + const [newTaskData, setNewTaskData]: any = useState({ + task: '', + taskText: '', + taskProperty: '', + date: new Date().toISOString().split('T')[0], + imageURL: null, + }); + + //Shows the modal for adding a new task. + const handleShowModal = () => { + setShowModal(true); + }; + // Closes the modal + const handleCloseModal = (): any => { + setShowModal(false); + }; + // Shows the modal for editing a category. + const handleShowEditCategoryModal = () => { + handleClose(); + setShowEditCategoryModal(true); + }; + //Closes the modal for editing a category. + const handleCloseEditCategoryModal = () => setShowEditCategoryModal(false); + + //Updates the category name + const handleUpdateCategory = async (updatedName: SetStateAction) => { + try { + const response = await axios.post('/api/TodoData/updateCategory', { + categoryId: id, + categoryName: updatedName, + }); + if (response.status === 200) { + setNewCategoryName(updatedName); + } else { + throw new Error('Failed to update category'); + } + } catch (error) { + console.error('Error updating category:', error); + } + }; + //Adds a new task to the category. + const handleAddTask = async () => { + try { + const response = await axios.post('/api/TodoData/addTask', { + categoryId: id, + newTaskData: { + ...newTaskData, + id: Math.random(), + taskImage: newTaskData.imageURL, + }, + }); + if (response.status === 200) { + setNewTaskData({ + taskText: '', + taskProperty: '', + date: newTaskData.date, + imageURL: '', + }); + handleCloseModal(); + setNewTaskData('Task added successfully'); + console.log('Task added successfully:', response.data); + } else { + throw new Error('Failed to add task'); + } + } catch (error) { + console.error('Error adding task:', error); + } + }; + // Clears all tasks from the current category. + const handleClearAll = () => { + clearAllTasks(id); + setAllTasks([]); + }; + // Deletes a specific task. + const handleDeleteTask = (taskId: number | any) => { + deleteTodo(taskId); + setAllTasks((prevTasks: any[]) => + prevTasks.filter((task: { id: number }) => task.id !== taskId), + ); + }; + //Handles the deletion of the current category. + const handleDeleteClick = () => { + setShowContainer(false); + deleteCategory(id); + }; + + const backgroundColor = category + ? category.name === 'Todo' + ? 'primary.light' + : category.name === 'Progress' + ? 'secondary.light' + : category.name === 'Pending' + ? 'warning.light' + : category.name === 'Done' + ? 'success.light' + : 'primary.light' + : 'primary.light'; + + return ( + <> + + {showContainer && category && ( + + + + {newCategoryName} + + + + {category.name === 'Todo' && ( + <> + + + + + + setAllTasks([...allTasks, newTaskData])} + /> + + )} + + + + + + + + + Edit + Delete + Clear All + + + + {allTasks.map((task: { id: any }, index: number) => ( + handleDeleteTask(task.id)} + index={index} + /> + ))} + + )} + + + ); +} +export default CategoryTaskList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/KanbanHeader.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/KanbanHeader.tsx new file mode 100644 index 0000000..060284f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/KanbanHeader.tsx @@ -0,0 +1,92 @@ +import { useState, useContext } from 'react'; +import { KanbanDataContext } from 'src/context/kanbancontext/index'; +import axios from 'src/utils/axios'; +import { + Dialog, + DialogActions, + DialogContent, + DialogTitle, + Button, + Typography, + Box, + Grid2 as Grid, +} from '@mui/material'; +import CustomFormLabel from '../../forms/theme-elements/CustomFormLabel'; +import CustomTextField from '../../forms/theme-elements/CustomTextField'; + +function KanbanHeader() { + const { addCategory, setError } = useContext(KanbanDataContext); + const [show, setShow] = useState(false); + const [listName, setListName] = useState(''); + + //Closes the modal + const handleClose = () => setShow(false); + //open the modal + const handleShow = () => setShow(true); + + //Handles Add a new category. + const handleSave = async () => { + try { + const response = await axios.post('/api/TodoData/addCategory', { + categoryName: listName, + }); + addCategory(response.data.name); + setListName(''); + setShow(false); + } catch (error: any) { + setError(error.message); + } + }; + + const isAddButtonDisabled = listName.trim().length === 0; + + return (<> + + Improving Work Processes + + + + Add List + + + + List Name + setListName(e.target.value)} + /> + + + + + + + + + ); +} +export default KanbanHeader; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskData.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskData.tsx new file mode 100644 index 0000000..51825fd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskData.tsx @@ -0,0 +1,195 @@ + +import { useContext, useState } from 'react'; +import { IconPencil, IconDotsVertical, IconTrash, IconCalendar } from '@tabler/icons-react'; +import EditTaskModal from './TaskModal/EditTaskModal'; +import { KanbanDataContext } from 'src/context/kanbancontext/index'; +import { Draggable } from '@hello-pangea/dnd'; +import axios from 'src/utils/axios'; +import Menu from '@mui/material/Menu'; +import MenuItem from '@mui/material/MenuItem'; +import { + Box, + Chip, + IconButton, + ListItemIcon, + ListItemText, + Stack, + Typography, +} from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; +import dayjs from 'dayjs'; +interface TaskDataProps { + task: { id: any }; + onDeleteTask: () => void; + index: number; +} +const TaskData: React.FC = ({ task, onDeleteTask, index }: any) => { + const { setError } = useContext(KanbanDataContext); + const [showEditModal, setShowEditModal] = useState(false); + const [editedTask, setEditedTask] = useState(task); + const [anchorEl, setAnchorEl] = useState(null); + + const handleShowEditModal = () => { + handleClose(); + setShowEditModal(true); + }; + const handleCloseEditModal = () => setShowEditModal(false); + + const handleClick = (event: any) => { + setAnchorEl(event.currentTarget); + }; + + const handleClose = () => { + setAnchorEl(null); + }; + + const handleDeleteClick = () => onDeleteTask(task.id); + + const handleSaveEditedTask = async (editedTaskData: { id: any }) => { + try { + const response = await axios.put('/api/TodoData/editTask', { + taskId: editedTaskData.id, + newData: editedTaskData, + }); + if (response.status === 200) { + setEditedTask(editedTaskData); + } else { + throw new Error('Failed to edit task'); + } + } catch (error: any) { + setError(error.message); + } + }; + + // Function to format the date as 'DD MMM' (Day and Month) + const formatDate = (date: string | undefined) => { + if (date) { + // If the date is provided, format it to 'DD MMM' (Day and Month) + const parsedDate = dayjs(date, "DD MMMM", true); // strict parsing mode + if (parsedDate.isValid()) { + return parsedDate.format("DD MMM"); + } else { + // If invalid, try to append the current year + const currentYear = dayjs().year(); + const newDate = `${date} ${currentYear}`; // Example: '24 july 2024' + const correctedDate = dayjs(newDate, "DD MMMM YYYY"); + return correctedDate.isValid() ? correctedDate.format("DD MMM") : dayjs().format("DD MMM"); + } + } else { + // If the date is not provided, return today's date in 'DD MMM' format + return dayjs().format("DD MMM"); + } + }; + + const taskDate = formatDate(editedTask.date); // Get formatted task date + + const backgroundColor = + editedTask.taskProperty === 'Design' + ? 'success.main' + : editedTask.taskProperty === 'Development' + ? 'warning.main' + : editedTask.taskProperty === 'Mobile' + ? 'primary.main' + : editedTask.taskProperty === 'UX Stage' + ? 'warning.main' + : editedTask.taskProperty === 'Research' + ? 'secondary.main' + : editedTask.taskProperty === 'Data Science' + ? 'error.main' + : editedTask.taskProperty === 'Branding' + ? 'success.main' + : 'primary.contrastText'; + + return ( + + {(provided: any) => ( + + + + + {editedTask.task} + + + + + + + + + + + Edit + + + + {' '} + + Delete + + + + + + + {editedTask.taskImage && ( + Task Image + )} + + {editedTask.taskText && ( + + {editedTask.taskText} + + )} + + + + {taskDate} + + + + + + + + )} + + ); +}; +export default TaskData; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskManager.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskManager.tsx new file mode 100644 index 0000000..88c4f32 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskManager.tsx @@ -0,0 +1,56 @@ + +import { useContext } from 'react'; +import KanbanHeader from './KanbanHeader'; +import { KanbanDataContext } from 'src/context/kanbancontext/index'; +import CategoryTaskList from './CategoryTaskList'; +import { DragDropContext, Droppable } from '@hello-pangea/dnd'; +import SimpleBar from 'simplebar-react'; +import { Box } from '@mui/material'; + +function TaskManager() { + const { todoCategories, moveTask } = useContext(KanbanDataContext); + const onDragEnd = (result: { source: any; destination: any; draggableId: any }) => { + const { source, destination, draggableId } = result; + + // If no destination is provided or the drop is in the same place, do nothing + if ( + !destination || + (source.droppableId === destination.droppableId && source.index === destination.index) + ) { + return; + } + + // Extract necessary information from the result + const sourceCategoryId = source.droppableId; + const destinationCategoryId = destination.droppableId; + const sourceIndex = source.index; + const destinationIndex = destination.index; + + // Call moveTask function from context + moveTask(draggableId, sourceCategoryId, destinationCategoryId, sourceIndex, destinationIndex); + }; + + return ( + <> + + + + + {todoCategories.map((category) => ( + + {(provided: any) => ( +
+ + {provided.placeholder} +
+ )} +
+ ))} +
+
+
+ + ); +} + +export default TaskManager; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskModal/AddNewTaskModal.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskModal/AddNewTaskModal.tsx new file mode 100644 index 0000000..007a3ab --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskModal/AddNewTaskModal.tsx @@ -0,0 +1,183 @@ + + + +import { TaskProperties } from '../../../../_mockApis/kanban/KanbanData'; +import { + Button, + MenuItem, + Dialog, + DialogTitle, + DialogContent, + DialogActions, + Grid2 as Grid, +} from '@mui/material'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; + +function AddNewList({ + show, + onHide, + onSave, + newTaskData, + setNewTaskData, + updateTasks, +}: any) { + + + const { task, taskText, taskProperty, taskImage } = newTaskData; + + //Function to handle saving changes and updating tasks + const handleSave = () => { + + // Update the task data with the default date if needed + setNewTaskData({ ...newTaskData }); + onSave(); + updateTasks(); + }; + + + const isFormValid = () => { + return task && taskText && taskProperty && taskImage; + }; + return ( + ( + Add Task + + + + {/* task title */} + + Task Title * + + + setNewTaskData({ ...newTaskData, task: e.target.value }) + } + /> + + + {/* task text */} + + Text* + + + setNewTaskData({ ...newTaskData, taskText: e.target.value }) + } + /> + + + {/* task image */} + + Image URL* + + + setNewTaskData({ ...newTaskData, taskImage: e.target.value }) + } + /> + {taskImage !== undefined && ( + Selected + )} + + + {/* task image */} + + Task Property * + + + setNewTaskData({ ...newTaskData, taskProperty: e.target.value }) + } + > + Select Task Property + {TaskProperties.map((property) => ( + + {property} + + ))} + + + + + + + + + + ) + ); +} +export default AddNewList; + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskModal/EditCategoryModal.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskModal/EditCategoryModal.tsx new file mode 100644 index 0000000..bdf79b5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskModal/EditCategoryModal.tsx @@ -0,0 +1,55 @@ + +import { useState } from 'react'; + +import { Button, Dialog, DialogTitle, DialogContent, Grid2 as Grid, DialogActions } from '@mui/material'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; + +function EditCategoryModal({ + showModal, + handleCloseModal, + handleUpdateCategory, + initialCategoryName, +}: any) { + const [newCategoryName, setNewCategoryName] = useState(initialCategoryName); + // Function to handle saving changes and updating category name + const handleSave = () => { + handleUpdateCategory(newCategoryName); + handleCloseModal(); + }; + return ( + ( + Edit Category + + + + {/* category title */} + Category name + setNewCategoryName(e.target.value)} + /> + + + + + + + + ) + ); +} +export default EditCategoryModal; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskModal/EditTaskModal.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskModal/EditTaskModal.tsx new file mode 100644 index 0000000..715e30b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/kanban/TaskModal/EditTaskModal.tsx @@ -0,0 +1,178 @@ + + +import { useEffect, useState } from 'react'; +import { TaskProperties } from '../../../../_mockApis/kanban/KanbanData'; +import { + Button, + + MenuItem, + DialogTitle, + DialogContent, + DialogActions, + Grid2 as Grid, +} from '@mui/material'; +import Dialog from '@mui/material/Dialog'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; + +function EditTaskModal({ show, onHide, editedTask, onSave }: any) { + const [tempEditedTask, setTempEditedTask] = useState(editedTask); + + const [newImageUrl, setNewImageUrl] = useState(editedTask.taskImage || ""); + const [imagePreview, setImagePreview] = useState(editedTask.taskImage || ""); + + useEffect(() => { + + setTempEditedTask({ + ...editedTask, + }); + setNewImageUrl(editedTask.taskImage || ""); + setImagePreview(editedTask.taskImage || ""); + }, [editedTask]); + + + // Function to handle changes in the task input fields + const handleChange = (e: { target: { name: any; value: any } }) => { + const { name, value } = e.target; + setTempEditedTask({ ...tempEditedTask, [name]: value }); + }; + + // Function to handle changes in the task property + const handlePropertyChange = (property: any) => { + setTempEditedTask({ ...tempEditedTask, taskProperty: property }); + }; + + // Function to handle saving the changes made to the task and hiding the modal + const handleSaveChanges = () => { + const updatedTask = { ...tempEditedTask, taskImage: newImageUrl }; + onSave(updatedTask); + onHide(); + }; + + + + // Function to handle new image URL input + const handleNewImageUrlChange = (e: React.ChangeEvent) => { + const url = e.target.value; + setNewImageUrl(url); + setImagePreview(url); // Update the preview with the new image URL + }; + + return ( + ( + Edit Task + + + + {/* Task title */} + + Task Title + + + + + {/* Task property */} + + Task Property * + + handlePropertyChange(e.target.value)} + > + {TaskProperties.map((property) => ( + + {property} + + ))} + + + + {/* Task text or image */} + {tempEditedTask.taskImage ? ( + <> + {/* Image handling */} + + Image URL + + + {imagePreview && ( + + Image Preview: + Selected + + )} + + ) : ( + <> + {/* Task text */} + + Text + + + + )} + + + + + + + + + + ) + ); +} + +export default EditTaskModal; \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/AddNotes.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/AddNotes.tsx new file mode 100644 index 0000000..b546706 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/AddNotes.tsx @@ -0,0 +1,107 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import * as React from 'react'; +import { addNote } from 'src/store/apps/notes/NotesSlice'; +import { + Button, + Dialog, + Fab, + DialogContent, + TextField, + DialogActions, + DialogContentText, + Typography, +} from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { IconCheck } from '@tabler/icons-react'; + +interface Props { + colors: any[]; +} + +const AddNotes = ({ colors }: Props) => { + const dispatch = useDispatch(); + const [open, setOpen] = React.useState(false); + const [scolor, setScolor] = React.useState('primary'); + const id = useSelector((state) => state.notesReducer.notes.length + 1); + const [title, setTitle] = React.useState(''); + + const setColor = (e: string) => { + setScolor(e); + }; + + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + + return ( + <> + + + + + Add New Note + + + To add new notes please enter your description and choose note colors. and press the + submit button to add new note. + + setTitle(e.target.value)} + margin="normal" + id="description" + label="Add Note Description" + type="text" + fullWidth + size="small" + variant="outlined" + /> + + Choose Color + + {colors.map((color) => ( + setColor(color.disp)} + > + {scolor === color.disp ? : ''} + + ))} + + + + + + + + ); +}; + +export default AddNotes; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/NoteContent.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/NoteContent.tsx new file mode 100644 index 0000000..31fe777 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/NoteContent.tsx @@ -0,0 +1,133 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { + Box, + Divider, + Fab, + TextField, + FormLabel, + useTheme, + IconButton, + Typography, +} from '@mui/material'; +import { IconCheck, IconMenu2 } from '@tabler/icons-react'; + +import { UpdateNote } from '../../../store/apps/notes/NotesSlice'; +import AddNotes from './AddNotes'; +import { NotesType } from 'src/types/apps/notes'; + +interface colorsType { + lineColor: string; + disp: string | any; + id: number; +} + +interface Props { + + // toggleNoteSidebar: func, + + toggleNoteSidebar: (event: React.MouseEvent) => void, +} + +const NoteContent = ({ toggleNoteSidebar }: Props) => { + const noteDetails: NotesType = useSelector( + (state) => state.notesReducer.notes[state.notesReducer.notesContent - 1], + ); + const theme = useTheme(); + + const dispatch = useDispatch(); + + const colorvariation: colorsType[] = [ + { + id: 1, + lineColor: theme.palette.warning.main, + disp: 'warning', + }, + { + id: 2, + lineColor: theme.palette.info.main, + disp: 'info', + }, + { + id: 3, + lineColor: theme.palette.error.main, + disp: 'error', + }, + { + id: 4, + lineColor: theme.palette.success.main, + disp: 'success', + }, + { + id: 5, + lineColor: theme.palette.primary.main, + disp: 'primary', + }, + ]; + + return ( + + {/* ------------------------------------------- */} + {/* Header Part */} + {/* ------------------------------------------- */} + + + + + + + + {/* ------------------------------------------- */} + {/* Edit notes */} + {/* ------------------------------------------- */} + {noteDetails && noteDetails.deleted === false ? ( + + + + Edit Note + + + + dispatch(UpdateNote(noteDetails.id, 'title', e.target.value))} + /> +
+ + Change Note Color + + + {colorvariation.map((color1) => ( + dispatch(UpdateNote(noteDetails.id, 'color', color1.disp))} + > + {noteDetails.color === color1.disp ? : ''} + + ))} +
+ ) : ( + Select a Note + )} +
+ ); +}; + + +export default NoteContent; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/NoteList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/NoteList.tsx new file mode 100644 index 0000000..de4de4a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/NoteList.tsx @@ -0,0 +1,108 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { IconButton, Box, Stack, Typography, TextField, Tooltip, Alert } from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import Scrollbar from '../../custom-scroll/Scrollbar'; +import { + fetchNotes, + SelectNote, + DeleteNote, + SearchNotes, +} from '../../../store/apps/notes/NotesSlice'; +import { IconTrash } from '@tabler/icons-react'; +import { NotesType } from 'src/types/apps/notes'; + +const NoteList = () => { + const dispatch = useDispatch(); + const activeNote = useSelector((state) => state.notesReducer.notesContent); + const searchTerm = useSelector((state) => state.notesReducer.noteSearch); + + useEffect(() => { + dispatch(fetchNotes()); + }, [dispatch]); + + const filterNotes = (notes: NotesType[], nSearch: string) => { + if (nSearch !== '') + return notes.filter( + (t: any) => + !t.deleted && + t.title.toLocaleLowerCase().concat(' ').includes(nSearch.toLocaleLowerCase()), + ); + + return notes.filter((t) => !t.deleted); + }; + + const notes = useSelector((state) => + filterNotes(state.notesReducer.notes, state.notesReducer.noteSearch), + ); + + return ( + <> + + dispatch(SearchNotes(e.target.value))} + /> + + All Notes + + + + + {notes && notes.length ? ( + notes.map((note) => ( + + dispatch(SelectNote(note.id))} + > + + {note.title} + + + + {new Date(note.datef).toLocaleDateString()} + + + dispatch(DeleteNote(note.id))} + > + + + + + + + )) + ) : ( + + + No Notes Found! + + + )} + + + + ); +}; + +export default NoteList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/NoteSidebar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/NoteSidebar.tsx new file mode 100644 index 0000000..63f2306 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/notes/NoteSidebar.tsx @@ -0,0 +1,34 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Drawer, Theme, useMediaQuery } from '@mui/material'; +import NoteList from './NoteList'; + +const drawerWidth = 260; + +interface NoteType { + isMobileSidebarOpen: boolean; + onSidebarClose: (event: React.MouseEvent) => void; +} + +const NoteSidebar = ({ isMobileSidebarOpen, onSidebarClose }: NoteType) => { + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + + return ( + + + + ); +}; + +export default NoteSidebar; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/tickets/TicketFilter.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/tickets/TicketFilter.tsx new file mode 100644 index 0000000..d60bb28 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/tickets/TicketFilter.tsx @@ -0,0 +1,85 @@ +import { Box, Grid2 as Grid, Typography, styled } from '@mui/material'; +import { useDispatch, useSelector } from 'src/store/Store'; +import { TicketType } from 'src/types/apps/ticket'; +import { setVisibilityFilter } from '../../../store/apps/tickets/TicketSlice'; + +const BoxStyled = styled(Box)(() => ({ + padding: '30px', + transition: '0.1s ease-in', + cursor: 'pointer', + color: 'inherit', + '&:hover': { + transform: 'scale(1.03)', + }, +})); + +const TicketFilter = () => { + const dispatch = useDispatch(); + const counter: TicketType[] = useSelector((state) => state.ticketReducer.tickets); + const pendingC = counter.filter((t) => t.Status === 'Pending').length; + const openC = counter.filter((t) => t.Status === 'Open').length; + const closeC = counter.filter((t) => t.Status === 'Closed').length; + + return ( + ( + + dispatch(setVisibilityFilter('total_tickets'))} + sx={{ backgroundColor: 'primary.light', color: 'primary.main' }} + > + {counter.length} + Total Tickets + + + + dispatch(setVisibilityFilter('Pending'))} + sx={{ backgroundColor: 'warning.light', color: 'warning.main' }} + > + {pendingC} + Pending Tickets + + + + dispatch(setVisibilityFilter('Open'))} + sx={{ backgroundColor: 'success.light', color: 'success.main' }} + > + {openC} + Open Tickets + + + + dispatch(setVisibilityFilter('Closed'))} + sx={{ backgroundColor: 'error.light', color: 'error.main' }} + > + {closeC} + Closed Tickets + + + ) + ); +}; + +export default TicketFilter; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/tickets/TicketListing.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/tickets/TicketListing.tsx new file mode 100644 index 0000000..0460b99 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/tickets/TicketListing.tsx @@ -0,0 +1,191 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { useDispatch, useSelector } from 'src/store/Store'; +import { format } from 'date-fns'; +import { + Box, + Table, + TableHead, + TableRow, + TableCell, + Typography, + TableBody, + IconButton, + Chip, + Stack, + Avatar, + Tooltip, + TextField, + Pagination, + useTheme, + TableContainer, +} from '@mui/material'; +import { fetchTickets, DeleteTicket, SearchTicket } from 'src/store/apps/tickets/TicketSlice'; +import { IconTrash } from '@tabler/icons-react'; +import { TicketType } from 'src/types/apps/ticket'; + +const TicketListing = () => { + const dispatch = useDispatch(); + const theme = useTheme(); + + useEffect(() => { + dispatch(fetchTickets()); + }, [dispatch]); + + const getVisibleTickets = (tickets: TicketType[], filter: string, ticketSearch: string) => { + switch (filter) { + case 'total_tickets': + return tickets.filter( + (c) => !c.deleted && c.ticketTitle.toLocaleLowerCase().includes(ticketSearch), + ); + + case 'Pending': + return tickets.filter( + (c) => + !c.deleted && + c.Status === 'Pending' && + c.ticketTitle.toLocaleLowerCase().includes(ticketSearch), + ); + + case 'Closed': + return tickets.filter( + (c) => + !c.deleted && + c.Status === 'Closed' && + c.ticketTitle.toLocaleLowerCase().includes(ticketSearch), + ); + + case 'Open': + return tickets.filter( + (c) => + !c.deleted && + c.Status === 'Open' && + c.ticketTitle.toLocaleLowerCase().includes(ticketSearch), + ); + + default: + throw new Error(`Unknown filter: ${filter}`); + } + }; + + const tickets = useSelector((state) => + getVisibleTickets( + state.ticketReducer.tickets, + state.ticketReducer.currentFilter, + state.ticketReducer.ticketSearch, + ), + ); + const ticketBadge = (ticket: TicketType) => { + return ticket.Status === 'Open' + ? theme.palette.success.light + : ticket.Status === 'Closed' + ? theme.palette.error.light + : ticket.Status === 'Pending' + ? theme.palette.warning.light + : ticket.Status === 'Moderate' + ? theme.palette.primary.light + : 'primary'; + }; + + return ( + + + dispatch(SearchTicket(e.target.value))} + /> + + + + + + + Id + + + Ticket + + + Assigned To + + + Status + + + Date + + + Action + + + + + {tickets.map((ticket) => ( + + {ticket.Id} + + + + {ticket.ticketTitle} + + + {ticket.ticketDescription} + + + + + + + {ticket.AgentName} + + + + + + + + {format(new Date(ticket.Date), 'E, MMM d')} + + + + + dispatch(DeleteTicket(ticket.Id))}> + + + + + + ))} + +
+
+ + + +
+ ); +}; + +export default TicketListing; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/followers/FollowerCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/followers/FollowerCard.tsx new file mode 100644 index 0000000..b3da5ae --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/followers/FollowerCard.tsx @@ -0,0 +1,129 @@ +import { + CardContent, + Box, + Stack, + Avatar, + Grid2 as Grid, + Button, + Typography, + Chip, + TextField, + InputAdornment, +} from '@mui/material'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import BlankCard from 'src/components/shared/BlankCard'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { fetchFollwores, onToggleFollow } from 'src/store/apps/userProfile/UserProfileSlice'; +import { IconMapPin, IconSearch } from '@tabler/icons-react'; +import { userType } from 'src/types/apps/users'; + +const FollowerCard = () => { + const dispatch = useDispatch(); + useEffect(() => { + dispatch(fetchFollwores()); + }, [dispatch]); + + const filterFollowers = (followers: userType[], cSearch: string) => { + if (followers) + return followers.filter((t) => + t.name.toLocaleLowerCase().includes(cSearch.toLocaleLowerCase()), + ); + + return followers; + }; + const [search, setSearch] = React.useState(''); + const getFollowers = useSelector((state) => + filterFollowers(state.userpostsReducer.followers, search), + ); + + return (<> + + + + + + Followers   + + + + + + + + ), + }} + fullWidth + onChange={(e) => setSearch(e.target.value)} + /> + + + + {getFollowers.map((profile) => { + return ( + ( + + + + + + {profile.name} + + + {profile.country} + + + + {profile.isFollowed ? ( + + ) : ( + + )} + + + + + ) + ); + })} + + ); +}; + +export default FollowerCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/friends/FriendsCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/friends/FriendsCard.tsx new file mode 100644 index 0000000..e54b9ac --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/friends/FriendsCard.tsx @@ -0,0 +1,143 @@ +import { + CardContent, + Box, + Stack, + Avatar, + Grid2 as Grid, + Typography, + Chip, + TextField, + InputAdornment, + Divider, + IconButton, +} from '@mui/material'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import BlankCard from 'src/components/shared/BlankCard'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { fetchFollwores } from 'src/store/apps/userProfile/UserProfileSlice'; +import { + IconBrandFacebook, + IconBrandGithub, + IconBrandInstagram, + IconBrandTwitter, + IconSearch, +} from '@tabler/icons-react'; +import { userType } from 'src/types/apps/users'; + +interface socialType { + name: string; + icon: React.ReactElement; +} + +const SocialIcons: socialType[] = [ + { + name: 'Facebook', + icon: , + }, + { + name: 'Instagram', + icon: , + }, + { + name: 'Github', + icon: , + }, + { + name: 'Twitter', + icon: , + }, +]; + +const FriendsCard = () => { + const dispatch = useDispatch(); + useEffect(() => { + dispatch(fetchFollwores()); + }, [dispatch]); + + const filterFriends = (friends: userType[], cSearch: string) => { + if (friends) + return friends.filter((t) => + t.name.toLocaleLowerCase().includes(cSearch.toLocaleLowerCase()), + ); + + return friends; + }; + const [search, setSearch] = React.useState(''); + const getFriends = useSelector((state) => + filterFriends(state.userpostsReducer.followers, search), + ); + + return (<> + + + + + + Friends   + + + + + + + + ), + }} + fullWidth + onChange={(e) => setSearch(e.target.value)} + /> + + + + {getFriends.map((profile) => { + return ( + ( + + + + + + {profile.name} + {profile.role} + + + + + + {SocialIcons.map((sicon) => { + return {sicon.icon}; + })} + + + ) + ); + })} + + ); +}; + +export default FriendsCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/gallery/GalleryCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/gallery/GalleryCard.tsx new file mode 100644 index 0000000..5407882 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/gallery/GalleryCard.tsx @@ -0,0 +1,147 @@ +import { + Box, + Stack, + Grid2 as Grid, + Typography, + Chip, + TextField, + InputAdornment, + IconButton, + CardMedia, + Skeleton, +} from '@mui/material'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect, useState } from 'react'; +import BlankCard from 'src/components/shared/BlankCard'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { fetchPhotos } from 'src/store/apps/userProfile/UserProfileSlice'; +import { IconDotsVertical, IconSearch } from '@tabler/icons-react'; +import { format } from 'date-fns'; +import { GallaryType } from 'src/types/apps/users'; + +import FsLightbox from 'fslightbox-react'; + +const GalleryCard = () => { + const dispatch = useDispatch(); + useEffect(() => { + dispatch(fetchPhotos()); + }, [dispatch]); + + const filterPhotos = (photos: GallaryType[], cSearch: string) => { + if (photos) + return photos.filter((t) => t.name.toLocaleLowerCase().includes(cSearch.toLocaleLowerCase())); + + return photos; + }; + const [search, setSearch] = React.useState(''); + const getPhotos = useSelector((state) => filterPhotos(state.userpostsReducer.gallery, search)); + + // skeleton + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 500); + + return () => clearTimeout(timer); + }, []); + + const [toggler, setToggler] = useState(false); + const [currentImage, setCurrentImage] = useState(null); + + const openLightbox = (image: any) => { + setCurrentImage(image); + setToggler((prev) => !prev); + }; + + return (<> + + + + + + Gallery   + + + + + + + + ), + }} + fullWidth + onChange={(e) => setSearch(e.target.value)} + /> + + + + {getPhotos.map((photo) => { + return ( + ( + + {isLoading ? ( + <> + + + ) : ( + openLightbox(photo.cover)} + sx={{ cursor: 'pointer' }} + /> + )} + + + + {photo.name}jpg + + {format(new Date(photo.time), 'E, MMM d, yyyy')} + + + + + + + + + + + ) + ); + })} + + {/* FSLightbox component */} + + ); +}; + +export default GalleryCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/IntroCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/IntroCard.tsx new file mode 100644 index 0000000..fa316a2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/IntroCard.tsx @@ -0,0 +1,37 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Stack, Typography } from '@mui/material'; + +import ChildCard from 'src/components/shared/ChildCard'; +import { IconBriefcase, IconDeviceDesktop, IconMail, IconMapPin } from '@tabler/icons-react'; + +const IntroCard = () => ( + + + Introduction + + + Hello, I am Julia Roberts. I love making websites and graphics. Lorem ipsum dolor sit amet, + consectetur adipiscing elit. + + + + Sir, P P Institute Of Science + + + + xyzjonathan@gmail.com + + + + www.xyz.com + + + + Newyork, USA - 100001 + + +); + +export default IntroCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PhotosCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PhotosCard.tsx new file mode 100644 index 0000000..bd266ff --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PhotosCard.tsx @@ -0,0 +1,106 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { Typography, ImageList, ImageListItem, Skeleton, Box } from '@mui/material'; + +import img1 from 'src/assets/images/products/s1.jpg'; +import img2 from 'src/assets/images/products/s2.jpg'; +import img3 from 'src/assets/images/products/s3.jpg'; +import img4 from 'src/assets/images/products/s4.jpg'; +import img5 from 'src/assets/images/products/s5.jpg'; +import img6 from 'src/assets/images/products/s6.jpg'; +import img7 from 'src/assets/images/products/s11.jpg'; +import img8 from 'src/assets/images/products/s8.jpg'; +import ChildCard from 'src/components/shared/ChildCard'; + +interface photoType { + img: string; + id: number; +} + +const photos: photoType[] = [ + { + img: img1, + id: 1, + }, + { + img: img2, + id: 2, + }, + { + img: img3, + id: 3, + }, + { + img: img4, + id: 4, + }, + { + img: img5, + id: 5, + }, + { + img: img6, + id: 6, + }, + { + img: img7, + id: 7, + }, + { + img: img8, + id: 8, + }, + { + img: img1, + id: 9, + }, +]; + +const PhotosCard = () => { + + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 500); + + return () => clearTimeout(timer); + }, []); + + return ( + + Photos + + {photos.map((photo) => ( + + { + isLoading ? ( + <> + + + ) : ( + + {photo.img} + + )} + + ))} + + + ) +}; + +export default PhotosCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/Post.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/Post.tsx new file mode 100644 index 0000000..3093238 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/Post.tsx @@ -0,0 +1,44 @@ +import Grid from '@mui/material/Grid2'; + +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { useSelector, useDispatch } from 'src/store/Store'; + +import { fetchPosts } from 'src/store/apps/userProfile/UserProfileSlice'; +import PostItem from './PostItem'; +import { PostTextBox } from './PostTextBox'; +import { PostType } from 'src/types/apps/userProfile'; + +const Post = () => { + const dispatch = useDispatch(); + useEffect(() => { + dispatch(fetchPosts()); + }, [dispatch]); + + const getPosts: PostType[] = useSelector((state) => state.userpostsReducer.posts); + + return ( + ( + + + + {getPosts.map((posts) => { + return ( + ( + + ) + ); + })} + ) + ); +}; + +export default Post; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PostComments.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PostComments.tsx new file mode 100644 index 0000000..e715f6c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PostComments.tsx @@ -0,0 +1,153 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { Stack, Avatar, Box, Typography, Tooltip, Fab, TextField, Button } from '@mui/material'; +import { IconArrowBackUp, IconCircle, IconThumbUp } from '@tabler/icons-react'; + +import { useDispatch } from 'src/store/Store'; +import uniqueId from 'lodash/uniqueId'; +import { addReply } from 'src/store/apps/userProfile/UserProfileSlice'; +import { + PostType, + Comment as CommentType, + CommentDataType, + Reply, + ProfileType, +} from 'src/types/apps/userProfile'; + +interface CommentProps { + comment: CommentType | any; + post: PostType; +} +interface ReplyProps { + data: CommentDataType; + reply: Reply[]; + profile: ProfileType; +} +const PostComments = ({ comment, post }: CommentProps) => { + const [replyTxt, setReplyTxt] = useState(''); + const [showReply, setShowReply] = useState(false); + const dispatch = useDispatch(); + const onSubmit = async (id: number, commentid: string | any, reply: CommentDataType) => { + const replyId = uniqueId('#REPLY_'); + const newReply: PostType[] | any = { + id: replyId, + profile: { + id: uniqueId('#REPLY_'), + avatar: post?.profile.avatar, + name: post?.profile.name, + time: 'now', + }, + data: { + comment: reply, + likes: { + like: false, + value: 0, + }, + replies: [], + }, + }; + dispatch(addReply(id, commentid, newReply)); + setReplyTxt(''); + setShowReply(false); + }; + + return ( + <> + theme.palette.divider, borderWidth: '1px', borderStyle: 'solid' }}> + + + {comment?.profile.name} + + {' '} + {comment?.profile.time} + + + + {comment?.data.comment} + + + + + + + + + {comment?.data && comment?.data.likes && comment?.data.likes.value} + + + setShowReply(!showReply)}> + + + + {comment?.data.replies.length > 0 ? comment?.data.replies.length : 0} + + + {comment?.data.replies ? ( + <> + {comment?.data.replies.map((reply: ReplyProps) => { + return ( + + theme.palette.grey[100], borderWidth: '1px', borderStyle: 'solid' }} + > + + + {reply.profile.name} + + {' '} + {reply.profile.time} + + + + {reply.data.comment} + + + + ); + })} + + ) : ( + '' + )} + {showReply ? ( + + + + setReplyTxt(e.target.value)} + variant="outlined" + fullWidth + /> + + + + ) : ( + '' + )} + + ); +}; + +export default PostComments; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PostItem.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PostItem.tsx new file mode 100644 index 0000000..03e665b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PostItem.tsx @@ -0,0 +1,187 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; + +import { + Stack, + Avatar, + Box, + Typography, + CardMedia, + Grid2 as Grid, + IconButton, + Fab, + Tooltip, + TextField, + Button, + Divider, +} from '@mui/material'; +import { IconCircle, IconMessage2, IconShare, IconThumbUp } from '@tabler/icons-react'; +import uniqueId from 'lodash/uniqueId'; +import { useDispatch, useSelector } from 'src/store/Store'; +import { likePosts, addComment } from 'src/store/apps/userProfile/UserProfileSlice'; +import PostComments from './PostComments'; +import BlankCard from '../../../shared/BlankCard'; +import { Comment as CommentType, PostType } from 'src/types/apps/userProfile'; + +interface Props { + post: PostType; +} + +const PostItem = ({ post }: Props) => { + const dispatch = useDispatch(); + const customizer = useSelector((state) => state.customizer); + const handleLike = async (postId: number) => { + dispatch(likePosts(postId)); + }; + const [comText, setComText] = useState(''); + + const onSubmit = async (id: number, comment: CommentType) => { + const commentId = uniqueId('#COMMENT_'); + const newComment: any = { + id: commentId, + profile: { + id: uniqueId('#COMMENT_'), + avatar: post?.profile.avatar, + name: post?.profile.name, + time: 'now', + }, + data: { + comment: comment, + likes: { + like: false, + value: 0, + }, + replies: [], + }, + }; + + dispatch(addComment(id, newComment)); + setComText(''); + }; + + return ( + ( + + + + {post?.profile.name} + + {' '} + {post?.profile.time} + + + {/**Post Content**/} + {post?.data.content} + {/**If Post has Image**/} + {post.data.images.length > 0 ? ( + + + {post?.data.images.map((photo) => { + return ( + ( + + ) + ); + })} + + + ) : ( + '' + )} + {/**If Post has Video**/} + {post?.data.video ? ( + + ) : ( + '' + )} + {/**Post Like Comment Share buttons**/} + + + + handleLike(post?.id)} + > + + + + + {post?.data && post?.data.likes && post?.data.likes.value} + + + + + + + + {post?.data.comments ? post?.data.comments.length : 0} + + + + + + + + + {/**Comments if any**/} + + {post?.data.comments ? ( + <> + {post?.data.comments.map((comment) => { + return ; + })} + + ) : ( + '' + )} + + + + + + + setComText(e.target.value)} + variant="outlined" + fullWidth + /> + + + + ) + ); +}; + + +export default PostItem; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PostTextBox.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PostTextBox.tsx new file mode 100644 index 0000000..308bed4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/PostTextBox.tsx @@ -0,0 +1,47 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Stack, Fab, TextField, Button } from '@mui/material'; +import { IconPhoto, IconNotebook } from '@tabler/icons-react'; +import ChildCard from 'src/components/shared/ChildCard'; + +export const PostTextBox = () => { + return ( + + + + + + + + + + + + + + ); +}; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/ProfileBanner.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/ProfileBanner.tsx new file mode 100644 index 0000000..45890f4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/ProfileBanner.tsx @@ -0,0 +1,182 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Grid2 as Grid, + Box, + Typography, + Button, + Avatar, + Stack, + CardMedia, + styled, + Fab, +} from '@mui/material'; +import profilecover from 'src/assets/images/backgrounds/profilebg.jpg'; +import userimg from 'src/assets/images/profile/user-1.jpg'; +import { + IconBrandDribbble, + IconBrandFacebook, + IconBrandTwitter, + IconBrandYoutube, + IconFileDescription, + IconUserCheck, + IconUserCircle, +} from '@tabler/icons-react'; +import ProfileTab from './ProfileTab'; +import BlankCard from '../../../shared/BlankCard'; + +const ProfileBanner = () => { + const ProfileImage = styled(Box)(() => ({ + backgroundImage: 'linear-gradient(#50b2fc,#f44c66)', + borderRadius: '50%', + width: '110px', + height: '110px', + display: 'flex', + alignItems: 'center', + justifyContent: 'center', + margin: '0 auto' + })); + + return (<> + + + + {/* Post | Followers | Following */} + + + + + + + + 938 + + + Posts + + + + + + + + 3,586 + + + Followers + + + + + + + + 2,659 + + + Following + + + + + {/* about profile */} + + + + + + + + + Mathew Anderson + + + Designer + + + + + + {/* friends following buttons */} + + + + + + + + + + + + + + + + + + + {/**TabbingPart**/} + + + ); +}; + +export default ProfileBanner; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/ProfileTab.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/ProfileTab.tsx new file mode 100644 index 0000000..8848653 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/apps/userprofile/profile/ProfileTab.tsx @@ -0,0 +1,70 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Tabs, Tab, Box } from '@mui/material'; +import { IconHeart, IconPhoto, IconUserCircle } from '@tabler/icons-react'; +import { Link, useLocation } from 'react-router'; + +const ProfileTab = () => { + const location = useLocation(); + const [value, setValue] = React.useState(location.pathname); + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const handleChange = (event: React.SyntheticEvent, newValue: string) => { + setValue(newValue); + }; + + interface profileType { + label: string; + icon: any; + to: string; + } + + const ProfileTabs: profileType[] = [ + { + label: 'Profile', + icon: , + to: '/user-profile', + }, + { + label: 'Followers', + icon: , + to: '/apps/followers', + }, + { + label: 'Friends', + icon: , + to: '/apps/friends', + }, + { + label: 'Gallery', + icon: , + to: '/apps/gallery', + }, + ]; + + return ( + theme.palette.grey[100] }}> + + + {ProfileTabs.map((tab) => { + return ( + + ); + })} + + + + ); +}; + +export default ProfileTab; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Area Chart/code/AreaChartCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Area Chart/code/AreaChartCode.tsx new file mode 100644 index 0000000..3b9c3ae --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Area Chart/code/AreaChartCode.tsx @@ -0,0 +1,102 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const AreaChartCode = () => { + return ( + <> + + {` +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Props } from 'react-apexcharts'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Area Chart', + }, +]; + +const AreaChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + const optionsareachart:Props = { + chart: { + id: 'area-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + zoom: { + enabled: true, + }, + toolbar: { + show: false, + }, + }, + dataLabels: { + enabled: false, + }, + stroke: { + width: '3', + curve: 'smooth', + }, + colors: [primary, secondary], + xaxis: { + type: 'datetime', + categories: [ + '2018-09-19T00:00:00', + '2018-09-19T01:30:00', + '2018-09-19T02:30:00', + '2018-09-19T03:30:00', + '2018-09-19T04:30:00', + '2018-09-19T05:30:00', + '2018-09-19T06:30:00', + ], + }, + yaxis: { + opposite: false, + labels: { + show: true, + }, + }, + legend: { + show: true, + position: 'bottom', + width: '50px', + }, + grid: { + show: false, + }, + tooltip: { + theme: 'dark', + fillSeriesColor: false, + }, + }; + const seriesareachart = [ + { + name: 'Sales Summery 1', + data: [31, 40, 28, 51, 42, 109, 100], + }, + { + name: 'Sales Summery 2', + data: [11, 32, 45, 32, 34, 52, 41], + }, + ]; + + return ( + + ); +}; + +export default AreaChart;`} + + + ); +}; + +export default AreaChartCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Candlestick Chart/code/CandlestickChartCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Candlestick Chart/code/CandlestickChartCode.tsx new file mode 100644 index 0000000..e911b31 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Candlestick Chart/code/CandlestickChartCode.tsx @@ -0,0 +1,147 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const CandlestickChartCode = () => { + return ( + <> + + {` +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Props } from 'react-apexcharts'; + + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Candlestick Chart', + }, +]; + +const CandlestickChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + const optionscandlestickchart: Props = { + chart: { + height: 350, + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + }, + xaxis: { + type: 'datetime', + }, + yaxis: { + tooltip: { + enabled: true, + }, + }, + plotOptions: { + candlestick: { + colors: { + upward: primary, + downward: secondary, + }, + }, + }, + tooltip: { + theme: 'dark', + }, + grid: { + show: false, + }, + }; + const seriecandlestickchart: any = [ + { + data: [ + { x: new Date(1538778600000), y: [6629.81, 6650.5, 6623.04, 6633.33] }, + { x: new Date(1538780400000), y: [6632.01, 6643.59, 6620, 6630.11] }, + { x: new Date(1538782200000), y: [6630.71, 6648.95, 6623.34, 6635.65] }, + { x: new Date(1538784000000), y: [6635.65, 6651, 6629.67, 6638.24] }, + { x: new Date(1538785800000), y: [6638.24, 6640, 6620, 6624.47] }, + { x: new Date(1538787600000), y: [6624.53, 6636.03, 6621.68, 6624.31] }, + { x: new Date(1538789400000), y: [6624.61, 6632.2, 6617, 6626.02] }, + { x: new Date(1538791200000), y: [6627, 6627.62, 6584.22, 6603.02] }, + { x: new Date(1538793000000), y: [6605, 6608.03, 6598.95, 6604.01] }, + { x: new Date(1538794800000), y: [6604.5, 6614.4, 6602.26, 6608.02] }, + { x: new Date(1538796600000), y: [6608.02, 6610.68, 6601.99, 6608.91] }, + { x: new Date(1538798400000), y: [6608.91, 6618.99, 6608.01, 6612] }, + { x: new Date(1538800200000), y: [6612, 6615.13, 6605.09, 6612] }, + { x: new Date(1538802000000), y: [6612, 6624.12, 6608.43, 6622.95] }, + { x: new Date(1538803800000), y: [6623.91, 6623.91, 6615, 6615.67] }, + { x: new Date(1538805600000), y: [6618.69, 6618.74, 6610, 6610.4] }, + { x: new Date(1538807400000), y: [6611, 6622.78, 6610.4, 6614.9] }, + { x: new Date(1538809200000), y: [6614.9, 6626.2, 6613.33, 6623.45] }, + { x: new Date(1538811000000), y: [6623.48, 6627, 6618.38, 6620.35] }, + { x: new Date(1538812800000), y: [6619.43, 6620.35, 6610.05, 6615.53] }, + { x: new Date(1538814600000), y: [6615.53, 6617.93, 6610, 6615.19] }, + { x: new Date(1538816400000), y: [6615.19, 6621.6, 6608.2, 6620] }, + { x: new Date(1538818200000), y: [6619.54, 6625.17, 6614.15, 6620] }, + { x: new Date(1538820000000), y: [6620.33, 6634.15, 6617.24, 6624.61] }, + { x: new Date(1538821800000), y: [6625.95, 6626, 6611.66, 6617.58] }, + { x: new Date(1538823600000), y: [6619, 6625.97, 6595.27, 6598.86] }, + { x: new Date(1538825400000), y: [6598.86, 6598.88, 6570, 6587.16] }, + { x: new Date(1538827200000), y: [6588.86, 6600, 6580, 6593.4] }, + { x: new Date(1538829000000), y: [6593.99, 6598.89, 6585, 6587.81] }, + { x: new Date(1538830800000), y: [6587.81, 6592.73, 6567.14, 6578] }, + { x: new Date(1538832600000), y: [6578.35, 6581.72, 6567.39, 6579] }, + { x: new Date(1538834400000), y: [6579.38, 6580.92, 6566.77, 6575.96] }, + { x: new Date(1538836200000), y: [6575.96, 6589, 6571.77, 6588.92] }, + { x: new Date(1538838000000), y: [6588.92, 6594, 6577.55, 6589.22] }, + { x: new Date(1538839800000), y: [6589.3, 6598.89, 6589.1, 6596.08] }, + { x: new Date(1538841600000), y: [6597.5, 6600, 6588.39, 6596.25] }, + { x: new Date(1538843400000), y: [6598.03, 6600, 6588.73, 6595.97] }, + { x: new Date(1538845200000), y: [6595.97, 6602.01, 6588.17, 6602] }, + { x: new Date(1538847000000), y: [6602, 6607, 6596.51, 6599.95] }, + { x: new Date(1538848800000), y: [6600.63, 6601.21, 6590.39, 6591.02] }, + { x: new Date(1538850600000), y: [6591.02, 6603.08, 6591, 6591] }, + { x: new Date(1538852400000), y: [6591, 6601.32, 6585, 6592] }, + { x: new Date(1538854200000), y: [6593.13, 6596.01, 6590, 6593.34] }, + { x: new Date(1538856000000), y: [6593.34, 6604.76, 6582.63, 6593.86] }, + { x: new Date(1538857800000), y: [6593.86, 6604.28, 6586.57, 6600.01] }, + { x: new Date(1538859600000), y: [6601.81, 6603.21, 6592.78, 6596.25] }, + { x: new Date(1538861400000), y: [6596.25, 6604.2, 6590, 6602.99] }, + { x: new Date(1538863200000), y: [6602.99, 6606, 6584.99, 6587.81] }, + { x: new Date(1538865000000), y: [6587.81, 6595, 6583.27, 6591.96] }, + { x: new Date(1538866800000), y: [6591.97, 6596.07, 6585, 6588.39] }, + { x: new Date(1538868600000), y: [6587.6, 6598.21, 6587.6, 6594.27] }, + { x: new Date(1538870400000), y: [6596.44, 6601, 6590, 6596.55] }, + { x: new Date(1538872200000), y: [6598.91, 6605, 6596.61, 6600.02] }, + { x: new Date(1538874000000), y: [6600.55, 6605, 6589.14, 6593.01] }, + { x: new Date(1538875800000), y: [6593.15, 6605, 6592, 6603.06] }, + { x: new Date(1538877600000), y: [6603.07, 6604.5, 6599.09, 6603.89] }, + { x: new Date(1538879400000), y: [6604.44, 6604.44, 6600, 6603.5] }, + { x: new Date(1538881200000), y: [6603.5, 6603.99, 6597.5, 6603.86] }, + { x: new Date(1538883000000), y: [6603.85, 6605, 6600, 6604.07] }, + { x: new Date(1538884800000), y: [6604.98, 6606, 6604.07, 6606] }, + ], + }, + ]; + + return ( + + ); +}; + +export default CandlestickChart; +`} + + + ); +}; + +export default CandlestickChartCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Column Chart/code/ColumnChartCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Column Chart/code/ColumnChartCode.tsx new file mode 100644 index 0000000..c26c696 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Column Chart/code/ColumnChartCode.tsx @@ -0,0 +1,116 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ColumnChartCode = () => { + return ( + <> + + {` +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Props } from 'react-apexcharts'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Column Chart', + }, +]; + +const ColumnChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const error = theme.palette.error.main; + + const optionscolumnchart: Props = { + chart: { + id: 'column-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + }, + colors: [primary, secondary, error], + plotOptions: { + bar: { + horizontal: false, + endingShape: 'rounded', + columnWidth: '20%', + }, + }, + dataLabels: { + enabled: false, + }, + stroke: { + show: true, + width: 2, + colors: ['transparent'], + }, + xaxis: { + categories: ['Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct'], + }, + yaxis: { + title: { + text: '$ (thousands)', + }, + }, + fill: { + opacity: 1, + }, + tooltip: { + y: { + formatter(val: any) { + return '$ {val} thousands'; + }, + }, + theme: 'dark', + }, + grid: { + show: false, + }, + legend: { + show: true, + position: 'bottom', + width: '50px', + }, + }; + const seriescolumnchart: any = [ + { + name: 'Desktop', + data: [44, 55, 57, 56, 61, 58, 63, 60, 66], + }, + { + name: 'Mobile', + data: [76, 85, 101, 98, 87, 105, 91, 114, 94], + }, + { + name: 'Other', + data: [35, 41, 36, 26, 45, 48, 52, 53, 41], + }, + ]; + + return ( + + ); +}; + +export default ColumnChart; + +`} + + + ); +}; + +export default ColumnChartCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Doughnut Charts/code/DoughnutChartsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Doughnut Charts/code/DoughnutChartsCode.tsx new file mode 100644 index 0000000..46e539d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Doughnut Charts/code/DoughnutChartsCode.tsx @@ -0,0 +1,80 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const DoughnutChartsCode = () => { + return ( + <> + + {` +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import Grid from '@mui/material/Grid2'; +import { Props } from 'react-apexcharts'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Doughtnut Chart', + }, +]; + +const DoughnutChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.primary.light; + const secondary = theme.palette.secondary.main; + const secondarylight = theme.palette.secondary.light; + const warning = theme.palette.warning.main; + + // 1 + const optionsdoughnutchart: Props = { + chart: { + id: 'donut-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + }, + dataLabels: { + enabled: false, + }, + plotOptions: { + pie: { + donut: { + size: '70px', + }, + }, + }, + legend: { + show: true, + position: 'bottom', + width: '50px', + }, + colors: [primary, primarylight, secondary, secondarylight, warning], + tooltip: { + theme: 'dark', + fillSeriesColor: false, + }, + }; + const seriesdoughnutchart = [45, 15, 27, 18, 35]; + + return ( + + ); +}; + +export default DoughnutChart; +`} + + + ); +}; + +export default DoughnutChartsCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Gradient Chart/code/GradientChartCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Gradient Chart/code/GradientChartCode.tsx new file mode 100644 index 0000000..a12a3c8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Gradient Chart/code/GradientChartCode.tsx @@ -0,0 +1,131 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const GradientChartCode = () => { + return ( + <> + + {` +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Props } from 'react-apexcharts'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Gradient Chart', + }, +]; + +const GredientChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + + const optionsgredientchart: Props = { + chart: { + height: 350, + type: 'line', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + dropShadow: { + enabled: true, + color: 'rgba(0,0,0,0.2)', + top: 12, + left: 4, + blur: 3, + opacity: 0.4, + }, + }, + stroke: { + width: 7, + curve: 'smooth', + }, + + xaxis: { + type: 'datetime', + categories: [ + '1/11/2000', + '2/11/2000', + '3/11/2000', + '4/11/2000', + '5/11/2000', + '6/11/2000', + '7/11/2000', + '8/11/2000', + '9/11/2000', + '10/11/2000', + '11/11/2000', + '12/11/2000', + '1/11/2001', + '2/11/2001', + '3/11/2001', + '4/11/2001', + '5/11/2001', + '6/11/2001', + ], + }, + fill: { + type: 'gradient', + gradient: { + shade: 'dark', + gradientToColors: [primary], + shadeIntensity: 1, + type: 'horizontal', + opacityFrom: 1, + opacityTo: 0.9, + stops: [0, 100, 100, 100], + }, + }, + markers: { + size: 4, + opacity: 0.9, + colors: [primary], + strokeColor: '#fff', + strokeWidth: 2, + + hover: { + size: 7, + }, + }, + yaxis: { + min: 0, + max: 40, + }, + tooltip: { + theme: 'dark', + }, + grid: { + show: false, + }, + }; + const seriesgredientchart: any = [ + { + name: 'Likes', + data: [4, 3, 10, 9, 35, 19, 22, 9, 12, 7, 19, 5, 13, 9, 17, 2, 7, 5], + }, + ]; + + return ( + + ); +}; + +export default GredientChart;`} + + + ); +}; + +export default GradientChartCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Line Chart/code/LineChartCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Line Chart/code/LineChartCode.tsx new file mode 100644 index 0000000..59ab875 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Line Chart/code/LineChartCode.tsx @@ -0,0 +1,106 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const LineChartCode = () => { + return ( + <> + + {` +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Props } from 'react-apexcharts'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Line Chart', + }, +]; + +const LineChart = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + const optionslinechart: Props = { + chart: { + height: 350, + type: 'line', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + zoom: { + type: 'x', + enabled: true, + }, + toolbar: { + show: false, + }, + shadow: { + enabled: true, + color: '#000', + top: 18, + left: 7, + blur: 10, + opacity: 1, + }, + }, + xaxis: { + categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul'], + title: { + text: 'Month', + }, + }, + grid: { + show: false, + }, + colors: [primary, secondary], + dataLabels: { + enabled: true, + }, + stroke: { + curve: 'straight', + width: '2', + }, + legend: { + position: 'top', + horizontalAlign: 'right', + floating: true, + offsetY: -25, + offsetX: -5, + }, + tooltip: { + theme: 'dark', + }, + }; + const serieslinechart: any = [ + { + name: 'High - 2013', + data: [28, 29, 33, 36, 32, 32, 33], + }, + { + name: 'Low - 2013', + data: [12, 11, 14, 18, 17, 13, 13], + }, + ]; + + return ( + + ); +}; + +export default LineChart;`} + + + ); +}; + +export default LineChartCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Pie Charts/code/PieChartsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Pie Charts/code/PieChartsCode.tsx new file mode 100644 index 0000000..40558a1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Pie Charts/code/PieChartsCode.tsx @@ -0,0 +1,79 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const PieChartsCode = () => { + return ( + <> + + {` +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import Grid from '@mui/material/Grid2'; +import { Props } from 'react-apexcharts'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Doughtnut Chart', + }, +]; + +const DoughnutChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.primary.light; + const secondary = theme.palette.secondary.main; + const secondarylight = theme.palette.secondary.light; + const warning = theme.palette.warning.main; + + // 2 + const optionspiechart: Props = { + chart: { + id: 'pie-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + }, + dataLabels: { + enabled: false, + }, + plotOptions: { + pie: { + donut: { + size: '70px', + }, + }, + }, + legend: { + show: true, + position: 'bottom', + width: '50px', + }, + colors: [primary, primarylight, secondary, secondarylight, warning], + tooltip: { + fillSeriesColor: false, + }, + }; + const seriespiechart = [45, 15, 27, 18, 35]; + + return ( + + ); +}; + +export default DoughnutChart; +`} + + + ); +}; + +export default PieChartsCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Radar Charts/code/RadarChartsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Radar Charts/code/RadarChartsCode.tsx new file mode 100644 index 0000000..665de55 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Radar Charts/code/RadarChartsCode.tsx @@ -0,0 +1,72 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const RadarChartsCode = () => { + return ( + <> + + {` +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import Grid from '@mui/material/Grid2'; +import { useTheme } from '@mui/material/styles'; +import { Props } from 'react-apexcharts'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Radialbar Chart', + }, +]; + +const RadialbarChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const success = theme.palette.success.main; + const warning = theme.palette.warning.main; + + // 2 + const optionsradarchart: Props = { + chart: { + id: 'pie-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + toolbar: { + show: false, + }, + }, + colors: [primary], + labels: ['January', 'February', 'March', 'April', 'May', 'June'], + tooltip: { + theme: 'dark', + }, + }; + const seriesradarchart: any = [ + { + name: 'Sales', + data: [80, 50, 30, 40, 100, 20], + }, + ]; + + return ( + + ); +}; + +export default RadialbarChart;`} + + + ); +}; + +export default RadarChartsCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Radialbar Charts/code/RadialbarChartsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Radialbar Charts/code/RadialbarChartsCode.tsx new file mode 100644 index 0000000..431b17f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/charts/Radialbar Charts/code/RadialbarChartsCode.tsx @@ -0,0 +1,85 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const RadialbarChartsCode = () => { + return ( + <> + + {` +import React from 'react'; +import Chart from 'react-apexcharts'; +import Grid from '@mui/material/Grid2'; +import { useTheme } from '@mui/material/styles'; +import { Props } from 'react-apexcharts'; + + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Radialbar Chart', + }, +]; + +const RadialbarChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const success = theme.palette.success.main; + const warning = theme.palette.warning.main; + + const optionsradialchart: Props = { + chart: { + id: 'pie-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + }, + colors: [primary, secondary, success, warning], + plotOptions: { + radialBar: { + dataLabels: { + name: { + fontSize: '22px', + }, + value: { + fontSize: '16px', + }, + total: { + show: true, + label: 'Total', + formatter() { + return 249; + }, + }, + }, + }, + }, + tooltip: { + theme: 'dark', + }, + }; + const seriesradialchart: any = [44, 55, 67, 83]; + + return ( + + ); +}; + +export default RadialbarChart; +`} + + + ); +}; + +export default RadialbarChartsCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/container/PageContainer.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/container/PageContainer.tsx new file mode 100644 index 0000000..ae925cb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/container/PageContainer.tsx @@ -0,0 +1,23 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +import { Helmet } from 'react-helmet'; + +type Props = { + description?: string; + children: any | any[] + title?: string; +}; + +const PageContainer = ({ title, description, children }: Props) => ( +
+ + {title} + + + {children} +
+); + +export default PageContainer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/custom-scroll/Scrollbar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/custom-scroll/Scrollbar.tsx new file mode 100644 index 0000000..f782249 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/custom-scroll/Scrollbar.tsx @@ -0,0 +1,31 @@ +import SimpleBar from 'simplebar-react'; +import 'simplebar/dist/simplebar.min.css'; +import { Box, styled, SxProps } from '@mui/material'; + +const SimpleBarStyle = styled(SimpleBar)(() => ({ + maxHeight: '100%', +})); + +interface PropsType { + children: React.ReactElement | React.ReactNode; + sx: SxProps; +} + +const Scrollbar = (props: PropsType) => { + const { children, sx, ...other } = props; + const isMobile = /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test( + navigator.userAgent, + ); + + if (isMobile) { + return {children}; + } + + return ( + + {children} + + ); +}; + +export default Scrollbar; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/Expence.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/Expence.tsx new file mode 100644 index 0000000..55f2c56 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/Expence.tsx @@ -0,0 +1,74 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Typography } from '@mui/material'; +import { Props } from 'react-apexcharts'; + +import DashboardCard from '../../shared/DashboardCard'; + +const Expence = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const error = theme.palette.error.main; + + // chart + const optionsexpencechart: Props = { + chart: { + type: 'donut', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + + toolbar: { + show: false, + }, + height: 120, + }, + labels: ["Profit", "Revenue", "Expance"], + colors: [primary, error, secondary], + plotOptions: { + pie: { + + donut: { + size: '70%', + background: 'transparent' + }, + }, + }, + dataLabels: { + enabled: false, + }, + stroke: { + show: false, + }, + legend: { + show: false, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + }, + }; + const seriesexpencechart = [60, 25, 15]; + + return ( + + <> + $10,230 + + Expense + + + + + ); +}; + +export default Expence; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/Growth.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/Growth.tsx new file mode 100644 index 0000000..5908692 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/Growth.tsx @@ -0,0 +1,92 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Box, Typography, Avatar } from '@mui/material'; + +import DashboardCard from '../../shared/DashboardCard'; +import { Props } from 'react-apexcharts'; +import { IconArrowUpRight } from '@tabler/icons-react'; + +import icon1 from 'src/assets/images/svgs/icon-bars.svg'; + +const Growth = () => { + // chart color + const theme = useTheme(); + const secondary = theme.palette.secondary.main; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'area', + height: 25, + fontFamily: `inherit`, + foreColor: '#a1aab2', + toolbar: { + show: false, + }, + sparkline: { + enabled: true, + }, + group: 'sparklines', + }, + colors: [secondary], + stroke: { + curve: 'straight', + width: 2, + }, + fill: { + type: 'solid', + opacity: 0.05, + }, + markers: { + size: 0, + }, + tooltip: { + theme: 'dark', + x: { + show: false, + }, + }, + }; + const seriescolumnchart = [ + { + name: '', + data: [0, 10, 10, 10, 35, 45, 30, 30, 30, 50, 52, 30, 25, 45, 50, 80, 60, 65], + }, + ]; + + return ( + + <> + + + + + + + + + + 24% + + + + + + Growth + + + + ); +}; + +export default Growth; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/MonthlyEarnings.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/MonthlyEarnings.tsx new file mode 100644 index 0000000..364ab20 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/MonthlyEarnings.tsx @@ -0,0 +1,96 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Stack, Typography, Avatar } from '@mui/material'; +import { IconArrowUpLeft } from '@tabler/icons-react'; + +import DashboardCard from '../../shared/DashboardCard'; +import icon1Img from 'src/assets/images/svgs/icon-master-card-2.svg'; +import { Props } from 'react-apexcharts'; + +const MonthlyEarnings = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.primary.light; + const successlight = theme.palette.success.light; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'area', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 70, + sparkline: { + enabled: true, + }, + group: 'sparklines', + }, + stroke: { + curve: 'smooth', + width: 2, + }, + fill: { + colors: [primarylight], + type: 'solid', + opacity: 0.05, + }, + markers: { + size: 0, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + x: { + show: false, + }, + }, + }; + const seriescolumnchart = [ + { + name: '', + color: primary, + data: [25, 66, 20, 40, 12, 58, 20], + }, + ]; + + return ( + theme.palette.primary.light, width: 40, height: 40 }} + > + + + } + footer={ + + } + > + <> + + + $6,820 + + + + + + + +9% + + + + + + ); +}; + +export default MonthlyEarnings; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/PaymentGateways.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/PaymentGateways.tsx new file mode 100644 index 0000000..b99159d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/PaymentGateways.tsx @@ -0,0 +1,120 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { Stack, Typography, Avatar, Box, Button } from '@mui/material'; +import DashboardCard from '../../shared/DashboardCard'; + +import icon1Img from "src/assets/images/svgs/icon-paypal.svg" +import icon2Img from "src/assets/images/svgs/icon-office-bag.svg" +import icon3Img from "src/assets/images/svgs/icon-master-card.svg" +import icon4Img from "src/assets/images/svgs/icon-pie.svg" + + +interface statType { + title: string; + subtitle: string; + price: number; + color: string; + lightcolor: string; + icon: string; + } + + const PaymentGateways: React.FC = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.primary.light; + const error = theme.palette.error.main; + const errorlight = theme.palette.error.light; + const warning = theme.palette.warning.main; + const warninglight = theme.palette.warning.light; + const secondary = theme.palette.success.main; + const secondarylight = theme.palette.success.light; + + + const stats: statType[] = [ + { + title: 'Paypal', + subtitle: 'Big Brands', + price: 6235, + color: primary, + lightcolor: primarylight, + icon: icon1Img, + }, + { + title: 'Wallet', + subtitle: 'Bill payment', + price: 345, + color: secondary, + lightcolor: secondarylight, + icon: icon2Img, + }, + { + title: 'Credit Card', + subtitle: 'Money reversed', + price: 2235, + color: warning, + lightcolor: warninglight, + icon: icon3Img, + }, + { + title: 'Refund', + subtitle: 'Bill Payment', + price: 32, + color: error, + lightcolor: errorlight, + icon: icon4Img, + }, + ]; + + return ( + + <> + + {stats.map((stat, i) => ( + + + + + + + + {stat.title} + + + {stat.subtitle} + + + + {stat.price < 400 ? ( + + -${stat.price} + + ) : ( + + +${stat.price} + + )} + + ))} + + + + + ); +}; + +export default PaymentGateways; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/ProductPerformances.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/ProductPerformances.tsx new file mode 100644 index 0000000..7fbbaa1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/ProductPerformances.tsx @@ -0,0 +1,443 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import DashboardCard from '../../shared/DashboardCard'; +import CustomSelect from '../../forms/theme-elements/CustomSelect'; +import { Props } from 'react-apexcharts'; +import { + MenuItem, + Typography, + Box, + Table, + TableBody, + TableCell, + TableHead, + TableRow, + Avatar, + Chip, + TableContainer, + Stack, +} from '@mui/material'; + +import img1 from 'src/assets/images/products/s6.jpg'; +import img2 from 'src/assets/images/products/s9.jpg'; +import img3 from 'src/assets/images/products/s7.jpg'; +import img4 from 'src/assets/images/products/s4.jpg'; + +const ProductPerformances = () => { + // for select + const [month, setMonth] = React.useState('1'); + + const handleChange = (event: React.ChangeEvent) => { + setMonth(event.target.value); + }; + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const grey = theme.palette.grey[300]; + const primarylight = theme.palette.primary.light; + const greylight = theme.palette.grey[100]; + + // // chart 1 + const optionsrow1chart: Props = { + chart: { + type: 'area', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 35, + width: 100, + sparkline: { + enabled: true, + }, + group: 'sparklines', + }, + stroke: { + curve: 'smooth', + width: 2, + }, + fill: { + colors: [primarylight], + type: 'solid', + opacity: 0.05, + }, + markers: { + size: 0, + }, + tooltip: { + enabled: false, + }, + }; + const seriesrow1chart = [ + { + name: 'Customers', + color: primary, + data: [30, 25, 35, 20, 30], + }, + ]; + + // chart 2 + const optionsrow2chart: Props = { + chart: { + type: 'area', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 35, + width: 100, + sparkline: { + enabled: true, + }, + group: 'sparklines', + }, + stroke: { + curve: 'smooth', + width: 2, + }, + fill: { + colors: [greylight], + type: 'solid', + opacity: 0.05, + }, + markers: { + size: 0, + }, + tooltip: { + enabled: false, + }, + }; + const seriesrow2chart = [ + { + name: 'Customers', + color: grey, + data: [30, 25, 35, 20, 30], + }, + ]; + + // chart 3 + const optionsrow3chart: Props = { + chart: { + type: 'area', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 35, + width: 100, + sparkline: { + enabled: true, + }, + group: 'sparklines', + }, + stroke: { + curve: 'smooth', + width: 2, + }, + fill: { + colors: [primarylight], + type: 'solid', + opacity: 0.05, + }, + markers: { + size: 0, + }, + tooltip: { + enabled: false, + }, + }; + const seriesrow3chart = [ + { + name: 'Customers', + color: primary, + data: [30, 25, 35, 20, 30], + }, + ]; + + // chart 4 + const optionsrow4chart: Props = { + chart: { + type: 'area', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 35, + width: 100, + sparkline: { + enabled: true, + }, + group: 'sparklines', + }, + stroke: { + curve: 'smooth', + width: 2, + }, + fill: { + colors: [greylight], + type: 'solid', + opacity: 0.05, + }, + markers: { + size: 0, + }, + tooltip: { + enabled: false, + }, + }; + const seriesrow4chart = [ + { + color: grey, + data: [30, 25, 35, 20, 30], + }, + ]; + + return ( + + March 2023 + April 2023 + May 2023 + + } + > + + + + + + + Product + + + + + Progress + + + + + Status + + + + + Sales + + + + + Growth + + + + + + + + + + + + Gaming Console + + + Electronics + + + + + + + 78.5% + + + + theme.palette.success.light, + color: (theme) => theme.palette.success.main, + borderRadius: '6px', + width: 80, + }} + size="small" + label="Low" + /> + + + $3.9k + + + + + + {/* 2 */} + + + + + + + Leather Purse + + + Fashion + + + + + + + 58.6% + + + + theme.palette.warning.light, + color: (theme) => theme.palette.warning.main, + borderRadius: '6px', + width: 80, + }} + size="small" + label="Medium" + /> + + + $3.5k + + + + + + {/* 3 */} + + + + + + + Red Velvate Dress + + + Womens Fashion + + + + + + + 25% + + + + theme.palette.primary.light, + color: (theme) => theme.palette.primary.main, + borderRadius: '6px', + width: 80, + }} + size="small" + label="Very High" + /> + + + $3.5k + + + + + + {/* 4 */} + + + + + + + Headphone Boat + + + Electronics + + + + + + + 96.3% + + + + theme.palette.error.light, + color: (theme) => theme.palette.error.main, + borderRadius: '6px', + width: 80, + }} + size="small" + label="High" + /> + + + $3.5k + + + + + + +
+
+
+ ); +}; + +export default ProductPerformances; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/RecentTransactions.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/RecentTransactions.tsx new file mode 100644 index 0000000..5cdd49a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/RecentTransactions.tsx @@ -0,0 +1,103 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import DashboardCard from '../../shared/DashboardCard'; +import { + TimelineItem, + TimelineOppositeContent, + TimelineSeparator, + TimelineDot, + TimelineConnector, + TimelineContent, + timelineOppositeContentClasses, +} from '@mui/lab'; +import { Link, Typography } from '@mui/material'; +import Timeline from '@mui/lab/Timeline'; + +const RecentTransactions = () => { + return ( + + <> + + + 09:30 am + + + + + Payment received from John Doe of $385.90 + + + 10:00 am + + + + + + New sale recorded{' '} + + #ML-3467 + + + + + 12:00 am + + + + + Payment was made of $64.95 to Michael + + + 09:30 am + + + + + + New sale recorded{' '} + + #ML-3467 + + + + + 09:30 am + + + + + + New arrival recorded{' '} + + #ML-3467 + + + + + 12:00 am + + + + Payment Done + + + + + ); +}; + +export default RecentTransactions; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/RevenueUpdates.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/RevenueUpdates.tsx new file mode 100644 index 0000000..2962216 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/RevenueUpdates.tsx @@ -0,0 +1,116 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Stack, Typography, Avatar, Box } from '@mui/material'; +import DashboardCard from '../../shared/DashboardCard'; +import { Props } from 'react-apexcharts'; + +const RevenueUpdates: React.FC = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 320, + offsetX: -20, + stacked: true, + }, + colors: [primary, secondary], + plotOptions: { + bar: { + horizontal: false, + barHeight: '60%', + columnWidth: '20%', + borderRadius: [6], + borderRadiusApplication: 'end', + borderRadiusWhenStacked: 'all', + }, + }, + stroke: { + show: false, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + show: false, + + }, + yaxis: { + min: -5, + max: 5, + tickAmount: 4, + }, + xaxis: { + categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May'], + axisTicks: { + show: false, + } + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + }, + }; + const seriescolumnchart = [ + { + name: 'Footware', + data: [2.5, 3.7, 3.2, 2.6, 1.9], + }, + { + name: 'Fashionware', + data: [-2.8, -1.1, -3.0, -1.5, -1.9], + }, + ]; + + return ( + + <> + + + + + + Footware + + + + + + + + Fashionware + + + + + + + + + + ); +}; + +export default RevenueUpdates; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/Sales.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/Sales.tsx new file mode 100644 index 0000000..46df356 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/Sales.tsx @@ -0,0 +1,97 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Box, Typography } from '@mui/material'; +import { Props } from 'react-apexcharts'; + +import DashboardCard from '../../shared/DashboardCard'; + +const Sales = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 90, + width:'100%', + stacked: true, + stackType: '100%', + sparkline: { + enabled: true, + }, + }, + colors: [primary, secondary, '#EAEFF4'], + plotOptions: { + bar: { + horizontal: false, + columnWidth: '50%', + borderRadius: [3], + borderRadiusApplication: 'around', + borderRadiusWhenStacked: 'around', + }, + }, + dataLabels: { + enabled: false, + }, + stroke: { + show: false, + width: 1, + colors: ['rgba(0,0,0,0.01)'], + }, + fill: { + opacity: 1, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + x: { + show: false, + }, + }, + responsive: [{ breakpoint: 1025, options: { chart: { height: 150, width: 250 } } }], + }; + const seriescolumnchart = [ + { + color: primary, + name: '', + data: [25, 35, 20, 25, 40, 25], + }, + { + color: secondary, + name: '', + data: [35, 40, 20, 35, 40, 35], + }, + { + color: '#EAEFF4', + name: '', + data: [40, 25, 60, 40, 20, 40], + }, + ]; + + return ( + + <> + $65,432 + + Sales + + + + + + + ); +}; + +export default Sales; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/SalesOverview.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/SalesOverview.tsx new file mode 100644 index 0000000..1abb976 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/SalesOverview.tsx @@ -0,0 +1,149 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Stack, Typography, Box } from '@mui/material'; +import { IconGridDots } from '@tabler/icons-react'; +import { Props } from 'react-apexcharts'; + +import DashboardCard from '../../shared/DashboardCard'; + +const SalesOverview = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const primarylight = theme.palette.primary.light; + const textColor = theme.palette.mode === 'dark' ? 'rgba(255,255,255,0.8)' : '#2A3547'; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'donut', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + + toolbar: { + show: false, + }, + height: 275, + }, + labels: ["Profit", "Revenue", "Expance"], + colors: [primary, primarylight, secondary], + plotOptions: { + pie: { + + donut: { + size: '89%', + background: 'transparent', + + labels: { + show: true, + name: { + show: true, + offsetY: 7, + }, + value: { + show: false, + }, + total: { + show: true, + color: textColor, + fontSize: '20px', + fontWeight: '600', + label: '$500,458', + }, + }, + }, + }, + }, + dataLabels: { + enabled: false, + }, + stroke: { + show: false, + }, + legend: { + show: false, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + }, + }; + const seriescolumnchart = [55, 55, 55]; + + return ( + + <> + + + + + + + + + + + + + + $23,450 + + + Profit + + + + + + + + + + + + $23,450 + + + Expance + + + + + + + ); +}; + +export default SalesOverview; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/SalesTwo.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/SalesTwo.tsx new file mode 100644 index 0000000..aca4158 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/SalesTwo.tsx @@ -0,0 +1,136 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Box, Typography } from '@mui/material'; + +import DashboardCard from '../../shared/DashboardCard'; +import { Props } from 'react-apexcharts'; +import { IconArrowUpRight, IconShoppingCart } from '@tabler/icons-react'; + +const SalesTwo = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 25, + resize: true, + barColor: '#fff', + offsetX: -15, + sparkline: { + enabled: true, + }, + }, + colors: [primary], + grid: { + show: false, + }, + plotOptions: { + bar: { + horizontal: false, + columnWidth: '100%', + borderRadius: 3, + distributed: true, + } + }, + dataLabels: { + enabled: false, + }, + stroke: { + show: true, + width: 5, + colors: ['rgba(0,0,0,0.01)'] + }, + xaxis: { + axisBorder: { + show: false, + }, + axisTicks: { + show: false, + }, + labels: { + show: false, + }, + }, + yaxis: { + labels: { + show: false, + }, + }, + axisBorder: { + show: false, + }, + fill: { + opacity: 1, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + x: { + show: false, + }, + responsive: [ + { + breakpoint: 767, + options: { + chart: { height: 60 }, + plotOptions: { + bar: { columnWidth: "60%" } + } + + } + } + ], + }, + }; + const seriescolumnchart = [ + { + name: '', + data: [100, 60, 35, 90, 35, 100] + }, + ]; + + return ( + + <> + + + + + + + + + + + $16.5k + + Sales + + + + ); +}; + +export default SalesTwo; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/WelcomeCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/WelcomeCard.tsx new file mode 100644 index 0000000..8387693 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/WelcomeCard.tsx @@ -0,0 +1,64 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, Avatar, Typography, Card, CardContent, Grid2 as Grid, Divider, Stack } from '@mui/material'; +import { IconArrowUpRight } from '@tabler/icons-react'; + +import welcomeImg from 'src/assets/images/backgrounds/welcome-bg2.png'; +import userImg from 'src/assets/images/profile/user-1.jpg'; + +const WelcomeCard = () => { + return ( + ( theme.palette.primary.light, py: 0 }}> + + + + + + + + Welcome back Mathew Anderson! + + + + }> + + $2,340 + Today’s Sales + + + 35% + Performance + + + + + + + {welcomeImg} + + + + + ) + ); +}; + +export default WelcomeCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/YearlySales.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/YearlySales.tsx new file mode 100644 index 0000000..f237136 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/ecommerce/YearlySales.tsx @@ -0,0 +1,87 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; + +import DashboardWidgetCard from '../../shared/DashboardWidgetCard'; +import { Props } from 'react-apexcharts'; + +const YearlySales = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.grey[100]; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 295, + }, + colors: [primarylight, primarylight, primary, primarylight, primarylight, primarylight], + plotOptions: { + bar: { + borderRadius: 4, + columnWidth: '45%', + distributed: true, + endingShape: 'rounded', + }, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + yaxis: { + lines: { + show: false, + }, + }, + }, + xaxis: { + categories: [['Apr'], ['May'], ['June'], ['July'], ['Aug'], ['Sept']], + axisBorder: { + show: false, + }, + }, + yaxis: { + labels: { + show: false, + }, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + }, + }; + const seriescolumnchart = [ + { + name: '', + data: [20, 15, 30, 25, 10, 15], + }, + ]; + + return ( + + <> + + + + ); +}; + +export default YearlySales; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/Customers.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/Customers.tsx new file mode 100644 index 0000000..15c78fb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/Customers.tsx @@ -0,0 +1,92 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Stack, Typography, Avatar } from '@mui/material'; +import { IconArrowDownRight } from '@tabler/icons-react'; + +import DashboardCard from '../../shared/DashboardCard'; +import { Props } from 'react-apexcharts'; + +const Customers = () => { + // chart color + const theme = useTheme(); + const secondary = theme.palette.secondary.main; + const secondarylight = theme.palette.secondary.light; + const errorlight = theme.palette.error.light; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'area', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 80, + sparkline: { + enabled: true, + }, + group: 'sparklines', + }, + stroke: { + curve: 'smooth', + width: 2, + }, + fill: { + colors: [secondarylight], + type: 'solid', + opacity: 0.05, + }, + markers: { + size: 0, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + x: { + show: false, + }, + }, + }; + const seriescolumnchart = [ + { + name: '', + color: secondary, + data: [30, 25, 35, 20, 30, 40], + }, + ]; + + return ( + + + + } + > + <> + + Customers + + 36,358 + + + + + + +9% + + + + + ); +}; + +export default Customers; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/EmployeeSalary.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/EmployeeSalary.tsx new file mode 100644 index 0000000..682eaed --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/EmployeeSalary.tsx @@ -0,0 +1,87 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; + +import DashboardWidgetCard from '../../shared/DashboardWidgetCard'; +import { Props } from 'react-apexcharts'; + +const EmployeeSalary = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.grey[100]; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 280, + }, + colors: [primarylight, primarylight, primary, primarylight, primarylight, primarylight], + plotOptions: { + bar: { + borderRadius: 4, + columnWidth: '45%', + distributed: true, + endingShape: 'rounded', + }, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + yaxis: { + lines: { + show: false, + }, + }, + }, + xaxis: { + categories: [['Apr'], ['May'], ['June'], ['July'], ['Aug'], ['Sept']], + axisBorder: { + show: false, + }, + }, + yaxis: { + labels: { + show: false, + }, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + }, + }; + const seriescolumnchart = [ + { + name: '', + data: [20, 15, 30, 25, 10, 15], + }, + ]; + + return ( + + <> + + + + ); +}; + +export default EmployeeSalary; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/MonthlyEarnings.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/MonthlyEarnings.tsx new file mode 100644 index 0000000..4940077 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/MonthlyEarnings.tsx @@ -0,0 +1,94 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Stack, Typography, Avatar, Fab } from '@mui/material'; +import { IconArrowDownRight, IconCurrencyDollar } from '@tabler/icons-react'; + +import DashboardCard from '../../shared/DashboardCard'; +import { Props } from 'react-apexcharts'; + + +const MonthlyEarnings = () => { + // chart color + const theme = useTheme(); + const secondary = theme.palette.secondary.main; + const secondarylight = theme.palette.secondary.light; + const errorlight = theme.palette.error.light; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'area', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 60, + sparkline: { + enabled: true, + }, + group: 'sparklines', + }, + stroke: { + curve: 'smooth', + width: 2, + }, + fill: { + colors: [secondarylight], + type: 'solid', + opacity: 0.05, + }, + markers: { + size: 0, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + x: { + show: false + } + }, + }; + const seriescolumnchart = [ + { + name: '', + color: secondary, + data: [25, 66, 20, 40, 12, 58, 20], + }, + ]; + + return ( + + + + } + footer={ + + } + > + <> + + $6,820 + + + + + + + +9% + + + last year + + + + + ); +}; + +export default MonthlyEarnings; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/Projects.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/Projects.tsx new file mode 100644 index 0000000..fc9a6a0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/Projects.tsx @@ -0,0 +1,114 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Stack, Typography, Avatar } from '@mui/material'; +import { IconArrowUpLeft } from '@tabler/icons-react'; + +import DashboardCard from '../../shared/DashboardCard'; +import { Props } from 'react-apexcharts'; + + +const Projects = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const successlight = theme.palette.success.light; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 80, + resize: true, + barColor: '#fff', + sparkline: { + enabled: true, + }, + }, + colors: [primary], + grid: { + show: false, + }, + plotOptions: { + bar: { + horizontal: false, + startingShape: 'flat', + endingShape: 'flat', + columnWidth: '60%', + barHeight: '20%', + borderRadius: 3, + }, + }, + dataLabels: { + enabled: false, + }, + stroke: { + show: true, + width: 2.5, + colors: ['rgba(0,0,0,0.01)'], + }, + xaxis: { + axisBorder: { + show: false, + }, + axisTicks: { + show: false, + }, + labels: { + show: false, + }, + }, + yaxis: { + labels: { + show: false, + }, + }, + axisBorder: { + show: false, + }, + fill: { + opacity: 1, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + x: { + show: false, + }, + }, + }; + const seriescolumnchart = [ + { + name: '', + data: [4, 10, 9, 7, 9, 10, 11, 8, 10], + }, + ]; + + return ( + + <> + + Projects + + 78,298 + + + + + + +9% + + + + + + ); +}; + +export default Projects; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/RevenueUpdates.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/RevenueUpdates.tsx new file mode 100644 index 0000000..36b26dc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/RevenueUpdates.tsx @@ -0,0 +1,190 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { MenuItem, Grid2 as Grid, Stack, Typography, Button, Avatar, Box } from '@mui/material'; +import { IconGridDots } from '@tabler/icons-react'; +import DashboardCard from '../../shared/DashboardCard'; +import CustomSelect from '../../forms/theme-elements/CustomSelect'; +import { Props } from 'react-apexcharts'; + +const RevenueUpdates = () => { + const [month, setMonth] = React.useState('1'); + + const handleChange = (event: React.ChangeEvent) => { + setMonth(event.target.value); + }; + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: true, + }, + height: 370, + stacked: true, + }, + colors: [primary, secondary], + plotOptions: { + bar: { + horizontal: false, + barHeight: '60%', + columnWidth: '20%', + borderRadius: [6], + borderRadiusApplication: 'end', + borderRadiusWhenStacked: 'all', + }, + }, + + stroke: { + show: false, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + borderColor: 'rgba(0,0,0,0.1)', + strokeDashArray: 3, + xaxis: { + lines: { + show: false, + }, + }, + }, + yaxis: { + min: -5, + max: 5, + tickAmount: 4, + }, + xaxis: { + categories: ['16/08', '17/08', '18/08', '19/08', '20/08', '21/08', '22/08'], + axisBorder: { + show: false, + }, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + }, + }; + const seriescolumnchart = [ + { + name: 'Eanings this month', + data: [1.5, 2.7, 2.2, 3.6, 1.5, 1.0], + }, + { + name: 'Expense this month', + data: [-1.8, -1.1, -2.5, -1.5, -0.6, -1.8], + }, + ]; + + return ( + ( + March 2023 + April 2023 + May 2023 + + } + > + + {/* column */} + + + + + + {/* column */} + + + + + + + + + + + $63,489.50 + + + Total Earnings + + + + + + + + + + Earnings this month + + $48,820 + + + + + + + Expense this month + + $26,498 + + + + + + + ) + ); +}; + +export default RevenueUpdates; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/SellingProducts.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/SellingProducts.tsx new file mode 100644 index 0000000..7943ccb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/SellingProducts.tsx @@ -0,0 +1,91 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, CardContent, Chip, Paper, Stack, Typography, LinearProgress } from '@mui/material'; +import { useTheme } from '@mui/material/styles'; +import SavingsImg from '../../../assets/images/backgrounds/piggy.png'; + +interface sellsData { + product: string; + price: string; + percent: number; + color: string; +} + +const sells: sellsData[] = [ + { + product: 'MaterialPro', + price: '23,568', + percent: 55, + color: 'primary', + }, + { + product: 'Flexy Admin', + price: '23,568', + percent: 20, + color: 'secondary', + }, +]; + +const SellingProducts = () => { + const theme = useTheme(); + const secondarylight = theme.palette.secondary.light; + const primarylight = theme.palette.primary.light; + const secondary = theme.palette.secondary.main; + const primary = theme.palette.primary.main; + const borderColor = theme.palette.divider; + + return ( + + + + Best selling products + + + Overview 2023 + + + + {SavingsImg} + + + + + + {sells.map((sell: any, i: number) => ( + + + + {sell.product} + + ${sell.price} + + + + + + + ))} + + + + + ); +}; + +export default SellingProducts; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/Social.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/Social.tsx new file mode 100644 index 0000000..252ff32 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/Social.tsx @@ -0,0 +1,64 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Link } from 'react-router'; +import { Stack, Typography, Avatar, Box, AvatarGroup } from '@mui/material'; +import { IconMessage2 } from '@tabler/icons-react'; + +import DashboardCard from '../../shared/DashboardCard'; +import ProfileImg from '../../../assets/images/profile/user-1.jpg'; +import User1Img from '../../../assets/images/profile/user-2.jpg'; +import User2Img from '../../../assets/images/profile/user-3.jpg'; +import User3Img from '../../../assets/images/profile/user-4.jpg'; +import User4Img from '../../../assets/images/profile/user-5.jpg'; + +const Social = () => { + return ( + + <> + + + + Super awesome, Vue coming soon! + + 22 March, 2023 + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default Social; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/TopCards.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/TopCards.tsx new file mode 100644 index 0000000..7a91fdb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/TopCards.tsx @@ -0,0 +1,89 @@ +import { Box, CardContent, Grid2 as Grid, Typography } from '@mui/material'; + +import icon1 from '../../../assets/images/svgs/icon-connect.svg'; +import icon2 from '../../../assets/images/svgs/icon-user-male.svg'; +import icon3 from '../../../assets/images/svgs/icon-briefcase.svg'; +import icon4 from '../../../assets/images/svgs/icon-mailbox.svg'; +import icon5 from '../../../assets/images/svgs/icon-favorites.svg'; +import icon6 from '../../../assets/images/svgs/icon-speech-bubble.svg'; + +interface cardType { + icon: string; + title: string; + digits: string; + bgcolor: string; +} + +const topcards: cardType[] = [ + { + icon: icon2, + title: 'Employees', + digits: '96', + bgcolor: 'primary', + }, + { + icon: icon3, + title: 'Clients', + digits: '3,650', + bgcolor: 'warning', + }, + { + icon: icon4, + title: 'Projects', + digits: '356', + bgcolor: 'secondary', + }, + { + icon: icon5, + title: 'Events', + digits: '696', + bgcolor: 'error', + }, + { + icon: icon6, + title: 'Payroll', + digits: '$96k', + bgcolor: 'success', + }, + { + icon: icon1, + title: 'Reports', + digits: '59', + bgcolor: 'info', + }, +]; + +const TopCards = () => { + return ( + ( + {topcards.map((topcard, i) => ( + + + + {topcard.icon} + + {topcard.title} + + + {topcard.digits} + + + + + ))} + ) + ); +}; + +export default TopCards; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/TopPerformerData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/TopPerformerData.ts new file mode 100644 index 0000000..6118629 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/TopPerformerData.ts @@ -0,0 +1,55 @@ +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; + +interface PerformerType { + id: string; + imgsrc: string; + name: string; + post: string; + pname: string; + status: string; + budget: string; +} + +const TopPerformerData: PerformerType[] = [ + { + id: '1', + imgsrc: img1, + name: 'Sunil Joshi', + post: 'Web Designer', + pname: 'Elite Admin', + status: 'Low', + budget: '3.9', + }, + { + id: '2', + imgsrc: img2, + name: 'John Deo', + post: 'Web Developer', + pname: 'Flexy Admin', + status: 'Medium', + budget: '24.5', + }, + { + id: '3', + imgsrc: img3, + name: 'Mathew Anderson', + post: 'Web Manager', + pname: 'Material Pro', + status: 'High', + budget: '12.8', + }, + { + id: '4', + imgsrc: img4, + name: 'Yuvraj Sheth', + post: 'Project Manager', + pname: 'Xtreme Admin', + status: 'Very High', + budget: '2.4', + }, +]; + +export default TopPerformerData; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/TopPerformers.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/TopPerformers.tsx new file mode 100644 index 0000000..c6e3a68 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/TopPerformers.tsx @@ -0,0 +1,140 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import DashboardCard from '../../shared/DashboardCard'; +import CustomSelect from '../../forms/theme-elements/CustomSelect'; +import { + MenuItem, + Typography, + Box, + Table, + TableBody, + TableCell, + TableHead, + TableRow, + Avatar, + Chip, + TableContainer, + Stack, +} from '@mui/material'; +import TopPerformerData from './TopPerformerData'; + +const performers = TopPerformerData; + +const TopPerformers = () => { + // for select + const [month, setMonth] = React.useState('1'); + + const handleChange = (event: React.ChangeEvent) => { + setMonth(event.target.value); + }; + + return ( + + March 2023 + April 2023 + May 2023 + + } + > + + + + + + + Assigned + + + + + Project + + + + + Priority + + + + + Budget + + + + + + {performers.map((basic) => ( + + + + + + + {basic.name} + + + {basic.post} + + + + + + + {basic.pname} + + + + {/* theme.palette.error.light + : basic.status === 'Medium' + ? (theme) => theme.palette.warning.light + : basic.status === 'Low' + ? (theme) => theme.palette.success.light + : (theme) => theme.palette.secondary.light, + color: + basic.status === 'High' + ? (theme) => theme.palette.error.main + : basic.status === 'Medium' + ? (theme) => theme.palette.warning.main + : basic.status === 'Low' + ? (theme) => theme.palette.success.main + : (theme) => theme.palette.secondary.main, + borderRadius: '8px', + }} + size="small" + label={basic.status} + /> + + + ${basic.budget}k + + + ))} + +
+
+
+ ); +}; + +export default TopPerformers; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/WeeklyStats.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/WeeklyStats.tsx new file mode 100644 index 0000000..cbef6c4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/WeeklyStats.tsx @@ -0,0 +1,161 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Stack, Typography, Avatar, Box } from '@mui/material'; +import DashboardCard from '../../shared/DashboardCard'; +import { IconGridDots } from '@tabler/icons-react'; +import { Props } from 'react-apexcharts'; + +interface Stat { + title: string; + subtitle: string; + percent: string; + color: string; + lightcolor: string; + icon: any; +} + +const WeeklyStats: React.FC = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.primary.light; + const error = theme.palette.error.main; + const errorlight = theme.palette.error.light; + const secondary = theme.palette.success.main; + const secondarylight = theme.palette.success.light; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'area', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 130, + sparkline: { + enabled: true, + }, + group: 'sparklines', + }, + stroke: { + curve: 'smooth', + width: 2, + }, + fill: { + type: 'gradient', + gradient: { + shadeIntensity: 0, + inverseColors: false, + opacityFrom: 0.45, + opacityTo: 0, + stops: [20, 180], + }, + }, + markers: { + size: 0, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + x: { + show: false, + }, + }, + }; + const seriescolumnchart = [ + { + name: 'Weekly Stats', + color: primary, + data: [5, 15, 5, 10, 5], + }, + ]; + + const stats: Stat[] = [ + { + title: 'Top Sales', + subtitle: 'Johnathan Doe', + percent: '68', + color: primary, + lightcolor: primarylight, + icon: , + }, + { + title: 'Best Seller', + subtitle: 'Footware', + percent: '45', + color: secondary, + lightcolor: secondarylight, + icon: , + }, + { + title: 'Most Commented', + subtitle: 'Fashionware', + percent: '14', + color: error, + lightcolor: errorlight, + icon: , + }, + ]; + + return ( + + <> + + + + + {stats.map((stat, i) => ( + + + + {stat.icon} + + + + {stat.title} + + + {stat.subtitle} + + + + + + +{stat.percent} + + + + ))} + + + + ); +}; + +export default WeeklyStats; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/YearlyBreakup.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/YearlyBreakup.tsx new file mode 100644 index 0000000..c58f0d0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/dashboards/modern/YearlyBreakup.tsx @@ -0,0 +1,126 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Grid2 as Grid, Stack, Typography, Avatar } from '@mui/material'; +import { IconArrowUpLeft } from '@tabler/icons-react'; + +import DashboardCard from '../../shared/DashboardCard'; +import { Props } from 'react-apexcharts'; + +const YearlyBreakup = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.primary.light; + const successlight = theme.palette.success.light; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'donut', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 155, + }, + colors: [primary, primarylight, '#F9F9FD'], + plotOptions: { + pie: { + startAngle: 0, + endAngle: 360, + donut: { + size: '75%', + background: 'transparent', + }, + }, + }, + tooltip: { + enabled: false, + }, + stroke: { + show: false, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + responsive: [ + { + breakpoint: 991, + options: { + chart: { + width: 120, + }, + }, + }, + ], + }; + const seriescolumnchart = [38, 40, 25]; + + return ( + ( + + {/* column */} + + + $36,358 + + + + + + + +9% + + + last year + + + + + + + 2022 + + + + + + 2023 + + + + + {/* column */} + + + + + ) + ); +}; + +export default YearlyBreakup; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-custom/code/FormCustomCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-custom/code/FormCustomCode.tsx new file mode 100644 index 0000000..54fef77 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-custom/code/FormCustomCode.tsx @@ -0,0 +1,671 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const FormCustomCode = () => { + return ( + <> + + {` + +import * as React from 'react'; +import { + Grid2 as Grid, + Box, + Typography, + FormControl, + MenuItem, + RadioGroup, + FormControlLabel, + Button, + SliderValueLabelProps, +} from '@mui/material'; +import { SliderThumb } from '@mui/material/Slider'; +import { LocalizationProvider } from '@mui/x-date-pickers'; +import { AdapterDayjs } from "@mui/x-date-pickers/AdapterDayjs"; +import { DateTimePicker } from '@mui/x-date-pickers/DateTimePicker'; +import { TimePicker } from '@mui/x-date-pickers/TimePicker'; +import { styled } from '@mui/material/styles'; +import { TextField } from '@mui/material'; +import { Select } from '@mui/material'; +import { Slider } from '@mui/material'; +import { Switch } from '@mui/material'; +import { Button } from '@mui/material'; +import { Typography } from '@mui/material'; +import Checkbox, { CheckboxProps } from '@mui/material/Checkbox'; +import Radio, { RadioProps } from '@mui/material/Radio'; +import { useTheme } from '@mui/material/styles'; +import { Card, CardHeader, CardContent, Divider, Box } from '@mui/material'; +import { useSelector } from '@/store/hooks'; +import { AppState } from '@/store/store'; +import { IconVolume, IconVolume2 } from '@tabler/icons-react'; +import { Stack } from '@mui/material'; + +const CustomTextField = styled((props: any) => )(({ theme }) => ({ + '& .MuiOutlinedInput-input::-webkit-input-placeholder': { + color: theme.palette.text.secondary, + opacity: '0.8', + }, + '& .MuiOutlinedInput-input.Mui-disabled::-webkit-input-placeholder': { + color: theme.palette.text.secondary, + opacity: '1', + }, + '& .Mui-disabled .MuiOutlinedInput-notchedOutline': { + borderColor: theme.palette.grey[200], + }, +})); + +const CustomSelect = styled((props: any) => )(({}) => ({})); + +const countries = [ + { + value: 'india', + label: 'India', + }, + { + value: 'uk', + label: 'United Kingdom', + }, + { + value: 'srilanka', + label: 'Srilanka', + }, +]; + +const [country, setCountry] = React.useState(''); + + const handleChange = (event: any) => { + setCountry(event.target.value); + }; + + const [showPassword, setShowPassword] = React.useState(false); + + const handleClickShowPassword = () => setShowPassword((show) => !show); + + const handleMouseDownPassword = (event: React.MouseEvent) => { + event.preventDefault(); +}; + +
+ + Account Details + + + + + Username + + + + + + + + Email + + + + @example.com} + id="fs-email" + placeholder="john.deo" + fullWidth + /> + + + + Password + + + + + + {showPassword ? : } + + + } + id="fs-pwd" + placeholder="john.deo" + fullWidth + /> + + + + + Personal Info + + + + + Full Name + + + + + + + + Country + + + + + {countries.map((option) => ( + + {option.label} + + ))} + + + + + Birth Date + + + + + + + + Phone no + + + + + + + + + + + + + +
+`} +
+ + ); +}; + +export default FormSeparatorCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbBasicHeaderForm.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbBasicHeaderForm.tsx new file mode 100644 index 0000000..ad01f43 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbBasicHeaderForm.tsx @@ -0,0 +1,283 @@ +"use client"; +import React from "react"; +import { + Box, + FormControlLabel, + Button, + Grid2 as Grid, + MenuItem, + FormControl, + Alert, +} from "@mui/material"; +import CustomTextField from "../theme-elements/CustomTextField"; +import CustomSelect from "../theme-elements/CustomSelect"; +import CustomRadio from "../theme-elements/CustomRadio"; +import CustomFormLabel from "../theme-elements/CustomFormLabel"; +import ParentCard from "../../shared/ParentCard"; + +import BasicHeaderFormCode from "src/components/forms/form-layouts/code/BasicHeaderFormCode"; + +const currencies = [ + { + value: "female", + label: "Female", + }, + { + value: "male", + label: "Male", + }, + { + value: "other", + label: "Other", + }, +]; + +const countries = [ + { + value: "india", + label: "India", + }, + { + value: "uk", + label: "United Kingdom", + }, + { + value: "srilanka", + label: "Srilanka", + }, +]; + +const FbBasicHeaderForm = () => { + const [currency, setCurrency] = React.useState(""); + + const handleChange2 = (event: any) => { + setCurrency(event.target.value); + }; + + const [selectedValue, setSelectedValue] = React.useState(""); + + const handleChange3 = (event: any) => { + setSelectedValue(event.target.value); + }; + + const [country, setCountry] = React.useState(""); + + const handleChange4 = (event: any) => { + setCountry(event.target.value); + }; + + return ( + (
+ {/* ------------------------------------------------------------------------------------------------ */} + {/* Basic Checkbox */} + {/* ------------------------------------------------------------------------------------------------ */} + } + footer={ + <> + + + + } + > + <> + Person Info +
+ + + + First Name + + + + Select Gender + + + {currencies.map((option) => ( + + {option.label} + + ))} + + Membership + + + + } + /> + } + name="radio-button-demo" + /> + + + + + + Last Name + + + + Date of Birth + + + + +
+ Address + + + + Street + + + + + + + City + + + + + + State + + + + + + Post Code + + + + + + Country + + + {countries.map((option) => ( + + {option.label} + + ))} + + + + +
+
) + ); +}; + +export default FbBasicHeaderForm; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbDefaultForm.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbDefaultForm.tsx new file mode 100644 index 0000000..6d0a31c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbDefaultForm.tsx @@ -0,0 +1,221 @@ +"use client"; +import React from "react"; +import { + FormControlLabel, + Button, + Grid2 as Grid, + RadioGroup, + FormControl, + MenuItem, +} from "@mui/material"; +import CustomTextField from "../theme-elements/CustomTextField"; +import CustomSelect from "../theme-elements/CustomSelect"; +import CustomCheckbox from "../theme-elements/CustomCheckbox"; +import CustomRadio from "../theme-elements/CustomRadio"; +import CustomFormLabel from "../theme-elements/CustomFormLabel"; +import ParentCard from "../../shared/ParentCard"; + +import DefaultFormCode from "src/components/forms/form-layouts/code/DefaultFormCode"; + +const numbers = [ + { + value: "one", + label: "One", + }, + { + value: "two", + label: "Two", + }, + { + value: "three", + label: "Three", + }, + { + value: "four", + label: "Four", + }, +]; + +const FbDefaultForm = () => { + const [state, setState] = React.useState({ + checkedA: false, + checkedB: false, + checkedC: false, + }); + + const handleChange = (event: any) => { + setState({ ...state, [event.target.name]: event.target.checked }); + }; + + const [value, setValue] = React.useState(""); + + const handleChange2 = (event: any) => { + setValue(event.target.value); + }; + + const [number, setNumber] = React.useState(""); + + const handleChange3 = (event: any) => { + setNumber(event.target.value); + }; + + return ( + (}> +
+ + Default Text + + + Email + + + Password + + + + + Textarea + + + + Read Only + + + + + + } + label="Check this custom checkbox" + /> + + } + label="Check this custom checkbox" + /> + + } + label="Check this custom checkbox" + /> + + + + + } + label="Toggle this custom radio" + /> + } + label="Toggle this custom radio" + /> + } + label="Toggle this custom radio" + /> + + + + + + Select + + + {numbers.map((option) => ( + + {option.label} + + ))} + +
+ +
+ +
) + ); +}; + +export default FbDefaultForm; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbDisabledForm.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbDisabledForm.tsx new file mode 100644 index 0000000..dd7d5f8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbDisabledForm.tsx @@ -0,0 +1,51 @@ +'use client' + +import { Box, Button } from '@mui/material'; +import CustomTextField from '../theme-elements/CustomTextField'; +import CustomFormLabel from '../theme-elements/CustomFormLabel'; +import ParentCard from '../../shared/ParentCard'; + +const FbDisabledForm = () => ( + +
+ + Name + + + Email + + Password + + + + + +
+); + +export default FbDisabledForm; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbInputVariants.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbInputVariants.tsx new file mode 100644 index 0000000..b3f2f48 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbInputVariants.tsx @@ -0,0 +1,63 @@ +"use client"; + +import { FormControl } from "@mui/material"; +import CustomTextField from "../theme-elements/CustomTextField"; +import CustomFormLabel from "../theme-elements/CustomFormLabel"; +import ParentCard from "../../shared/ParentCard"; + +import InputVariantsCode from "src/components/forms/form-layouts/code/InputVariantsCode"; + +const FbInputVariants = () => { + return ( + }> +
+ + Success Input + + + Error Input + + + + Input with Error text + + + + +
+ ); +}; + +export default FbInputVariants; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbLeftIconForm.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbLeftIconForm.tsx new file mode 100644 index 0000000..0c18df7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbLeftIconForm.tsx @@ -0,0 +1,129 @@ +"use client"; +import React from "react"; +import { + Button, + FormControlLabel, + FormControl, + InputAdornment, + OutlinedInput, + Stack, +} from "@mui/material"; +import CustomCheckbox from "../theme-elements/CustomCheckbox"; +import CustomFormLabel from "../theme-elements/CustomFormLabel"; +import ParentCard from "../../shared/ParentCard"; +import { IconLock, IconMail, IconUser } from "@tabler/icons-react"; + +import LeftIconFormCode from "src/components/forms/form-layouts/code/LeftIconFormCode"; + +const FbLeftIconForm = () => { + const [state, setState] = React.useState({ + checkedA: false, + }); + + const handleChange = (event: any) => { + setState({ ...state, [event.target.name]: event.target.checked }); + }; + + return ( + } + footer={ + <> + + + + + + } + > +
+ + + Username + + + + + } + id="username-text" + placeholder="Username" + fullWidth + /> + + {/* 2 */} + + Email + + + + } + id="mail-text" + placeholder="Email" + fullWidth + /> + + {/* 3 */} + + Password + + + + } + id="pwd-text" + placeholder="Password" + fullWidth + /> + + + + + Confirm Password + + + + + } + id="cpwd-text" + placeholder="Confirm Password" + fullWidth + /> + + + + } + sx={{ + mt: "10px", + }} + label="Remember Me!" + /> + +
+ ); +}; + +export default FbLeftIconForm; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbOrdinaryForm.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbOrdinaryForm.tsx new file mode 100644 index 0000000..8c02877 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbOrdinaryForm.tsx @@ -0,0 +1,72 @@ +'use client' + +import { FormControlLabel, Button } from '@mui/material'; +import CustomTextField from '../theme-elements/CustomTextField'; +import CustomCheckbox from '../theme-elements/CustomCheckbox'; +import CustomFormLabel from '../theme-elements/CustomFormLabel'; +import ParentCard from '../../shared/ParentCard'; +import React from 'react'; + +const FbOrdinaryForm = () => { + const [state, setState] = React.useState({ + checkedB: false, + }); + + const handleChange = (event: any) => { + setState({ ...state, [event.target.name]: event.target.checked }); + }; + + return ( + +
+ + Email + + + Password + + + + } + label="Check Me Out!" + sx={{ + mb: 1, + }} + /> +
+ +
+ +
+ ); +}; + +export default FbOrdinaryForm; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbReadonlyForm.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbReadonlyForm.tsx new file mode 100644 index 0000000..2878c52 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbReadonlyForm.tsx @@ -0,0 +1,67 @@ +'use client' + +import { Button } from '@mui/material'; +import CustomTextField from '../theme-elements/CustomTextField'; +import CustomFormLabel from '../theme-elements/CustomFormLabel'; +import ParentCard from '../../shared/ParentCard'; + +const FbReadonlyForm = () => { + return ( + +
+ + Name + + + Email + + + Password + + +
+ +
+ +
+ ); +}; + +export default FbReadonlyForm; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbRightIconForm.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbRightIconForm.tsx new file mode 100644 index 0000000..23a287e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/FbRightIconForm.tsx @@ -0,0 +1,121 @@ +'use client' + +import { + Button, + FormControlLabel, + FormControl, + InputAdornment, + OutlinedInput, +} from '@mui/material'; +import CustomCheckbox from '../theme-elements/CustomCheckbox'; +import CustomFormLabel from '../theme-elements/CustomFormLabel'; +import ParentCard from '../../shared/ParentCard'; +import { IconLock, IconUser, IconMail } from '@tabler/icons-react'; +import { Stack } from '@mui/system'; +import React from 'react'; + +const FbRightIconForm = () => { + const [state, setState] = React.useState({ + checkedB: false, + }); + + const handleChange = (event: any) => { + setState({ ...state, [event.target.name]: event.target.checked }); + }; + + return ( + + + + + + + + }> +
+ + + Username + + + + + } + id="username2-text" + placeholder="Username" + fullWidth + /> + + {/* 2 */} + + Email + + + + } + id="mail2-text" + placeholder="Email" + fullWidth + /> + + {/* 3 */} + + Password + + + + } + id="pwd2-text" + placeholder="Password" + fullWidth + /> + + + + Confirm Password + + + + } + id="cpwd2-text" + placeholder="Confirm Password" + fullWidth + /> + + + } + sx={{ + mt: '10px', + }} + label="Remember Me!" + /> + +
+ ); +}; + +export default FbRightIconForm; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/code/BasicHeaderFormCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/code/BasicHeaderFormCode.tsx new file mode 100644 index 0000000..b2c0c53 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/code/BasicHeaderFormCode.tsx @@ -0,0 +1,367 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; + +const BasicHeaderFormCode = () => { + return ( + <> + + {` +"use client"; +import React from "react"; +import { + Box, + FormControlLabel, + Button, + Grid2 as Grid, + MenuItem, + FormControl, + Alert, +} from "@mui/material"; +import { styled } from '@mui/material/styles'; +import { Typography } from '@mui/material'; +import { TextField } from '@mui/material'; +import { Select } from '@mui/material'; +import Radio, { RadioProps } from '@mui/material/Radio'; + +const BpIcon2 = styled('span')(({ theme }) => ({ + borderRadius: '50%', + width: 21, + height: 21, + boxShadow: + theme.palette.mode === 'dark' + ? '0 0 0 1px {theme.palette.grey[200]}' + : 'inset 0 0 0 1px {theme.palette.grey[300]}', + backgroundColor: 'transparent', + '.Mui-focusVisible &': { + outline: + theme.palette.mode === 'dark' + ? '0px auto {theme.palette.grey[200]}' + : '0px auto {theme.palette.grey[300]}', + outlineOffset: 2, + }, + 'input:hover ~ &': { + backgroundColor: theme.palette.primary, + }, + 'input:disabled ~ &': { + boxShadow: 'none', + background: theme.palette.grey[100], + }, +})); + +const BpCheckedIcon2 = styled(BpIcon2)(({ theme }) => ({ + boxShadow: 'none', + '&:before': { + display: 'block', + width: 21, + height: 21, + backgroundImage: + theme.palette.mode === 'dark' + ? 'radial-gradient({theme.palette.background.paper},{theme.palette.background.paper} 28%,transparent 32%)' + : 'radial-gradient(#fff,#fff 28%,transparent 32%)', + content: '""', + }, +})); + +const CustomTextField = styled((props: any) => )(({ theme }) => ({ + '& .MuiOutlinedInput-input::-webkit-input-placeholder': { + color: theme.palette.text.secondary, + opacity: '0.8', + }, + '& .MuiOutlinedInput-input.Mui-disabled::-webkit-input-placeholder': { + color: theme.palette.text.secondary, + opacity: '1', + }, + '& .Mui-disabled .MuiOutlinedInput-notchedOutline': { + borderColor: theme.palette.grey[200], + }, +})); + +const CustomFormLabel = styled((props: any) => ( + +))(() => ({ + marginBottom: '5px', + marginTop: '25px', + display: 'block', +})); + +const CustomSelect = styled((props: any) => )(({}) => ({})); + +function CustomCheckbox(props: CheckboxProps) { + return ( + + } + icon={} + inputProps={{ 'aria-label': 'Checkbox demo' }} + {...props} + /> + ); +} + +function CustomRadio(props: RadioProps) { + return ( + + } + icon={} + inputProps={{ 'aria-label': 'Checkbox demo' }} + {...props} + /> + ); +} + +const numbers = [ + { + value: 'one', + label: 'One', + }, + { + value: 'two', + label: 'Two', + }, + { + value: 'three', + label: 'Three', + }, + { + value: 'four', + label: 'Four', + }, +]; + +const [state, setState] = React.useState({ + checkedA: false, + checkedB: false, + checkedC: false, +}); + +const handleChange = (event: any) => { + setState({ ...state, [event.target.name]: event.target.checked }); +}; + +const [value, setValue] = React.useState(''); + +const handleChange2 = (event: any) => { + setValue(event.target.value); +}; + +const [number, setNumber] = React.useState(''); + +const handleChange3 = (event: any) => { + setNumber(event.target.value); +}; + +
+ + Default Text + + + Email + + + Password + + + + + Textarea + + + + Read Only + + + + + + } + label="Check this custom checkbox" + /> + + } + label="Check this custom checkbox" + /> + + } + label="Check this custom checkbox" + /> + + + + + } + label="Toggle this custom radio" + /> + } + label="Toggle this custom radio" + /> + } + label="Toggle this custom radio" + /> + + + + + + Select + + + {numbers.map((option) => ( + + {option.label} + + ))} + +
+ +
+ +`} +
+ + ); +}; + +export default DefaultFormCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/code/InputVariantsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/code/InputVariantsCode.tsx new file mode 100644 index 0000000..b1ec2f3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/code/InputVariantsCode.tsx @@ -0,0 +1,93 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; + +const InputVariantsCode = () => { + return ( + <> + + {` +"use client"; + +import { FormControl } from '@mui/material'; +import { styled } from '@mui/material/styles'; +import { Typography } from '@mui/material'; +import { TextField } from '@mui/material'; + +const CustomTextField = styled((props: any) => )(({ theme }) => ({ + '& .MuiOutlinedInput-input::-webkit-input-placeholder': { + color: theme.palette.text.secondary, + opacity: '0.8', + }, + '& .MuiOutlinedInput-input.Mui-disabled::-webkit-input-placeholder': { + color: theme.palette.text.secondary, + opacity: '1', + }, + '& .Mui-disabled .MuiOutlinedInput-notchedOutline': { + borderColor: theme.palette.grey[200], + }, +})); + +const CustomFormLabel = styled((props: any) => ( + +))(() => ({ + marginBottom: '5px', + marginTop: '25px', + display: 'block', +})); + +
+ + Success Input + + + Error Input + + + Input with Error text + + + +`} +
+ + ); +}; + +export default InputVariantsCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/code/LeftIconFormCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/code/LeftIconFormCode.tsx new file mode 100644 index 0000000..e528ac5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/code/LeftIconFormCode.tsx @@ -0,0 +1,197 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; + +const LeftIconFormCode = () => { + return ( + <> + + {` +"use client"; +import React from "react"; +import { + Button, + FormControlLabel, + FormControl, + InputAdornment, + OutlinedInput, + Stack, +} from "@mui/material"; +import { IconLock, IconMail, IconUser } from "@tabler/icons-react"; +import { styled } from '@mui/material/styles'; +import { Typography } from '@mui/material'; +import Checkbox, { CheckboxProps } from '@mui/material/Checkbox'; + +const BpIcon = styled('span')(({ theme }) => ({ + borderRadius: 3, + width: 19, + height: 19, + marginLeft: '4px', + boxShadow: + theme.palette.mode === 'dark' + ? '0 0 0 1px {theme.palette.grey[200]}' + : 'inset 0 0 0 1px {theme.palette.grey[300]}', + backgroundColor: 'transparent', + + '.Mui-focusVisible &': { + outline: + theme.palette.mode === 'dark' + ? '0px auto {theme.palette.grey[200]}' + : '0px auto {theme.palette.grey[300]}', + outlineOffset: 2, + }, + 'input:hover ~ &': { + backgroundColor: theme.palette.mode === 'dark' ? theme.palette.primary : theme.palette.primary, + }, + 'input:disabled ~ &': { + boxShadow: 'none', + background: theme.palette.grey[100], + }, +})); + +const BpCheckedIcon = styled(BpIcon)({ + boxShadow: 'none', + width: 19, + height: 19, + '&:before': { + display: 'block', + width: 19, + height: 19, + backgroundImage: + "url(\"data:image/svg+xml;charset=utf-8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath" + + " fill-rule='evenodd' clip-rule='evenodd' d='M12 5c-.28 0-.53.11-.71.29L7 9.59l-2.29-2.3a1.003 " + + "1.003 0 00-1.42 1.42l3 3c.18.18.43.29.71.29s.53-.11.71-.29l5-5A1.003 1.003 0 0012 5z' fill='%23fff'/%3E%3C/svg%3E\")", + content: '""', + }, +}); + +// Inspired by blueprintjs +function CustomCheckbox(props: CheckboxProps) { + return ( + + } + icon={} + inputProps={{ 'aria-label': 'Checkbox demo' }} + {...props} + /> + ); +} + +const CustomFormLabel = styled((props: any) => ( + +))(() => ({ + marginBottom: '5px', + marginTop: '25px', + display: 'block', +})); + +const [state, setState] = React.useState({ + checkedA: false, +}); + +const handleChange = (event: any) => { + setState({ ...state, [event.target.name]: event.target.checked }); +}; + +
+ + + Username + + + + + } + id="username-text" + placeholder="Username" + fullWidth + /> + + + Email + + + + } + id="mail-text" + placeholder="Email" + fullWidth + /> + + + Password + + + + } + id="pwd-text" + placeholder="Password" + fullWidth + /> + + + Confirm Password + + + + } + id="cpwd-text" + placeholder="Confirm Password" + fullWidth + /> + + + + } + sx={{ + mt: '10px', + }} + label="Remember Me!" + /> + + <> + + + + + + +`} +
+ + ); +}; + +export default LeftIconFormCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/index.tsx new file mode 100644 index 0000000..2d27835 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-layouts/index.tsx @@ -0,0 +1,19 @@ +import FbOrdinaryForm from './FbOrdinaryForm'; +import FbDefaultForm from './FbDefaultForm'; +import FbBasicHeaderForm from './FbBasicHeaderForm'; +import FbReadonlyForm from './FbReadonlyForm'; +import FbDisabledForm from './FbDisabledForm'; +import FbLeftIconForm from './FbLeftIconForm'; +import FbRightIconForm from './FbRightIconForm'; +import FbInputVariants from './FbInputVariants'; + +export { + FbOrdinaryForm, + FbDefaultForm, + FbBasicHeaderForm, + FbReadonlyForm, + FbDisabledForm, + FbLeftIconForm, + FbRightIconForm, + FbInputVariants, +}; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVCheckbox.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVCheckbox.tsx new file mode 100644 index 0000000..7de7c8d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVCheckbox.tsx @@ -0,0 +1,57 @@ +'use client' + +import { useFormik } from 'formik'; +import * as yup from 'yup'; +import { Box, Button, Stack, FormHelperText } from '@mui/material'; +import CustomCheckbox from '../theme-elements/CustomCheckbox'; + +const validationSchema = yup.object({ + color: yup.array().min(1, 'At least one color is required'), +}); + +const FVCheckbox = () => { + const formik = useFormik({ + initialValues: { + color: [], + }, + validationSchema, + onSubmit: (values) => { + alert(values.color); + }, + }); + + return ( +
+ + + + + + {formik.errors.color && ( + + {' '} + {formik.errors.color}{' '} + + )} + + + + + +
+ ); +}; + +export default FVCheckbox; \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVLogin.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVLogin.tsx new file mode 100644 index 0000000..86891bb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVLogin.tsx @@ -0,0 +1,100 @@ +'use client' + +import { useFormik } from 'formik'; +import * as yup from 'yup'; +import { Link } from 'react-router'; + +import { Box, Button, Stack, FormGroup, FormControlLabel, Typography } from '@mui/material'; + +import CustomTextField from '../theme-elements/CustomTextField'; +import CustomFormLabel from '../theme-elements/CustomFormLabel'; +import CustomCheckbox from '../theme-elements/CustomCheckbox'; + +const validationSchema = yup.object({ + firstName: yup + .string() + .min(2, 'Too Short!') + .max(50, 'Too Long!') + .required('Firstname is Required'), + lastName: yup.string().min(2, 'Too Short!').max(50, 'Too Long!').required('Lastname is Required'), + email: yup.string().email('Enter a valid email').required('Email is required'), + password: yup + .string() + .min(8, 'Password should be of minimum 8 characters length') + .required('Password is required'), + changepassword: yup.string().when('password', { + is: (val: string) => (val && val.length > 0 ? true : false), + then: yup.string().oneOf([yup.ref('password')], 'Both password need to be the same'), + }), +}); + +const FVRegister = () => { + const formik = useFormik({ + initialValues: { + firstName: '', + email: '', + password: '', + changepassword: '', + }, + validationSchema: validationSchema, + onSubmit: (values) => { + alert(JSON.stringify(values, null, 2)); + }, + }); + + return ( +
+ + + Email Address + + + + Password + + + + + + } + label="Remeber this Device" + /> + + + Forgot Password ? + + + +
+ ); +}; + +export default FVRegister; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVOnLeave.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVOnLeave.tsx new file mode 100644 index 0000000..a990a4e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVOnLeave.tsx @@ -0,0 +1,71 @@ +'use client' + +import { useFormik } from 'formik'; +import * as yup from 'yup'; + +import { Box, Button, Stack } from '@mui/material'; + +import CustomTextField from '../theme-elements/CustomTextField'; +import CustomFormLabel from '../theme-elements/CustomFormLabel'; + +const validationSchema = yup.object({ + emailInstant: yup.string().email('Enter a valid email').required('Email is required'), + passwordInstant: yup + .string() + .min(8, 'Password should be of minimum 8 characters length') + .required('Password is required'), +}); + +const FVOnLeave = () => { + const formik = useFormik({ + initialValues: { + emailInstant: '', + passwordInstant: '', + }, + validationSchema, + onSubmit: (values) => { + alert(values.emailInstant); + }, + }); + + return ( +
+ + + Email Address + + + + Password + + + + + + +
+ ); +}; + +export default FVOnLeave; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVRadio.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVRadio.tsx new file mode 100644 index 0000000..df93aef --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVRadio.tsx @@ -0,0 +1,100 @@ +'use client' + +import { useFormik } from 'formik'; +import * as yup from 'yup'; + +import { + Box, + Button, + Stack, + FormControlLabel, + FormControl, + RadioGroup, + Radio, + FormHelperText, +} from '@mui/material'; + +const validationSchema = yup.object({ + color: yup.string().required('Color selection is required'), +}); + +const FVRadio = () => { + const formik = useFormik({ + initialValues: { + color: '', + }, + validationSchema, + onSubmit: (values) => { + alert(values.color); + }, + }); + + return ( +
+ + + + + + } + label="Primary" + /> + + } + label="Error" + /> + + } + label="Secondary" + /> + + + {formik.errors.color && ( + + {' '} + {formik.errors.color}{' '} + + )} + + + + + +
+ ); +}; + +export default FVRadio; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVRegister.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVRegister.tsx new file mode 100644 index 0000000..1442a73 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVRegister.tsx @@ -0,0 +1,123 @@ +'use client' +import { useFormik } from 'formik'; +import * as yup from 'yup'; +import { Link } from 'react-router'; + +import { Box, Button, Stack, FormGroup, FormControlLabel, Typography } from '@mui/material'; +import CustomTextField from '../theme-elements/CustomTextField'; +import CustomFormLabel from '../theme-elements/CustomFormLabel'; +import CustomCheckbox from '../theme-elements/CustomCheckbox'; + +const validationSchema = yup.object({ + firstName: yup + .string() + .min(2, 'Too Short!') + .max(50, 'Too Long!') + .required('Firstname is Required'), + lastName: yup.string().min(2, 'Too Short!').max(50, 'Too Long!').required('Lastname is Required'), + email: yup.string().email('Enter a valid email').required('Email is required'), + password: yup + .string() + .min(8, 'Password should be of minimum 8 characters length') + .required('Password is required'), + changepassword: yup.string().when('password', { + is: (val: any) => (val && val.length > 0 ? true : false), + then: yup.string().oneOf([yup.ref('password')], 'Both password need to be the same'), + }), +}); + +const FVRegister = () => { + const formik = useFormik({ + initialValues: { + firstName: '', + email: '', + password: '', + changepassword: '', + }, + validationSchema: validationSchema, + onSubmit: (values) => { + alert(JSON.stringify(values, null, 2)); + }, + }); + + return ( +
+ + + Name + + + + Email + + + + Password + + + + Confirm Password + + + + + + } + label="Remeber this Device" + /> + + + Forgot Password ? + + + +
+ ); +}; + +export default FVRegister; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVSelect.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVSelect.tsx new file mode 100644 index 0000000..6e2d6da --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/FVSelect.tsx @@ -0,0 +1,62 @@ +'use client' +import { useFormik } from 'formik'; +import * as yup from 'yup'; + +import { Box, Button, Stack, FormHelperText, MenuItem } from '@mui/material'; + +import CustomFormLabel from '../theme-elements/CustomFormLabel'; +import CustomSelect from '../theme-elements/CustomSelect'; + +const validationSchema = yup.object({ + age: yup.number().required('Age selection is required.'), +}); + +const FVSelect = () => { + const formik = useFormik({ + initialValues: { + age: '', + }, + validationSchema, + onSubmit: (values) => { + alert(values.age); + }, + }); + + return ( +
+ + + Age + + + None + + Ten + Twenty + Thirty + + {formik.errors.age && ( + + {' '} + {formik.errors.age}{' '} + + )} + + + + + +
+ ); +}; + +export default FVSelect; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/CheckboxCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/CheckboxCode.tsx new file mode 100644 index 0000000..9e5311e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/CheckboxCode.tsx @@ -0,0 +1,128 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const CheckboxCode = () => { + return ( + <> + + {` +"use client"; + +import { useFormik } from 'formik'; +import * as yup from 'yup'; +import { Box, Button, Stack, FormHelperText } from '@mui/material'; +import { styled } from '@mui/material/styles'; +import Checkbox, { CheckboxProps } from '@mui/material/Checkbox'; + +const BpIcon = styled('span')(({ theme }) => ({ + borderRadius: 3, + width: 19, + height: 19, + marginLeft: '4px', + boxShadow: + theme.palette.mode === 'dark' + ? '0 0 0 1px {theme.palette.grey[200]}' + : 'inset 0 0 0 1px {theme.palette.grey[300]}', + backgroundColor: 'transparent', + + '.Mui-focusVisible &': { + outline: + theme.palette.mode === 'dark' + ? '0px auto {theme.palette.grey[200]}' + : '0px auto {theme.palette.grey[300]}', + outlineOffset: 2, + }, + 'input:hover ~ &': { + backgroundColor: theme.palette.mode === 'dark' ? theme.palette.primary : theme.palette.primary, + }, + 'input:disabled ~ &': { + boxShadow: 'none', + background: theme.palette.grey[100], + }, +})); + +const BpCheckedIcon = styled(BpIcon)({ + boxShadow: 'none', + width: 19, + height: 19, + '&:before': { + display: 'block', + width: 19, + height: 19, + backgroundImage: + "url(\"data:image/svg+xml;charset=utf-8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath" + + " fill-rule='evenodd' clip-rule='evenodd' d='M12 5c-.28 0-.53.11-.71.29L7 9.59l-2.29-2.3a1.003 " + + "1.003 0 00-1.42 1.42l3 3c.18.18.43.29.71.29s.53-.11.71-.29l5-5A1.003 1.003 0 0012 5z' fill='%23fff'/%3E%3C/svg%3E\")", + content: '""', + }, +}); + + +function CustomCheckbox(props: CheckboxProps) { + return ( + + } + icon={} + inputProps={{ 'aria-label': 'Checkbox demo' }} + {...props} + /> + ); +} + +const validationSchema = yup.object({ + color: yup.array().min(1, 'At least one color is required'), +}); + +const formik = useFormik({ + initialValues: { + color: [], + }, + validationSchema, + onSubmit: (values) => { + alert(values.color); + }, + }); + +
+ + + + + + {formik.errors.color && ( + + {' '} + {formik.errors.color}{' '} + + )} + + + + + +
+`} +
+ + ); +}; + +export default CheckboxCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/OnLeaveCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/OnLeaveCode.tsx new file mode 100644 index 0000000..d42fd46 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/OnLeaveCode.tsx @@ -0,0 +1,110 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const OnLeaveCode = () => { + return ( + <> + + {` +"use client"; + +import { useFormik } from 'formik'; +import * as yup from 'yup'; +import { styled } from '@mui/material/styles'; +import { TextField } from '@mui/material'; +import { Typography } from '@mui/material'; + +import { Box, Button, Stack } from '@mui/material'; + +const CustomTextField = styled((props: any) => )(({ theme }) => ({ + '& .MuiOutlinedInput-input::-webkit-input-placeholder': { + color: theme.palette.text.secondary, + opacity: '0.8', + }, + '& .MuiOutlinedInput-input.Mui-disabled::-webkit-input-placeholder': { + color: theme.palette.text.secondary, + opacity: '1', + }, + '& .Mui-disabled .MuiOutlinedInput-notchedOutline': { + borderColor: theme.palette.grey[200], + }, +})); + +const CustomFormLabel = styled((props: any) => ( + +))(() => ({ + marginBottom: '5px', + marginTop: '25px', + display: 'block', +})); + +const validationSchema = yup.object({ + emailInstant: yup.string().email('Enter a valid email').required('Email is required'), + passwordInstant: yup + .string() + .min(8, 'Password should be of minimum 8 characters length') + .required('Password is required'), +}); + + + const formik = useFormik({ + initialValues: { + emailInstant: '', + passwordInstant: '', + }, + validationSchema, + onSubmit: (values) => { + alert(values.emailInstant); + }, + }); + + return ( +
+ + + Email Address + + + + Password + + + + + + +
+ ); + +`} +
+ + ); +}; + +export default OnLeaveCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/RadioCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/RadioCode.tsx new file mode 100644 index 0000000..cdb5677 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/RadioCode.tsx @@ -0,0 +1,108 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; + +const RadioCode = () => { + return ( + <> + + {` +"use client"; + +import { useFormik } from 'formik'; +import * as yup from 'yup'; + +import { + Box, + Button, + Stack, + FormControlLabel, + FormControl, + RadioGroup, + Radio, + FormHelperText, +} from '@mui/material'; + +const validationSchema = yup.object({ + color: yup.string().required('Color selection is required'), +}); + +const formik = useFormik({ + initialValues: { + color: '', + }, + validationSchema, + onSubmit: (values) => { + alert(values.color); + }, +}); + +
+ + + + + + } + label="Primary" + /> + + } + label="Error" + /> + + } + label="Secondary" + /> + + + {formik.errors.color && ( + + {' '} + {formik.errors.color}{' '} + + )} + + + + + +
+`} +
+ + ); +}; + +export default RadioCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/SelectCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/SelectCode.tsx new file mode 100644 index 0000000..4bde3a6 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/form-validation/code/SelectCode.tsx @@ -0,0 +1,87 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; + +const SelectCode = () => { + return ( + <> + + {` +"use client"; + +import { useFormik } from 'formik'; +import * as yup from 'yup'; +import { styled } from '@mui/material/styles'; +import { Typography } from '@mui/material'; +import { Select } from '@mui/material'; + +import { Box, Button, Stack, FormHelperText, MenuItem } from '@mui/material'; + +const CustomFormLabel = styled((props: any) => ( + +))(() => ({ + marginBottom: '5px', + marginTop: '25px', + display: 'block', +})); + +const CustomSelect = styled((props: any) => )(({ }) => ({})); + +export default CustomSelect; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/theme-elements/CustomSlider.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/theme-elements/CustomSlider.tsx new file mode 100644 index 0000000..d309277 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/theme-elements/CustomSlider.tsx @@ -0,0 +1,24 @@ +'use client' +import { styled } from '@mui/material/styles'; +import { Slider } from '@mui/material'; + +const CustomSlider = styled(Slider)(({ theme }) => ({ + '& .MuiSlider-rail': { + height: '9px', + borderRadius: '9px', + opacity: '1', + backgroundColor: theme.palette.grey[200], + }, + '& .MuiSlider-thumb': { + borderRadius: '50%', + backgroundColor: () => theme.palette.secondary.main, + width: '23px', + height: '23px', + }, + '& .MuiSlider-track': { + height: '9px', + borderRadius: '9px', + }, +})); + +export default CustomSlider; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/theme-elements/CustomSocialButton.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/theme-elements/CustomSocialButton.tsx new file mode 100644 index 0000000..e55afcc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/forms/theme-elements/CustomSocialButton.tsx @@ -0,0 +1,16 @@ +'use client' + +import { styled } from '@mui/material/styles'; +import { Button } from '@mui/material'; + +const CustomSocialButton = styled((props: any) => ( + + + + + + + Do you need a highly customizable and developer friendly premium next.js admin + template packed with numerous features? Modernize React Admin Template has + everything you need. This bootstrap based admin template is designed in accordance + with industry standards and best practices to provide you. + + + + + ) + ); +}; + +export default Banner; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/key-metric/ContentArea.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/key-metric/ContentArea.tsx new file mode 100644 index 0000000..74783e9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/key-metric/ContentArea.tsx @@ -0,0 +1,30 @@ +import { Typography } from '@mui/material'; + +const ContentArea = () => { + return ( + <> + + Key metric at a glance + + + From the year we were founded to the impressive customer base we've built, and the growth + percentages that reflect our continuous improvement, these numbers tell our story at a + glance. Explore the data that drives our mission and underscores our commitment to + excellence. + + + ); +}; + +export default ContentArea; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/key-metric/Key.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/key-metric/Key.tsx new file mode 100644 index 0000000..bb1e37d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/key-metric/Key.tsx @@ -0,0 +1,67 @@ +import { Grid2 as Grid, Typography } from '@mui/material'; + +const keys = [ + { + text: 'Founded', + title: '2019', + subtext: 'When we founded Modernize', + }, + { + text: 'Growth', + title: '1,400%', + subtext: 'Revenue growth in 2024', + }, + { + text: 'Customers', + title: '300k+', + isMargin: true, + subtext: 'Customers on Modernize', + }, + { + text: 'Dashboards', + title: '25k+', + isMargin: true, + subtext: 'Dashboards built using Modernize', + }, +]; + +const Key = () => { + return ( + ( + {keys.map((key, i) => ( + + + {key.text} + + + {key.title} + + {key.subtext} + + ))} + ) + ); +}; + +export default Key; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/key-metric/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/key-metric/index.tsx new file mode 100644 index 0000000..bfbc21e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/key-metric/index.tsx @@ -0,0 +1,42 @@ +import { Box, Container, Grid2 as Grid } from '@mui/material'; +import ContentArea from './ContentArea'; +import Key from './Key'; + +const KeyMetric = () => { + return ( + ( theme.shadows[10], + }} + > + + + + + + + + + + + ) + ); +}; + +export default KeyMetric; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/process/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/process/index.tsx new file mode 100644 index 0000000..56cbb9d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/about/process/index.tsx @@ -0,0 +1,145 @@ +import { Box, Stack, Typography, Grid2 as Grid, Container, Divider } from '@mui/material'; + +import Icon1 from 'src/assets/images/svgs/icon-briefcase.svg'; +import FeatureApp from 'src/assets/images/frontend-pages/homepage/feature-apps.png'; +import IconBubble from 'src/assets/images/svgs/icon-speech-bubble.svg'; +import IconFav from 'src/assets/images/svgs/icon-favorites.svg'; + +const Process = () => { + return ( + ( + + + + + The hassle-free setup process + + + + + + + + + + + icon1 + + + Light & Dark Color Schemes + + + Choose your preferred visual style effortlessly. + + + + + + + + + + + 12+ Ready to Use Application Designs + + + {' '} + Instantly deployable designs for your applications. + + + + + icon1 + + + + + + + + + + icon1 + + + Code Improvements + + + {' '} + Benefit from continuous improvements and optimizations. + + + + + + + + + + + icon1 + + + 50+ UI Components + + + {' '} + A rich collection for seamless user experiences. + + + + + + + + + ) + ); +}; + +export default Process; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/blog/banner/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/blog/banner/index.tsx new file mode 100644 index 0000000..a5f71b3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/blog/banner/index.tsx @@ -0,0 +1,40 @@ +import { Box, Typography, Container, Grid2 as Grid } from "@mui/material"; + +const Banner = () => { + + return (<> + + + + + Blog Page + Latest blog & news + + + + + + + ); +}; + +export default Banner; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/contact/banner/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/contact/banner/index.tsx new file mode 100644 index 0000000..459ac30 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/contact/banner/index.tsx @@ -0,0 +1,70 @@ +import { Box, Typography, Container, Grid2 as Grid } from '@mui/material'; + +const Banner = () => { + return (<> + + + + + + Contact us + + + We'd love to hear from you + + + + + + + + + + + ); +}; + +export default Banner; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/contact/form/Address.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/contact/form/Address.tsx new file mode 100644 index 0000000..fa78548 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/contact/form/Address.tsx @@ -0,0 +1,39 @@ +import { Box, Typography, Divider } from '@mui/material'; +import { styled } from '@mui/material/styles'; + +import Shape1 from 'src/assets/images/frontend-pages/contact/shape1.png'; + +const ShapeBg = styled(Box)(() => ({ + position: 'absolute', + right: 0, + top: 0, +})); + +const Address = () => { + return ( + + + img + + + + Reach Out Today + + + Have questions or need assistance? We're just a message away. + + + + + + Our Location + + + Visit us in person or find our contact details to connect with us directly. + + + + ); +}; + +export default Address; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/contact/form/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/contact/form/index.tsx new file mode 100644 index 0000000..b3d1740 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/contact/form/index.tsx @@ -0,0 +1,146 @@ +import React from 'react'; +import { Box, Container, Grid2 as Grid, MenuItem, Button } from '@mui/material'; +import CustomFormLabel from '../../../forms/theme-elements/CustomFormLabel'; +import CustomTextField from '../../../forms/theme-elements/CustomTextField'; +import CustomSelect from '../../../forms/theme-elements/CustomSelect'; +import Address from './Address'; + +const numbers = [ + { + value: 'one', + label: 'General Enquiry', + }, + { + value: 'two', + label: 'General Enquiry 2', + }, +]; + +const Form = () => { + const [number, setNumber] = React.useState('one'); + + const handleChange3 = (event: any) => { + setNumber(event.target.value); + }; + + return (<> + + + + +
+ + + + First Name * + + + + + + Last Name * + + + + + + Phone Number * + + + + + + Email * + + + + + + Enquire related to * + + + {numbers.map((option) => ( + + {option.label} + + ))} + + + + + Message + + + + + + + +
+
+ +
+ + + + + ); +}; + +export default Form; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/banner/Banner.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/banner/Banner.tsx new file mode 100644 index 0000000..ab04380 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/banner/Banner.tsx @@ -0,0 +1,291 @@ +import React from 'react'; +import { + Box, + Stack, + Typography, + AvatarGroup, + Avatar, + Container, + Grid2 as Grid, + Button, + useTheme, +} from '@mui/material'; +import useMediaQuery from '@mui/material/useMediaQuery'; +import Tooltip from '@mui/material/Tooltip'; + +import Dialog from '@mui/material/Dialog'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; + +// icons +import icon1 from 'src/assets/images/frontend-pages/icons/icon-react.svg'; +import icon2 from 'src/assets/images/frontend-pages/icons/icon-mui.svg'; +import icon3 from 'src/assets/images/frontend-pages/icons/icon-next.svg'; +import icon4 from 'src/assets/images/frontend-pages/icons/icon-ts.svg'; +import icon5 from 'src/assets/images/frontend-pages/icons/icon-redux.svg'; +import icon6 from 'src/assets/images/frontend-pages/icons/icon-tabler.svg'; + +import BannerTopLeft from 'src/assets/images/frontend-pages/homepage/banner-top-left.svg'; +import BannerBottomPart from 'src/assets/images/frontend-pages/homepage/bottom-part.svg'; +import BannerTopRight from 'src/assets/images/frontend-pages/homepage/banner-top-right.svg'; + +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; + +import iconPlay from 'src/assets/images/frontend-pages/homepage/icon-play.svg'; + +const Frameworks = [ + { + name: 'React', + icon: icon1, + }, + { + name: 'Material Ui', + icon: icon2, + }, + { + name: 'React', + icon: icon3, + }, + { + name: 'Typescript', + icon: icon4, + }, + { + name: 'Redux', + icon: icon5, + }, + { + name: 'Tabler Icon', + icon: icon6, + }, +]; +const Banner = () => { + const theme = useTheme(); + // sidebar + const lgUp = useMediaQuery(theme.breakpoints.up('lg')); + + const [open, setOpen] = React.useState(false); + + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + + return ( + ( + + + {lgUp ? ( + + banner + + ) : null} + + + + Most powerful &{' '} + + developer friendly + {' '} + dashboard + + + + + + + + + 52,589+ developers & agencies using our templates + + + + + + + + + + + + + + + + + {Frameworks.map((fw, i) => ( + + + {fw.icon} + + + ))} + + + {lgUp ? ( + + banner + + ) : null} + + + {lgUp ? ( + banner + ) : null} + + ) + ); +}; + +export default Banner; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabEmbedding.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabEmbedding.tsx new file mode 100644 index 0000000..ea3e3db --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabEmbedding.tsx @@ -0,0 +1,165 @@ +import { Box, Divider, Typography, Grid2 as Grid, Button } from '@mui/material'; + +import { styled } from '@mui/material/styles'; +import { IconMinus, IconPlus } from '@tabler/icons-react'; +import Accordion from '@mui/material/Accordion'; +import AccordionSummary from '@mui/material/AccordionSummary'; +import AccordionDetails from '@mui/material/AccordionDetails'; +import { useState } from 'react'; + +import IconAcc from 'src/assets/images/frontend-pages/homepage/accordian1.jpg'; + +const StyledAccordian = styled(Accordion)(() => ({ + boxShadow: 'none', + marginBottom: '0 !important', + '&.Mui-expanded': { + margin: '0', + }, + '& .MuiAccordionSummary-root': { + padding: 0, + minHeight: '60px', + }, + '& .MuiAccordionDetails-root': { + padding: '0 0 20px', + }, +})); + +const TabEmbedding = () => { + const [expanded, setExpanded] = useState(true); + const [expanded2, setExpanded2] = useState(false); + const [expanded3, setExpanded3] = useState(false); + + const handleChange2 = () => { + setExpanded(!expanded); + }; + + const handleChange3 = () => { + setExpanded2(!expanded2); + }; + + const handleChange4 = () => { + setExpanded3(!expanded3); + }; + + return ( + ( + + img + + + + Defend your focus + + + + + ) : ( + + ) + } + aria-controls="panel3-content" + id="panel3-header" + > + + Round robin pooling + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + ) : ( + + ) + } + aria-controls="panel1-content" + id="panel1-header" + > + + Combine teammate schedules + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + ) : ( + + ) + } + aria-controls="panel2-content" + id="panel2-header" + > + + Factor in outside colleagues + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + + + + + ) + ); +}; +export default TabEmbedding; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabPayments.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabPayments.tsx new file mode 100644 index 0000000..828dd5a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabPayments.tsx @@ -0,0 +1,163 @@ +import { Box, Divider, Typography, Grid2 as Grid, Button } from '@mui/material'; + +import { styled } from '@mui/material/styles'; +import { IconMinus, IconPlus } from '@tabler/icons-react'; +import Accordion from '@mui/material/Accordion'; +import AccordionSummary from '@mui/material/AccordionSummary'; +import AccordionDetails from '@mui/material/AccordionDetails'; +import { useState } from 'react'; + +import IconAcc from 'src/assets/images/frontend-pages/homepage/accordian1.jpg'; + +const StyledAccordian = styled(Accordion)(() => ({ + boxShadow: 'none', + marginBottom: '0 !important', + '&.Mui-expanded': { + margin: '0', + }, + '& .MuiAccordionSummary-root': { + padding: 0, + minHeight: '60px', + }, + '& .MuiAccordionDetails-root': { + padding: '0 0 20px', + }, +})); + +const TabPayments = () => { + const [expanded, setExpanded] = useState(true); + const [expanded2, setExpanded2] = useState(false); + const [expanded3, setExpanded3] = useState(false); + + const handleChange2 = () => { + setExpanded(!expanded); + }; + + const handleChange3 = () => { + setExpanded2(!expanded2); + }; + + const handleChange4 = () => { + setExpanded3(!expanded3); + }; + + return ( + ( + + img + + + + Defend your focus + + + + + ) : ( + + ) + } + aria-controls="panel1-content" + id="panel1-header" + > + + Combine teammate schedules + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + ) : ( + + ) + } + aria-controls="panel2-content" + id="panel2-header" + > + + Factor in outside colleagues + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + ) : ( + + ) + } + aria-controls="panel3-content" + id="panel3-header" + > + + Round robin pooling + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + + + + ) + ); +}; +export default TabPayments; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabTeamScheduling.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabTeamScheduling.tsx new file mode 100644 index 0000000..740360f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabTeamScheduling.tsx @@ -0,0 +1,163 @@ +import { Box, Divider, Typography, Grid2 as Grid, Button } from '@mui/material'; + +import { styled } from '@mui/material/styles'; +import { IconMinus, IconPlus } from '@tabler/icons-react'; +import Accordion from '@mui/material/Accordion'; +import AccordionSummary from '@mui/material/AccordionSummary'; +import AccordionDetails from '@mui/material/AccordionDetails'; +import { useState } from 'react'; +import IconAcc from 'src/assets/images/frontend-pages/homepage/accordian1.jpg'; + +const StyledAccordian = styled(Accordion)(() => ({ + boxShadow: 'none', + marginBottom: '0 !important', + '&.Mui-expanded': { + margin: '0', + }, + '& .MuiAccordionSummary-root': { + padding: 0, + minHeight: '60px', + }, + '& .MuiAccordionDetails-root': { + padding: '0 0 20px', + }, +})); + +const TabTeamScheduling = () => { + const [expanded, setExpanded] = useState(true); + const [expanded2, setExpanded2] = useState(false); + const [expanded3, setExpanded3] = useState(false); + + const handleChange2 = () => { + setExpanded(!expanded); + }; + + const handleChange3 = () => { + setExpanded2(!expanded2); + }; + + const handleChange4 = () => { + setExpanded3(!expanded3); + }; + + return ( + ( + + img + + + + Defend your focus + + + + + ) : ( + + ) + } + aria-controls="panel2-content" + id="panel2-header" + > + + Factor in outside colleagues + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + ) : ( + + ) + } + aria-controls="panel1-content" + id="panel1-header" + > + + Combine teammate schedules + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + ) : ( + + ) + } + aria-controls="panel3-content" + id="panel3-header" + > + + Round robin pooling + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + + + + ) + ); +}; +export default TabTeamScheduling; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabWorkflows.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabWorkflows.tsx new file mode 100644 index 0000000..f13ed7d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/TabWorkflows.tsx @@ -0,0 +1,163 @@ +import { Box, Divider, Typography, Grid2 as Grid, Button } from '@mui/material'; + +import { styled } from '@mui/material/styles'; +import { IconMinus, IconPlus } from '@tabler/icons-react'; +import Accordion from '@mui/material/Accordion'; +import AccordionSummary from '@mui/material/AccordionSummary'; +import AccordionDetails from '@mui/material/AccordionDetails'; +import { useState } from 'react'; +import IconAcc from 'src/assets/images/frontend-pages/homepage/accordian1.jpg'; + +const StyledAccordian = styled(Accordion)(() => ({ + boxShadow: 'none', + marginBottom: '0 !important', + '&.Mui-expanded': { + margin: '0', + }, + '& .MuiAccordionSummary-root': { + padding: 0, + minHeight: '60px', + }, + '& .MuiAccordionDetails-root': { + padding: '0 0 20px', + }, +})); + +const TabWorkflows = () => { + const [expanded, setExpanded] = useState(true); + const [expanded2, setExpanded2] = useState(false); + const [expanded3, setExpanded3] = useState(false); + + const handleChange2 = () => { + setExpanded(!expanded); + }; + + const handleChange3 = () => { + setExpanded2(!expanded2); + }; + + const handleChange4 = () => { + setExpanded3(!expanded3); + }; + + return ( + ( + + img + + + + Defend your focus + + + + + ) : ( + + ) + } + aria-controls="panel2-content" + id="panel2-header" + > + + Factor in outside colleagues + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + ) : ( + + ) + } + aria-controls="panel1-content" + id="panel1-header" + > + + Combine teammate schedules + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + ) : ( + + ) + } + aria-controls="panel3-content" + id="panel3-header" + > + + Round robin pooling + + + + + Factor in availability for required attendees, and skip checking for conflicts for + optional attendees. + + + + + + + + + + ) + ); +}; +export default TabWorkflows; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/index.tsx new file mode 100644 index 0000000..bc63830 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/defend-focus/index.tsx @@ -0,0 +1,127 @@ +import * as React from 'react'; +import { Box, Divider, Container } from '@mui/material'; +import Tab from '@mui/material/Tab'; +import TabContext from '@mui/lab/TabContext'; +import TabList from '@mui/lab/TabList'; +import TabPanel from '@mui/lab/TabPanel'; +import { styled } from '@mui/material/styles'; +import { IconAppWindow, IconArrowRampLeft, IconUserCircle, IconWallet } from '@tabler/icons-react'; +import { useTheme } from '@mui/material/styles'; +import TabTeamScheduling from './TabTeamScheduling'; +import TabPayments from './TabPayments'; +import TabEmbedding from './TabEmbedding'; +import TabWorkflows from './TabWorkflows'; + +const COMMON_TAB = [ + { + value: '1', + icon: , + label: 'Team Scheduling', + disabled: false, + }, + { value: '2', icon: , label: 'Payments', disabled: false }, + { + value: '3', + icon: , + label: 'Embedding', + disabled: true, + }, + { + value: '4', + icon: , + label: 'Workflows', + disabled: true, + }, +]; + +const StyledTabPanelItem = styled(TabPanel)(() => ({ + padding: 0, + marginTop: '85px', +})); + +const DefendFocus = () => { + const theme = useTheme(); + const borderColor = theme.palette.divider; + + const [value, setValue] = React.useState('1'); + + const handleChange = (newValue: any) => { + setValue(newValue); + }; + + const StyledTab = styled(Tab)(() => ({ + fontWeight: 500, + borderRight: `1px solid ${borderColor}`, + '& .MuiTab-iconWrapper': { + marginRight: '12px', + width: '24px', + height: '24px', + strokeWidth: '1.5px', + }, + '&:last-child': { + borderRight: 0, + }, + })); + + return ( + theme.shadows[10], pb: { xs: 2, lg: 4 } }}> + + + + + + {COMMON_TAB.map((tab, index) => ( + + ))} + + + + + + + + + + + + + + + + + + + + + + + ); +}; +export default DefendFocus; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/exceptional-feature/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/exceptional-feature/index.tsx new file mode 100644 index 0000000..7931f4a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/exceptional-feature/index.tsx @@ -0,0 +1,304 @@ +import { Box, Grid2 as Grid, Typography, Container } from '@mui/material'; +import { styled } from '@mui/material/styles'; +import { useTheme } from '@mui/material/styles'; + +import IconColor from 'src/assets/images/frontend-pages/icons/icon-color.svg'; +import IconSidebar from 'src/assets/images/frontend-pages/icons/icon-sidebar.svg'; +import IconPages from 'src/assets/images/frontend-pages/icons/icon-pages.svg'; +import IconComponents from 'src/assets/images/frontend-pages/icons/icon-components.svg'; +import IconFramework from 'src/assets/images/frontend-pages/icons/icon-framework.svg'; +import IconIcons from 'src/assets/images/frontend-pages/icons/icon-icons.svg'; +import IconResponsive from 'src/assets/images/frontend-pages/icons/icon-responsive.svg'; +import IconSass from 'src/assets/images/frontend-pages/icons/icon-sass.svg'; +import IconCustomize from 'src/assets/images/frontend-pages/icons/icon-customize.svg'; +import IconChart from 'src/assets/images/frontend-pages/icons/icon-chart.svg'; +import IconTable from 'src/assets/images/frontend-pages/icons/icon-table.svg'; +import IconUpdate from 'src/assets/images/frontend-pages/icons/icon-update.svg'; +import IconSupport from 'src/assets/images/frontend-pages/icons/icon-support.svg'; + +const StyledAnimationFeature = styled(Box)(() => ({ + width: '100%', + overflowX: 'hidden', + whiteSpace: 'nowrap', + boxSizing: 'border-box', +})); + +const StyledAnimationContent = styled(Box)(() => ({ + animation: 'marquee 25s linear infinite', +})); + +const StyledAnimationContent2 = styled(Box)(() => ({ + animation: 'marquee2 25s linear infinite', +})); + +const slide1 = [ + { + icon: IconColor, + text: '6 Theme Colors', + }, + { + icon: IconSidebar, + text: 'Dark & Light Sidebar', + }, + { + icon: IconPages, + text: '65+ Page Templates', + }, + { + icon: IconComponents, + text: '50+ UI Components', + }, + { + icon: IconColor, + text: '6 Theme Colors', + }, + { + icon: IconSidebar, + text: 'Dark & Light Sidebar', + }, + { + icon: IconPages, + text: '65+ Page Templates', + }, + { + icon: IconComponents, + text: '50+ UI Components', + }, + { + icon: IconColor, + text: '6 Theme Colors', + }, + { + icon: IconSidebar, + text: 'Dark & Light Sidebar', + }, + { + icon: IconPages, + text: '65+ Page Templates', + }, + { + icon: IconComponents, + text: '50+ UI Components', + }, +]; + +const slide2 = [ + { + icon: IconFramework, + text: 'Material Ui', + }, + { + icon: IconIcons, + text: '3400+ Icon', + }, + { + icon: IconResponsive, + text: 'Fully Responsive', + }, + { + icon: IconSass, + text: 'Sassbase CSS', + }, + { + icon: IconFramework, + text: 'Material Ui', + }, + { + icon: IconIcons, + text: '3400+ Icon', + }, + { + icon: IconResponsive, + text: 'Fully Responsive', + }, + { + icon: IconSass, + text: 'Sassbase CSS', + }, + { + icon: IconFramework, + text: 'Material Ui', + }, + { + icon: IconIcons, + text: '3400+ Icon', + }, + { + icon: IconResponsive, + text: 'Fully Responsive', + }, + { + icon: IconSass, + text: 'Sassbase CSS', + }, +]; + +const slide3 = [ + { + icon: IconCustomize, + text: 'Easy to Customize', + }, + { + icon: IconChart, + text: 'Lots of Chart Options', + }, + { + icon: IconTable, + text: 'Lots of Table Examples', + }, + { + icon: IconUpdate, + text: 'Regular Updates', + }, + { + icon: IconSupport, + text: 'Dedicated Support', + }, + { + icon: IconCustomize, + text: 'Easy to Customize', + }, + { + icon: IconChart, + text: 'Lots of Chart Options', + }, + { + icon: IconTable, + text: 'Lots of Table Examples', + }, + { + icon: IconUpdate, + text: 'Regular Updates', + }, + { + icon: IconSupport, + text: 'Dedicated Support', + }, + { + icon: IconCustomize, + text: 'Easy to Customize', + }, + { + icon: IconChart, + text: 'Lots of Chart Options', + }, + { + icon: IconTable, + text: 'Lots of Table Examples', + }, + { + icon: IconUpdate, + text: 'Regular Updates', + }, + { + icon: IconSupport, + text: 'Dedicated Support', + }, +]; + +const ExceptionalFeature = () => { + const theme = useTheme(); + + const StyledFeatureBox = styled(Box)(() => ({ + boxShadow: theme.shadows[10], + backgroundColor: theme.palette.background.default, + minHeight: '72px', + width: '315px', + borderRadius: '16px', + marginTop: '15px', + marginBottom: '15px', + display: 'flex', + alignItems: 'center', + justifyContent: 'center', + gap: '10px', + flexShrink: 0, + })); + + return (<> + + + + + + + Enjoy unparalleled features & exceptional flexibility. + + + + + + + + {slide1.map((slide, i) => ( + + color + + {slide.text} + + + ))} + + + + + + {slide2.map((slide, i) => ( + + color + + {slide.text} + + + ))} + + + + + + {slide3.map((slide, i) => ( + + color + + {slide.text} + + + ))} + + + + + ); +}; + +export default ExceptionalFeature; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/faq/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/faq/index.tsx new file mode 100644 index 0000000..4da9d38 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/faq/index.tsx @@ -0,0 +1,271 @@ +import { Box, Typography, Grid2 as Grid, Container, Link } from '@mui/material'; + +import { styled } from '@mui/material/styles'; +import { IconMinus, IconPlus } from '@tabler/icons-react'; +import { useTheme } from '@mui/material/styles'; +import Accordion from '@mui/material/Accordion'; +import AccordionSummary from '@mui/material/AccordionSummary'; +import AccordionDetails from '@mui/material/AccordionDetails'; +import { useState } from 'react'; + +const FAQ = () => { + const theme = useTheme(); + + const [expanded, setExpanded] = useState(true); + const [expanded2, setExpanded2] = useState(false); + const [expanded3, setExpanded3] = useState(false); + const [expanded4, setExpanded4] = useState(false); + const [expanded5, setExpanded5] = useState(false); + const [expanded6, setExpanded6] = useState(false); + + const StyledAccordian = styled(Accordion)(() => ({ + borderRadius: '8px', + marginBottom: '16px !important', + boxShadow: theme.palette.mode == 'light' ? '0px 3px 0px rgba(235, 241, 246, 0.25)' : 'unset', + border: `1px solid ${theme.palette.divider}`, + '&:before': { + display: 'none', + }, + '&.Mui-expanded': { + margin: '0', + }, + '& .MuiAccordionSummary-root': { + padding: '8px 24px', + minHeight: '60px', + fontSize: '18px', + fontWeight: 500, + }, + '& .MuiAccordionDetails-root': { + padding: '0 24px 24px', + }, + })); + + const handleChange = () => { + setExpanded(!expanded); + }; + + const handleChange2 = () => { + setExpanded2(!expanded2); + }; + + const handleChange3 = () => { + setExpanded3(!expanded3); + }; + + const handleChange4 = () => { + setExpanded4(!expanded4); + }; + + const handleChange5 = () => { + setExpanded5(!expanded5); + }; + + const handleChange6 = () => { + setExpanded6(!expanded6); + }; + + return ( + ( + + + + Frequently Asked Questions + + + + + ) : ( + + ) + } + aria-controls="panel1-content" + id="panel1-header" + > + What is included with my purchase? + + + Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse malesuada lacus + ex, sit amet blandit leo lobortis eget. + + + + + ) : ( + + ) + } + aria-controls="panel2-content" + id="panel2-header" + > + Are there any recurring fees? + + + Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse malesuada lacus + ex, sit amet blandit leo lobortis eget. + + + + + ) : ( + + ) + } + aria-controls="panel3-content" + id="panel3-header" + > + Can I use the template on multiple projects? + + + Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse malesuada lacus + ex, sit amet blandit leo lobortis eget. + + + + + ) : ( + + ) + } + aria-controls="panel2-content" + id="panel2-header" + > + Can I customize the admin dashboard template to match my brand? + + + Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse malesuada lacus + ex, sit amet blandit leo lobortis eget. + + + + + ) : ( + + ) + } + aria-controls="panel2-content" + id="panel2-header" + > + Are there any restrictions on using the template? + + + Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse malesuada lacus + ex, sit amet blandit leo lobortis eget. + + + + + ) : ( + + ) + } + aria-controls="panel2-content" + id="panel2-header" + > + How can I get support after purchase? + + + Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse malesuada lacus + ex, sit amet blandit leo lobortis eget. + + + + + + + + + Still have a question? + + Ask on discord{' '} + + or + + submit a ticket + + . + + + + ) + ); +}; +export default FAQ; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/features/FeatureTitle.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/features/FeatureTitle.tsx new file mode 100644 index 0000000..c95a737 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/features/FeatureTitle.tsx @@ -0,0 +1,25 @@ +import { Box, Grid2 as Grid, Typography } from '@mui/material'; + +const FeatureTitle = () => { + return ( + ( + + + Introducing Modernize's Light & Dark Skins,{' '} + + Exceptional Dashboards + + , and
+ Dynamic Pages - Stay Updated on What's New! +
+
+
) + ); +}; + +export default FeatureTitle; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/features/Features.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/features/Features.tsx new file mode 100644 index 0000000..e4b1cda --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/features/Features.tsx @@ -0,0 +1,152 @@ +import { Box, Stack, Typography, Grid2 as Grid, Container } from '@mui/material'; +import FeatureTitle from './FeatureTitle'; + +import icon1 from 'src/assets/images/svgs/icon-briefcase.svg'; +import FeatureApp from 'src/assets/images/frontend-pages/homepage/feature-apps.png'; +import LogoIcon from 'src/assets/images/logos/logoIcon.svg'; +import Screen1 from 'src/assets/images/frontend-pages/homepage/screen1.png'; +import IconBubble from 'src/assets/images/svgs/icon-speech-bubble.svg'; +import IconFav from 'src/assets/images/svgs/icon-favorites.svg'; + +const Features = () => { + return ( + ( + + + + + + + + + + icon1 + + + Light & Dark Color Schemes + + + Choose your preferred visual style effortlessly. + + + + + + + + + 12+ Ready to Use Application Designs + + + {' '} + Instantly deployable designs for your applications. + + + + + icon1 + + + + + + + logo + + New Demos + + + Brand new demos to help you build the perfect dashboard:{' '} + + Dark and Right-to-Left. + + + + icon1 + + + + + + + + + + icon1 + + + Code Improvements + + + {' '} + Benefit from continuous improvements and optimizations. + + + + + + + + + icon1 + + + 50+ UI Components + + + {' '} + A rich collection for seamless user experiences. + + + + + + + + ) + ); +}; + +export default Features; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/powerful-dozens/DozensCarousel.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/powerful-dozens/DozensCarousel.tsx new file mode 100644 index 0000000..cffa548 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/powerful-dozens/DozensCarousel.tsx @@ -0,0 +1,157 @@ +import Slider from 'react-slick'; +import 'slick-carousel/slick/slick.css'; +import './carousel.css'; +import { Box } from '@mui/material'; + +import Demo1 from 'src/assets/images/landingpage/demos/demo-main.jpg'; +import Demo2 from 'src/assets/images/landingpage/demos/demo-dark.jpg'; +import Demo3 from 'src/assets/images/landingpage/demos/demo-rtl.jpg'; +import Demo4 from 'src/assets/images/landingpage/demos/demo-horizontal.jpg'; + +import App1 from 'src/assets/images/landingpage/apps/app-chat.jpg'; +import App2 from 'src/assets/images/landingpage/apps/app-email.jpg'; +import { NavLink } from 'react-router'; + +const DozensCarousel = () => { + const settings = { + dots: false, + arrows: false, + infinite: true, + speed: 4500, + autoplay: true, + centerMode: false, + slidesToShow: 4, + slidesToScroll: 4, + responsive: [ + { + breakpoint: 1024, + settings: { + slidesToShow: 2, + slidesToScroll: 2, + }, + }, + { + breakpoint: 480, + settings: { + slidesToShow: 1, + slidesToScroll: 1, + }, + }, + ], + }; + + return ( + +
+ theme.shadows[10], padding: '0 30px 16px' }} + > + + user-img + + +
+
+ theme.shadows[10], padding: '0 30px 16px' }} + > + + user-img + + +
+
+ theme.shadows[10], padding: '0 30px 16px' }} + > + + user-img + + +
+
+ theme.shadows[10], padding: '0 30px 16px' }} + > + + user-img + + +
+
+ theme.shadows[10], padding: '0 30px 16px' }} + > + + user-img + + +
+
+ theme.shadows[10], padding: '0 30px 16px' }} + > + + user-img + + +
+
+ ); +}; + +export default DozensCarousel; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/powerful-dozens/carousel.css b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/powerful-dozens/carousel.css new file mode 100644 index 0000000..97ee7f3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/powerful-dozens/carousel.css @@ -0,0 +1,18 @@ +.dozenscarousel .slick-track { + display: flex; + gap: 70px; +} +.dozenscarousel .slick-list { + max-height: 340px; +} +.dozenscarousel .slick-slide { + margin-bottom: 20px; +} + +.dozenscarousel.slick-slider .slick-list { + margin: 0 0 0 -15px; +} + +.dozenscarousel { + margin-left: 15px; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/powerful-dozens/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/powerful-dozens/index.tsx new file mode 100644 index 0000000..73959fa --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/homepage/powerful-dozens/index.tsx @@ -0,0 +1,105 @@ +import { Box, Grid2 as Grid, Typography, Container } from '@mui/material'; +import DozensCarousel from './DozensCarousel'; + +const features = [ + { + title: 'High Customizability', + subtext: + 'Tailor the dashboard to your exact needs. Customize layouts, color schemes, and widgets effortlessly for a personalized user experience.', + }, + { + title: 'Powerful Data Analytics', + subtext: + 'Unlock the true potential of your data with our advanced analytics tools. Gain valuable insights and make data-driven decisions with ease.', + }, + { + title: 'Interactive Charts', + subtext: + 'Visualize complex data sets beautifully with our interactive graphs and charts. Quickly grasp trends and patterns for smarter analysis.', + }, +]; + +const PowerfulDozens = () => { + return (<> + + + + + + + Discover Powerful Dozens of Purpose-Fit Templates + + + + + + + + {features.map((feature, i) => ( + + + {feature.title} + + + {feature.subtext} + + + ))} + + + + + ); +}; + +export default PowerfulDozens; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/portfolio/Banner.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/portfolio/Banner.tsx new file mode 100644 index 0000000..2d8868a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/portfolio/Banner.tsx @@ -0,0 +1,52 @@ +import { Box, Typography, Container, Grid2 as Grid } from '@mui/material'; + +const Banner = () => { + return (<> + + + + + + Portfolio + + + Explore Our Latest Works + + + + + + ); +}; + +export default Banner; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/pricing/Banner.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/pricing/Banner.tsx new file mode 100644 index 0000000..c773955 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/pricing/Banner.tsx @@ -0,0 +1,52 @@ +import { Box, Typography, Container, Grid2 as Grid } from '@mui/material'; + +const Banner = () => { + return (<> + + + + + + Pricing Page + + + Choose Your Plan + + + + + + ); +}; + +export default Banner; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/c2a/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/c2a/index.tsx new file mode 100644 index 0000000..6dfdd02 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/c2a/index.tsx @@ -0,0 +1,109 @@ +import { Box, Grid2 as Grid, Typography, Container, Stack, Button } from '@mui/material'; +import useMediaQuery from '@mui/material/useMediaQuery'; + +import DesignCol from 'src/assets/images/frontend-pages/homepage/design-collection.png'; + +const C2a = () => { + const lgUp = useMediaQuery((theme: any) => theme.breakpoints.up('lg')); + const smUp = useMediaQuery((theme: any) => theme.breakpoints.only('sm')); + + return (<> + + + + + + + Develop with feature-rich React Dashboard + + + + + + + + One-time purchase - + {' '} + no recurring fees. + + + + + + {lgUp ? ( + design + ) : null} + + {smUp ? ( + design + ) : null} + + + ); +}; + +export default C2a; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/footer/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/footer/index.tsx new file mode 100644 index 0000000..b8bab60 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/footer/index.tsx @@ -0,0 +1,230 @@ +import React from 'react'; +import { Box, Grid2 as Grid, Typography, Container, Divider, Stack, Tooltip } from '@mui/material'; +import { Link, NavLink } from 'react-router'; + +import IconFacebook from 'src/assets/images/frontend-pages/icons/icon-facebook.svg'; +import IconTwitter from 'src/assets/images/frontend-pages/icons/icon-twitter.svg'; +import IconInstagram from 'src/assets/images/frontend-pages/icons/icon-instagram.svg'; + +import LogoIcon from 'src/assets/images/logos/logoIcon.svg'; + +const footerLinks = [ + { + id: 1, + children: [ + { + title: true, + titleText: 'Applications', + }, + { + title: false, + titleText: 'Kanban', + link: 'https://modernize-react.adminmart.com/apps/kanban', + }, + { + title: false, + titleText: 'Invoice List', + link: 'https://modernize-react.adminmart.com/apps/invoice/list', + }, + { + title: false, + titleText: 'eCommerce', + link: 'https://modernize-react.adminmart.com/apps/ecommerce/shop', + }, + { + title: false, + titleText: 'Chat', + link: 'https://modernize-react.adminmart.com/apps/chats', + }, + { + title: false, + titleText: 'Tickets', + link: 'https://modernize-react.adminmart.com/apps/tickets', + }, + { + title: false, + titleText: 'Blog', + link: 'https://modernize-react.adminmart.com/frontend-pages/blog', + }, + ], + }, + { + id: 2, + children: [ + { + title: true, + titleText: 'Forms', + }, + { + title: false, + titleText: 'Form Layout', + link: 'https://modernize-react.adminmart.com/forms/form-layouts', + }, + { + title: false, + titleText: 'Form Horizontal', + link: 'https://modernize-react.adminmart.com/forms/form-horizontal', + }, + { + title: false, + titleText: 'Form Wizard', + link: 'https://modernize-react.adminmart.com/forms/form-wizard', + }, + { + title: false, + titleText: 'Form Validation', + link: 'https://modernize-react.adminmart.com/forms/form-validation', + }, + { + title: false, + titleText: 'Tiptap Editor', + link: 'https://modernize-react.adminmart.com/forms/form-tiptap', + }, + ], + }, + { + id: 3, + children: [ + { + title: true, + titleText: 'Tables', + }, + { + title: false, + titleText: 'Basic Table', + link: 'https://modernize-react.adminmart.com/tables/basic', + }, + { + title: false, + titleText: 'Fixed Header', + link: 'https://modernize-react.adminmart.com/tables/fixed-header', + }, + { + title: false, + titleText: 'Pagination Table', + link: 'https://modernize-react.adminmart.com/tables/pagination', + }, + { + title: false, + titleText: 'React Dense Table', + link: 'https://modernize-react.adminmart.com/react-tables/dense', + }, + { + title: false, + titleText: 'Row Selection Table', + link: 'https://modernize-react.adminmart.com/react-tables/row-selection', + }, + { + title: false, + titleText: 'Drag n Drop Table', + link: 'https://modernize-react.adminmart.com/react-tables/drag-drop', + }, + ], + }, +]; + +const Footer = () => { + return (<> + + + {footerLinks.map((footerlink, i) => ( + + {footerlink.children.map((child, i) => ( + + {child.title ? ( + + {child.titleText} + + ) : ( + + theme.palette.text.primary, + '&:hover': { + color: (theme) => theme.palette.primary.main, + }, + }} + component="span" + > + {child.titleText} + + + )} + + ))} + + ))} + + + Follow us + + + + + + facebook + + + + + twitter + + + + + instagram + + + + + + + + + + + logo + + All rights reserved by Modernize.{' '} + + + + Produced by{' '} + + AdminMart + + . + + + + ); +}; + +export default Footer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/HeaderAlert.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/HeaderAlert.tsx new file mode 100644 index 0000000..585f409 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/HeaderAlert.tsx @@ -0,0 +1,113 @@ +import { useState } from 'react'; +import { Box, Stack, Typography, Chip, IconButton } from '@mui/material'; +import { styled } from '@mui/material/styles'; +import useMediaQuery from '@mui/material/useMediaQuery'; +import { IconX } from '@tabler/icons-react'; +import NotificationRight from 'src/assets/images/frontend-pages/homepage/notification-right.png'; +import NotificationTopRight from 'src/assets/images/frontend-pages/homepage/notification-top-right.png'; +import NotificationLeft from 'src/assets/images/frontend-pages/homepage/notification-left.png'; + +const NotificationBg = styled(Box)(() => ({ + position: 'absolute', + right: '20%', + top: 0, +})); + +const NotificationBg2 = styled(Box)(() => ({ + position: 'absolute', + right: 0, + top: 0, +})); + +const NotificationBg3 = styled(Box)(() => ({ + position: 'absolute', + left: 0, + bottom: '-5px', +})); + +const HeaderAlert = () => { + // State to track if the div should be shown or hidden + const [isAlertVisible, setIsAlertVisible] = useState(true); + + // Function to toggle the visibility + const handleAlert = () => { + setIsAlertVisible(false); // Hides the div when the button is clicked + }; + + // sidebar + const lgUp = useMediaQuery((theme: any) => theme.breakpoints.up('lg')); + + return ( + <> + {isAlertVisible ? ( + + + {lgUp ? ( + + ) : null} + + + Frontend Pages Included + + + + + + <> + {lgUp ? ( + <> + + img + + + img + + + img + + + ) : null} + + + ) : null} + + ); +}; + +export default HeaderAlert; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/HpHeader.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/HpHeader.tsx new file mode 100644 index 0000000..5613008 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/HpHeader.tsx @@ -0,0 +1,92 @@ +import React from 'react'; +import AppBar from '@mui/material/AppBar'; +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import Drawer from '@mui/material/Drawer'; +import IconButton from '@mui/material/IconButton'; +import Stack from '@mui/material/Stack'; +import Toolbar from '@mui/material/Toolbar'; +import useMediaQuery from '@mui/material/useMediaQuery'; +import { styled } from '@mui/material/styles'; +import Logo from '../../../../layouts/full/shared/logo/Logo'; +import Navigations from './Navigations'; +import MobileSidebar from './MobileSidebar'; +import { IconMenu2 } from '@tabler/icons-react'; + +const HpHeader = () => { + const AppBarStyled = styled(AppBar)(({ theme }) => ({ + justifyContent: 'center', + [theme.breakpoints.up('lg')]: { + minHeight: '100px', + }, + backgroundColor: theme.palette.primary.light, + })); + + const ToolbarStyled = styled(Toolbar)(({ theme }) => ({ + width: '100%', + paddingLeft: '0 !important', + paddingRight: '0 !important', + color: theme.palette.text.secondary, + justifyContent: 'space-between', + })); + + // sidebar + const lgUp = useMediaQuery((theme: any) => theme.breakpoints.up('lg')); + const lgDown = useMediaQuery((theme: any) => theme.breakpoints.down('lg')); + + const [open, setOpen] = React.useState(false); + + const handleDrawerOpen = () => { + setOpen(true); + }; + + const toggleDrawer = (newOpen: any) => () => { + setOpen(newOpen); + }; + + return ( + + + + + {lgDown ? ( + + + + ) : null} + {lgUp ? ( + <> + + + + + + ) : null} + + + theme.shadows[8], + }, + }} + > + + + + ); +}; + +export default HpHeader; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/MobileSidebar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/MobileSidebar.tsx new file mode 100644 index 0000000..80887e7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/MobileSidebar.tsx @@ -0,0 +1,59 @@ +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import Stack from '@mui/material/Stack'; +import Logo from '../../../../layouts/full/shared/logo/Logo'; +import { NavLinks } from './Navigations'; +import { Chip } from '@mui/material'; + +const MobileSidebar = () => { + return ( + <> + + + + + + {NavLinks.map((navlink, i) => ( + + ))} + + + + + + + ); +}; + +export default MobileSidebar; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/Navigations.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/Navigations.tsx new file mode 100644 index 0000000..766e541 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/header/Navigations.tsx @@ -0,0 +1,88 @@ +import Button from '@mui/material/Button'; + +import { styled } from '@mui/material/styles'; +import { Chip } from '@mui/material'; + +import { NavLink } from 'react-router'; + +import { useLocation } from 'react-router'; + +export const NavLinks = [ + { + title: 'About Us', + to: '/frontend-pages/about', + }, + { + title: 'Blog', + to: '/frontend-pages/blog', + }, + { + title: 'Portfolio', + new: true, + to: '/frontend-pages/portfolio', + }, + + { + title: 'Dashboard', + to: '/', + }, + { + title: 'Pricing', + to: '/frontend-pages/pricing', + }, + { + title: 'Contact', + to: '/frontend-pages/contact', + }, +]; + +const Navigations = () => { + const StyledButton = styled(Button)(({ theme }) => ({ + fontSize: '15px', + a: { + color: theme.palette.text.secondary, + }, + + fontWeight: 500, + '&.active': { + backgroundColor: 'rgba(93, 135, 255, 0.15)', + a: { + color: theme.palette.primary.main, + }, + }, + })); + + const location = useLocation(); + const pathname = location.pathname; + + return ( + <> + {NavLinks.map((navlink, i) => ( + + + {navlink.title}{' '} + {navlink.new ? ( + + ) : null} + + + ))} + + ); +}; + +export default Navigations; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/Contact.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/Contact.tsx new file mode 100644 index 0000000..78a4229 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/Contact.tsx @@ -0,0 +1,47 @@ +import { Box, Stack, Typography, Link, AvatarGroup, Container, Avatar } from '@mui/material'; + +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; + +const Contact = () => { + return ( + + + + + + + + + Save valuable time and effort spent searching for a solution. + + + + Contact us now + + + + + + ); +}; + +export default Contact; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/LeaderShipCarousel.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/LeaderShipCarousel.tsx new file mode 100644 index 0000000..29f1894 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/LeaderShipCarousel.tsx @@ -0,0 +1,255 @@ +import { Box, Typography } from '@mui/material'; +import Slider from 'react-slick'; +import 'slick-carousel/slick/slick.css'; +import { styled } from '@mui/material/styles'; +import { IconArrowLeft, IconArrowRight } from '@tabler/icons-react'; +import './carousel.css'; +import { useTheme } from '@mui/material/styles'; + +import user1 from 'src/assets/images/frontend-pages/homepage/user1.jpg'; +import user2 from 'src/assets/images/frontend-pages/homepage/user2.jpg'; +import user3 from 'src/assets/images/frontend-pages/homepage/user3.jpg'; +import user4 from 'src/assets/images/frontend-pages/homepage/user4.jpg'; +import user5 from 'src/assets/images/frontend-pages/homepage/user5.jpg'; + +function SampleNextArrow(props: any) { + const { className, onClick } = props; + return ( + theme.palette.grey[100], + width: '48px', + height: '48px', + borderRadius: '50%', + }} + onClick={onClick} + > + + + ); +} + +function SamplePrevArrow(props: any) { + const { className, onClick } = props; + return ( + theme.palette.grey[100], + width: '48px', + height: '48px', + borderRadius: '50%', + }} + onClick={onClick} + > + + + ); +} + +const LeaderShipCarousel = () => { + const theme = useTheme(); + + const slideStyle = { + padding: '0 30px', // Add padding between slides + }; + + const settings = { + dots: false, + infinite: true, + speed: 500, + slidesToShow: 4, + className: 'slider variable-width', + centerMode: false, + slidesToScroll: 4, + nextArrow: , + prevArrow: , + responsive: [ + { + breakpoint: 1024, + settings: { + slidesToShow: 2, + slidesToScroll: 2, + }, + }, + { + breakpoint: 480, + settings: { + slidesToShow: 1, + slidesToScroll: 1, + }, + }, + ], + }; + + const UserBox = styled(Box)(() => ({ + backgroundColor: theme.palette.mode === 'dark' ? theme.palette.background.default : 'white', + maxWidth: 'calc(100% - 51px)', + marginLeft: '15px', + borderRadius: '8px', + marginTop: '-30px !important', + boxShadow: '0px 6px 12px rgba(127, 145, 156, 0.12)', + marginBottom: '10px', + })); + + return ( + +
+ user-img + + + Alex Martinez + + CEO & Co-Founder + +
+
+ user-img + + + Jordan Nguyen + + CTO & Co-Founder + +
+
+ user-img + + + Taylor Roberts + + Product Manager + +
+
+ user-img + + + Morgan Patel + + Lead Developer + +
+
+ user-img + + + Kiana Collins + + Software Developer + +
+
+ user-img + + + Alex Martinez + + CEO & Co-Founder + +
+
+ user-img + + + Jordan Nguyen + + CTO & Co-Founder + +
+
+ user-img + + + Taylor Roberts + + Product Manager + +
+
+ user-img + + + Morgan Patel + + Lead Developer + +
+
+ ); +}; + +export default LeaderShipCarousel; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/carousel.css b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/carousel.css new file mode 100644 index 0000000..5a16212 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/carousel.css @@ -0,0 +1,7 @@ +.leadership-carousel.slick-slider .slick-list { + margin: 0 -15px; +} + +.leadership-carousel { + margin-left: 15px; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/index.tsx new file mode 100644 index 0000000..2a7e616 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/leadership/index.tsx @@ -0,0 +1,51 @@ +import { Box, Grid2 as Grid, Typography, Container } from '@mui/material'; +import 'slick-carousel/slick/slick.css'; + +import LeaderShipCarousel from './LeaderShipCarousel'; +import Contact from './Contact'; + +const Leadership = () => { + return (<> + + + + + + Our leadership + + + Our robust analytics offer rich insights into the information buyers want, informing + where teams + + + + + + + + + ); +}; + +export default Leadership; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/pricing/PaymentMethods.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/pricing/PaymentMethods.tsx new file mode 100644 index 0000000..079cdfc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/pricing/PaymentMethods.tsx @@ -0,0 +1,72 @@ +import { Box, Link, Typography, Tooltip } from '@mui/material'; + +import IconVisa from 'src/assets/images/frontend-pages/payments/icon-visa.svg'; +import IconMasterCard from 'src/assets/images/frontend-pages/payments/icon-mastercard.svg'; +import IconAmericanExpress from 'src/assets/images/frontend-pages/payments/icon-american-express.svg'; +import IconDiscover from 'src/assets/images/frontend-pages/payments/icon-discover.svg'; +import IconPaypal from 'src/assets/images/frontend-pages/payments/icon-paypal.svg'; +import IcoMasetro from 'src/assets/images/frontend-pages/payments/icon-masetro.svg'; +import IconJcb from 'src/assets/images/frontend-pages/payments/icon-jcb.svg'; +import IconDiners from 'src/assets/images/frontend-pages/payments/icon-diners.svg'; + +const PaymentMethods = () => { + return ( + <> + + Secured payment with PayPal & Razorpay + + + + + + payment + + + + + payment + + + + + payment + + + + + payment + + + + + payment + + + + + payment + + + + + payment + + + + + payment + + + + + ); +}; + +export default PaymentMethods; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/pricing/PricingCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/pricing/PricingCard.tsx new file mode 100644 index 0000000..a38b380 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/pricing/PricingCard.tsx @@ -0,0 +1,212 @@ +import { Box, Grid2 as Grid, Typography, Chip, CardContent, Divider, Stack, Button } from '@mui/material'; +import BlankCard from '../../../shared/BlankCard'; + +import IconCheck from 'src/assets/images/frontend-pages/icons/icon-check.svg'; +import IconClose from 'src/assets/images/frontend-pages/icons/icon-close.svg'; + +const Licenses = [ + { + id: 1, + type: 'Single Use', + isPopular: false, + typeText: 'Use for single end product which end users can’t be charged for.', + price: '49', + fullSourceCode: true, + isDoc: true, + isSass: false, + isSingleProject: true, + isSupport: true, + isUpdate: true, + }, + { + id: 2, + type: 'Multiple Use', + isPopular: false, + typeText: 'Use for unlimited end products end users can’t be charged for.', + price: '89', + fullSourceCode: true, + isDoc: true, + isSass: false, + isSingleProject: false, + isSupport: true, + isUpdate: true, + }, + { + id: 3, + type: 'Extended Use', + isPopular: true, + typeText: 'Use for single end product which end users can be charged for.', + price: '299', + fullSourceCode: true, + isDoc: true, + isSass: true, + isSingleProject: true, + isSupport: true, + isUpdate: true, + }, + { + id: 4, + type: 'Unlimited Use', + isPopular: false, + typeText: 'Use in unlimited end products end users can be charged for.', + price: '499', + fullSourceCode: true, + isDoc: true, + isSass: true, + isSingleProject: false, + isSupport: true, + isUpdate: true, + }, +]; + +const PricingCard = () => { + return (<> + + {Licenses.map((license, i) => ( + + + + + + {license.type} + + {license.isPopular ? ( + + ) : null} + + + + {license.typeText} + + + + + ${license.price} + + + / one time pay + + + + + {license.fullSourceCode ? ( + circle + ) : ( + circle + )} + + Full source code + + + + {license.isDoc ? ( + circle + ) : ( + circle + )} + + Documentation + + + + {license.isSass ? ( + circle + ) : ( + circle + )} + + Use in SaaS app + + + + {license.isSingleProject ? ( + circle + ) : ( + circle + )} + + + {' '} + {license.isSingleProject ? 'One' : 'Unlimited'}{' '} + + Project + + + + {license.isSupport ? ( + circle + ) : ( + circle + )} + + + One Year + {' '} + Technical Support + + + + {license.isUpdate ? ( + circle + ) : ( + circle + )} + + + One Year + {' '} + Free Updates + + + + + + + + ))} + + ); +}; + +export default PricingCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/pricing/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/pricing/index.tsx new file mode 100644 index 0000000..cd6ec9f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/pricing/index.tsx @@ -0,0 +1,48 @@ +import { Box, Grid2 as Grid, Typography, Container } from '@mui/material'; +import PricingCard from './PricingCard'; +import PaymentMethods from './PaymentMethods'; + +const Pricing = () => { + return (<> + + + + + + 111,476+ Trusted developers & many tech giants as well + + + + + + + + + + ); +}; + +export default Pricing; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/reviews/ContentArea.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/reviews/ContentArea.tsx new file mode 100644 index 0000000..fa29fc2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/reviews/ContentArea.tsx @@ -0,0 +1,42 @@ +import { Typography } from '@mui/material'; + +import LogoIcon from 'src/assets/images/logos/logoIcon.svg'; + +const ContentArea = () => { + return ( + <> + + What our clients think{' '} + logo{' '} + about us? + + + Our users' feedback is a testament to our commitment to quality and user satisfaction. Read + what they have to say about their journey with us. + + + ); +}; + +export default ContentArea; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/reviews/ReviewCarousel.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/reviews/ReviewCarousel.tsx new file mode 100644 index 0000000..3580f8b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/reviews/ReviewCarousel.tsx @@ -0,0 +1,163 @@ +import { useState, useRef } from 'react'; +import { Avatar, CardContent, Divider, Stack, Typography, Box, Paper } from '@mui/material'; +import Slider from 'react-slick'; +import 'slick-carousel/slick/slick.css'; +import { IconChevronLeft, IconChevronRight } from '@tabler/icons-react'; + +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; +import user4 from 'src/assets/images/profile/user-4.jpg'; +import user5 from 'src/assets/images/profile/user-5.jpg'; + +function SampleNextArrow(props: any) { + const { className, onClick } = props; + return ( + theme.palette.grey[100], + width: '32px', + height: '32px', + borderRadius: '50%', + }} + onClick={onClick} + > + + + ); +} + +function SamplePrevArrow(props: any) { + const { className, onClick } = props; + return ( + theme.palette.grey[100], + width: '32px', + height: '32px', + borderRadius: '50%', + }} + onClick={onClick} + > + + + ); +} + +const Reviews = [ + { + id: 1, + img: user1, + name: 'Jenny Wilson', + text: 'This template is great, UI-rich and up-to-date. Although it is pretty much complete, I suggest to improve a bit of documentation. Thanks & Highly recommended!', + }, + { + id: 2, + img: user2, + name: 'Jenny Wilson', + text: 'This template is great, UI-rich and up-to-date. Although it is pretty much complete, I suggest to improve a bit of documentation. Thanks & Highly recommended!', + }, + { + id: 3, + img: user3, + name: 'Jenny Wilson', + text: 'This template is great, UI-rich and up-to-date. Although it is pretty much complete, I suggest to improve a bit of documentation. Thanks & Highly recommended!', + }, + { + id: 4, + img: user4, + name: 'Jenny Wilson', + text: 'This template is great, UI-rich and up-to-date. Although it is pretty much complete, I suggest to improve a bit of documentation. Thanks & Highly recommended!', + }, + { + id: 5, + img: user5, + name: 'Jenny Wilson', + text: 'This template is great, UI-rich and up-to-date. Although it is pretty much complete, I suggest to improve a bit of documentation. Thanks & Highly recommended!', + }, +]; + +const ReviewCarousel = () => { + const [, setOldSlide] = useState(0); + const [activeSlide, setActiveSlide] = useState(1); + const [, setActiveSlide2] = useState(1); + + let sliderRef = useRef(null); + + const settings = { + dots: false, + fade: true, + infinite: true, + speed: 500, + + slidesToShow: 1, + slidesToScroll: 1, + nextArrow: , + prevArrow: , + beforeChange: (current: any, next: any) => { + setOldSlide(current); + setActiveSlide(next); + }, + afterChange: (current: any) => setActiveSlide2(current), + }; + + return ( + <> + { + sliderRef.current = slider; + }} + {...settings} + > + {Reviews.map((review, i) => ( +
+ + + + Features avaibility + + + + + {review.name} + + + + {review.text} + + + + + {' '} + {activeSlide} / {Reviews.length} + + + +
+ ))} +
+ + ); +}; + +export default ReviewCarousel; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/reviews/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/reviews/index.tsx new file mode 100644 index 0000000..2dc20bf --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/reviews/index.tsx @@ -0,0 +1,48 @@ +import { Box, Grid2 as Grid, Container } from '@mui/material'; +import ContentArea from './ContentArea'; +import ReviewCarousel from './ReviewCarousel'; + +const Reviews = () => { + return (<> + + + + + + + + + + + + + + + + + ); +}; + +export default Reviews; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/scroll-to-top/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/scroll-to-top/index.tsx new file mode 100644 index 0000000..406ef40 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/frontend-pages/shared/scroll-to-top/index.tsx @@ -0,0 +1,53 @@ +import { useEffect, useState } from 'react'; +import { IconArrowUp } from '@tabler/icons-react'; +import { Fab } from '@mui/material'; + +const ScrollToTop = () => { + const [isVisible, setIsVisible] = useState(false); + + // Function to handle scroll to top + const scrollToTop = () => { + window.scrollTo({ + top: 0, + behavior: 'smooth', // Smooth scrolling + }); + }; + + // Function to handle showing/hiding the button on scroll + const toggleVisibility = () => { + if (window.pageYOffset > 300) { + setIsVisible(true); + } else { + setIsVisible(false); + } + }; + + useEffect(() => { + window.addEventListener('scroll', toggleVisibility); + + return () => { + window.removeEventListener('scroll', toggleVisibility); + }; + }, []); + + return ( + <> + {' '} + {isVisible ? ( + + + + ) : null} + + ); +}; + +export default ScrollToTop; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/animation/Animation.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/animation/Animation.tsx new file mode 100644 index 0000000..008435b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/animation/Animation.tsx @@ -0,0 +1,35 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; + +// third party +import { useInView } from 'react-intersection-observer'; +import { motion, useAnimation } from 'framer-motion'; + +function AnimateFadeIn({ children }: { children: React.ReactElement }) { + const controls = useAnimation(); + const [ref, inView] = useInView(); + + useEffect(() => { + if (inView) { + controls.start('visible'); + } + }, [controls, inView]); + + return ( + + {children} + + ); +} + +export default AnimateFadeIn; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/banner/Banner.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/banner/Banner.tsx new file mode 100644 index 0000000..fe10896 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/banner/Banner.tsx @@ -0,0 +1,92 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Box, Container, useMediaQuery, styled, Stack, Theme } from '@mui/material'; +import BannerContent from './BannerContent'; +import bannerbgImg1 from 'src/assets/images/landingpage/bannerimg1.svg'; +import bannerbgImg2 from 'src/assets/images/landingpage/bannerimg2.svg'; + +const Banner = () => { + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + + const SliderBox = styled(Box)(() => ({ + '@keyframes slideup': { + '0%': { + transform: 'translate3d(0, 0, 0)', + }, + '100% ': { + transform: 'translate3d(0px, -100%, 0px)', + }, + }, + + animation: 'slideup 35s linear infinite', + })); + + const SliderBox2 = styled(Box)(() => ({ + '@keyframes slideDown': { + '0%': { + transform: 'translate3d(0, -100%, 0)', + }, + '100% ': { + transform: 'translate3d(0px, 0, 0px)', + }, + }, + + animation: 'slideDown 35s linear infinite', + })); + + return ( + ( + + + + + + {lgUp ? ( + + theme.palette.primary.light, + minWidth: '2000px', + height: 'calc(100vh - 100px)', + maxHeight: '790px', + }} + > + + + + banner + + + banner + + + + + banner + + + banner + + + + + + ) : null} + + + ) + ); +}; + +export default Banner; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/banner/BannerContent.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/banner/BannerContent.tsx new file mode 100644 index 0000000..26d27d0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/banner/BannerContent.tsx @@ -0,0 +1,99 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Typography, Box, Button, Stack, styled, useMediaQuery, Theme } from '@mui/material'; +import { IconRocket } from '@tabler/icons-react'; + + +// third party + +import { motion } from 'framer-motion'; + +const StyledButton = styled(Button)(() => ({ + padding: '13px 48px', + fontSize: '16px', +})); + +const BannerContent = () => { + + const lgDown = useMediaQuery((theme: Theme) => theme.breakpoints.down('lg')); + + return ( + + + + + + {' '} + Kick start your project with + + + + Most powerful &{' '} + + Developer friendly + {' '} + React dashboard + + + + + + Modernize comes with light & dark color skins, well designed dashboards, applications + and pages. + + + + + + + Login + + + + Live Preview + + + + + ); +}; + +export default BannerContent; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/c2a/C2a.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/c2a/C2a.tsx new file mode 100644 index 0000000..93b885e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/c2a/C2a.tsx @@ -0,0 +1,97 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + CardContent, + Grid2 as Grid, + Typography, + Box, + styled, + Button, + Container, + Stack, +} from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; +import AnimationFadeIn from '../animation/Animation'; +import bannerbgImg from 'src/assets/images/landingpage/shape/line-bg.svg'; + +const ImgCard = styled(BlankCard)(() => ({ + backgroundImage: `url(${bannerbgImg})`, + backgroundRepeat: 'no-repeat', + backgroundPosition: 'center center', +})); + +const StyledButton = styled(Button)(() => ({ + padding: '13px 48px', + fontSize: '16px', +})); + +const StyledButton2 = styled(Button)(({ theme }) => ({ + padding: '13px 48px', + fontSize: '16px', + background: theme.palette.background.paper, +})); + +const C2a = () => { + return ( + ( + + + + + + + + + Haven't found an answer to your question? + + + Connect with us either on discord or email us + + + + + Ask on Discord + + + Submit Ticket + + + + + + + + + ) + ); +}; + +export default C2a; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/c2a/C2a2.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/c2a/C2a2.tsx new file mode 100644 index 0000000..4b20403 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/c2a/C2a2.tsx @@ -0,0 +1,89 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Typography, Box, Button, styled, Container, Stack } from '@mui/material'; +import c2aImg from 'src/assets/images/landingpage/background/c2a.png'; +import GuaranteeCard from './GuaranteeCard'; + +const StyledButton = styled(Button)(({ theme }) => ({ + padding: '13px 34px', + fontSize: '16px', + backgroundColor: theme.palette.background.paper, + color: theme.palette.primary.main, + fontWeight: 600, +})); + +const StyledButton2 = styled(Button)(({ theme }) => ({ + padding: '13px 34px', + fontSize: '16px', + borderColor: theme.palette.background.paper, + color: theme.palette.background.paper, + fontWeight: 600, + '&:hover': { + backgroundColor: theme.palette.background.paper, + color: theme.palette.primary.main, + }, +})); + +const C2a2 = () => { + return ( + ( + + + + + + Build your app with our highly customizable React based Dashboard + + + + + Login + + + Register + + + + + + img + + + + + + + + + ) + ); +}; + +export default C2a2; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/c2a/GuaranteeCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/c2a/GuaranteeCard.tsx new file mode 100644 index 0000000..5c4c065 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/c2a/GuaranteeCard.tsx @@ -0,0 +1,66 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Typography, Box, Button, styled, CardContent, Stack } from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; +import badgeImg from 'src/assets/images/landingpage/shape/badge.svg'; +import lineImg from 'src/assets/images/landingpage/shape/line-bg-2.svg'; + +const ImgCard = styled(BlankCard)(() => ({ + backgroundImage: `url(${lineImg})`, + backgroundRepeat: 'no-repeat', + backgroundPosition: 'center center', + marginTop: '-70px', +})); + +const StyledButton = styled(Button)(() => ({ + padding: '13px 34px', + fontSize: '16px', +})); + +const GuaranteeCard = () => { + return ( + + + + + + bagde + + + 100% moneyback guarantee + + We offer 48 hours moneyback guarantee. + + + + + + Contact + + + + + + ); +}; + +export default GuaranteeCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/demo-slider/DemoSlider.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/demo-slider/DemoSlider.tsx new file mode 100644 index 0000000..7bf65e0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/demo-slider/DemoSlider.tsx @@ -0,0 +1,377 @@ +import { + Box, + Container, + Button, + styled, + Typography, + Grid2 as Grid, + Avatar, + Chip, + useTheme, +} from '@mui/material'; + +// images +import mainDemo from 'src/assets/images/landingpage/demos/demo-main.jpg'; +import darkDemo from 'src/assets/images/landingpage/demos/demo-dark.jpg'; +import horizontalDemo from 'src/assets/images/landingpage/demos/demo-horizontal.jpg'; +import minisidebarDemo from 'src/assets/images/landingpage/demos/demo-firebase.jpg'; +import rtlDemo from 'src/assets/images/landingpage/demos/demo-rtl.jpg'; + +import app1 from 'src/assets/images/landingpage/apps/app-calendar.jpg'; +import app2 from 'src/assets/images/landingpage/apps/app-chat.jpg'; +import app3 from 'src/assets/images/landingpage/apps/app-contact.jpg'; +import app4 from 'src/assets/images/landingpage/apps/app-email.jpg'; +import app5 from 'src/assets/images/landingpage/apps/app-note.jpg'; +import app6 from 'src/assets/images/landingpage/apps/app-user-profile.jpg'; +import app7 from 'src/assets/images/landingpage/apps/app-blog.jpg'; +import app8 from 'src/assets/images/landingpage/apps/app-ticket.jpg'; +import app9 from 'src/assets/images/landingpage/apps/app-ecommerce-shop.jpg'; +import app10 from 'src/assets/images/landingpage/apps/app-ecommerce-detail.jpg'; +import app11 from 'src/assets/images/landingpage/apps/app-ecommerce-checkout.jpg'; +import app12 from 'src/assets/images/landingpage/apps/app-ecommerce-list.jpg'; +import app13 from 'src/assets/images/landingpage/apps/app-blog-detail.jpg'; +import app14 from 'src/assets/images/landingpage/apps/app-kanban.jpg'; +import app15 from 'src/assets/images/landingpage/apps/app-invoice.jpg'; + +import Page1 from 'src/assets/images/landingpage/f-pages/page-homepage.jpg'; +import Page2 from 'src/assets/images/landingpage/f-pages/page-about.jpg'; +import Page3 from 'src/assets/images/landingpage/f-pages/page-portfolio.jpg'; +import Page4 from 'src/assets/images/landingpage/f-pages/page-pricing.jpg'; + +import DemoTitle from './DemoTitle'; + +interface DemoTypes { + link: string; + img: string; + title: string; + hot?: boolean; +} + +const demos: DemoTypes[] = [ + { + link: 'https://modernize-react-main.netlify.app/dashboards/modern', + img: mainDemo, + title: 'Main', + }, + { + link: 'https://modernize-react-dark.netlify.app/dashboards/ecommerce', + img: darkDemo, + title: 'Dark', + }, + { + link: 'https://modernize-react-horizontal.netlify.app/dashboards/modern', + img: horizontalDemo, + title: 'Horizontal', + }, + { + link: 'https://modernize-react-firebase.netlify.app/auth/login', + img: minisidebarDemo, + title: 'Firebase', + }, + { + link: 'https://modernize-react-rtl.netlify.app/dashboards/modern', + img: rtlDemo, + title: 'RTL', + }, +]; + +const pages: DemoTypes[] = [ + { + link: 'https://modernize-react.adminmart.com/frontend-pages/homepage', + img: Page1, + title: 'Homepage', + }, + { + link: 'https://modernize-react.adminmart.com/frontend-pages/about', + img: Page2, + title: 'About us', + }, + { + link: 'https://modernize-react.adminmart.com/frontend-pages/portfolio', + img: Page3, + title: 'Portfolio', + }, + { + link: 'https://modernize-react.adminmart.com/frontend-pages/pricing', + img: Page4, + title: 'Pricing', + }, +]; + +const apps: DemoTypes[] = [ + { + link: 'https://modernize-nextjs.adminmart.com/apps/kanban', + img: app14, + hot: true, + title: 'Kanban App', + }, + { + link: 'https://modernize-nextjs.adminmart.com/apps/invoice/list', + img: app15, + hot: true, + title: 'Invoice App', + }, + { + link: '/apps/calendar', + img: app1, + title: 'Calendar App', + }, + { + link: '/apps/chats', + img: app2, + title: 'Chat App', + }, + { + link: 'apps/contacts', + img: app3, + title: 'Contact App', + }, + { + link: 'apps/email', + img: app4, + title: 'Email App', + }, + { + link: '/apps/notes', + img: app5, + title: 'Note App', + }, + { + link: '/apps/user-profile', + img: app6, + title: 'User Profile App', + }, + { + link: '/apps/blog/posts', + img: app7, + title: 'Blog App', + }, + { + link: '/apps/blog/detail/streaming-video-way-before-it-was-cool-go-dark-tomorrow', + img: app13, + title: 'Blog Detail App', + }, + { + link: '/apps/tickets', + img: app8, + title: 'Ticket App', + }, + { + link: '/apps/ecommerce/shop', + img: app9, + title: 'eCommerce Shop App', + }, + { + link: '/apps/ecommerce/detail/1', + img: app10, + title: 'eCommerce Detail App', + }, + { + link: '/apps/ecommerce/eco-checkout', + img: app11, + title: 'eCommerce Checkout App', + }, + { + link: '/apps/ecommerce/eco-product-list', + img: app12, + title: 'eCommerce List App', + }, +]; + +const DemoSlider = () => { + const theme = useTheme(); + + const StyledBox = styled(Box)(() => ({ + overflow: 'auto', + position: 'relative', + border: `1px solid ${theme.palette.divider}`, + '.MuiButton-root': { + display: 'none', + }, + '&:hover': { + '.MuiButton-root': { + display: 'block', + transform: 'translate(-50%,-50%)', + position: 'absolute', + left: '50%', + right: '50%', + top: '50%', + minWidth: '100px', + zIndex: '9', + }, + '&:before': { + content: '""', + position: 'absolute', + top: '0', + left: ' 0', + width: '100%', + height: '100%', + zIndex: '8', + backgroundColor: 'rgba(55,114,255,.2)', + }, + }, + })); + + return ( + ( + + {/* Title */} + + + {/* slider */} + + + {demos.map((demo, index) => ( + + + {/* */} + + + + + {/* */} + + {demo.title} + + + + ))} + + + + + + {/* apps */} + + + {pages.map((page, index) => ( + + + + + + + + {page.title}{' '} + {page.hot ? : null} + + + + ))} + + + + + + + + {apps.map((demo, index) => ( + + + {/* */} + + + + + {/* */} + + {demo.title} {demo.hot ? : null} + + + + ))} + + + + ) + ); +}; + +export default DemoSlider; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/demo-slider/DemoTitle.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/demo-slider/DemoTitle.tsx new file mode 100644 index 0000000..ec25a55 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/demo-slider/DemoTitle.tsx @@ -0,0 +1,64 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Typography, AvatarGroup, Avatar, Stack } from '@mui/material'; +import AnimationFadeIn from '../animation/Animation'; + +// images +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; + +const DemoTitle = () => { + return ( + ( + + + <> + + + + + + + 52,589+ + + developers & agencies using our templates + + + + Production Ready & Developer Friendly Material UI React Admin Template + + + + + ) + ); +}; + +export default DemoTitle; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/features/Features.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/features/Features.tsx new file mode 100644 index 0000000..7f0cb01 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/features/Features.tsx @@ -0,0 +1,161 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import FeaturesTitle from './FeaturesTitle'; +import { Typography, Grid2 as Grid, Container, Box } from '@mui/material'; +import { + IconAdjustments, + IconArchive, + IconArrowsShuffle, + IconBook, + IconBuildingCarousel, + IconCalendar, + IconChartPie, + IconDatabase, + IconDiamond, + IconLanguageKatakana, + IconLayersIntersect, + IconMessages, + IconRefresh, + IconShieldLock, + IconTag, + IconWand, + IconTable, + IconPresentation, +} from '@tabler/icons-react'; +import AnimationFadeIn from '../animation/Animation'; + +interface FeaturesType { + icon: React.ReactElement; + title: string; + subtext: string; +} + +const featuresData: FeaturesType[] = [ + { + icon: , + title: '6 Theme Colors', + subtext: 'We have included 6 pre-defined Theme Colors with Elegant Admin.', + }, + { + icon: , + title: 'JWT + Firebase Auth', + subtext: 'It is JSON Object is used to securely transfer information over the web.', + }, + { + icon: , + title: '65+ Page Templates', + subtext: 'Yes, we have 5 demos & 65+ Pages per demo to make it easier.', + }, + { + icon: , + title: '45+ UI Components', + subtext: 'Almost 45+ UI Components being given with Modernize Admin Pack.', + }, + { + icon: , + title: '4+ Frontend Pages', + subtext: 'We have added useful frontend pages with Modernize Admin', + }, + { + icon: , + title: 'Material Ui', + subtext: 'Its been made with Material Ui and full responsive layout.', + }, + { + icon: , + title: 'React Table', + subtext: 'Supercharge your tables or build a datagrid from scratch for TS/JS React.', + }, + { + icon: , + title: '3400+ Font Icons', + subtext: 'Lots of Icon Fonts are included here in the package of Elegant Admin.', + }, + { + icon: , + title: 'Axios', + subtext: 'Axios is a promise-based HTTP Client for node.js and the browser.', + }, + { + icon: , + title: 'i18 React', + subtext: 'react-i18 is a powerful internationalization framework for React.', + }, + { + icon: , + title: 'Slick Carousel', + subtext: 'The Last React Carousel You will Ever Need!', + }, + { + icon: , + title: 'Easy to Customize', + subtext: 'Customization will be easy as we understand your pain.', + }, + { + icon: , + title: 'Lots of Chart Options', + subtext: 'You name it and we have it, Yes lots of variations for Charts.', + }, + { + icon: , + title: 'Lots of Table Examples', + subtext: 'Data Tables are initial requirement and we added them.', + }, + { + icon: , + title: 'Regular Updates', + subtext: 'We are constantly updating our pack with new features.', + }, + { + icon: , + title: 'Detailed Documentation', + subtext: 'We have made detailed documentation, so it will easy to use.', + }, + { + icon: , + title: 'Calendar Design', + subtext: 'Calendar is available with our package & in nice design.', + }, + { + icon: , + title: 'Dedicated Support', + subtext: 'We believe in supreme support is key and we offer that.', + }, +]; + +const Features = () => { + return ( + ( + + + + + + {featuresData.map((feature, index) => ( + + {feature.icon} + + {feature.title} + + + {feature.subtext} + + + ))} + + + + + ) + ); +}; + +export default Features; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/features/FeaturesTitle.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/features/FeaturesTitle.tsx new file mode 100644 index 0000000..aa21c05 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/features/FeaturesTitle.tsx @@ -0,0 +1,33 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Typography } from '@mui/material'; + + +const FeaturesTitle = () => { + + return ( + ( + + ALMOST COVERED EVERYTHING + Other Amazing Features & Flexibility Provided + + ) + ); +}; + +export default FeaturesTitle; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/footer/Footer.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/footer/Footer.tsx new file mode 100644 index 0000000..d93d755 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/footer/Footer.tsx @@ -0,0 +1,35 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Link, Typography, Container } from '@mui/material'; +import logoIcon from 'src/assets/images/logos/logoIcon.svg'; + +const Footer = () => { + return ( + ( + + + icon + + All rights reserved by Modernize. Designed & Developed by + + + {' '} + AdminMart + {' '} + + . + + + + ) + ); +}; + +export default Footer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/frameworks/Frameworks.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/frameworks/Frameworks.tsx new file mode 100644 index 0000000..59079e4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/frameworks/Frameworks.tsx @@ -0,0 +1,53 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, Container, styled, Stack } from '@mui/material'; +import FrameworksTitle from './FrameworksTitle'; + +// images +import sliderImg from 'src/assets/images/landingpage/background/slider-group.png'; + +const SliderBox = styled(Box)(() => ({ + '@keyframes slide': { + '0%': { + transform: 'translate3d(0, 0, 0)', + }, + '100% ': { + transform: 'translate3d(-100%, 0, 0)', + }, + }, + animation: 'slide 45s linear infinite', +})); + +const Frameworks = () => { + return ( + + + {/* Title */} + + + + + + slide + + + + + slide + + + + + ); +}; + +export default Frameworks; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/frameworks/FrameworksTitle.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/frameworks/FrameworksTitle.tsx new file mode 100644 index 0000000..21b59c2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/frameworks/FrameworksTitle.tsx @@ -0,0 +1,33 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Typography } from '@mui/material'; + + +const FrameworksTitle = () => { + + return ( + ( + + Increase speed of your development and + launch quickly with Modernize + + ) + ); +}; + +export default FrameworksTitle; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/DemosDD.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/DemosDD.tsx new file mode 100644 index 0000000..80073cb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/DemosDD.tsx @@ -0,0 +1,197 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, Typography, Avatar, Stack, styled, Button } from '@mui/material'; +import { NavLink } from 'react-router'; + +import mainDemo from 'src/assets/images/landingpage/demos/demo-main.jpg'; +import darkDemo from 'src/assets/images/landingpage/demos/demo-dark.jpg'; +import horizontalDemo from 'src/assets/images/landingpage/demos/demo-horizontal.jpg'; +import minisidebarDemo from 'src/assets/images/landingpage/demos/demo-firebase.jpg'; +import rtlDemo from 'src/assets/images/landingpage/demos/demo-rtl.jpg'; +import app1 from 'src/assets/images/landingpage/apps/app-calendar.jpg'; +import app2 from 'src/assets/images/landingpage/apps/app-chat.jpg'; +import app3 from 'src/assets/images/landingpage/apps/app-contact.jpg'; +import app4 from 'src/assets/images/landingpage/apps/app-email.jpg'; +import app5 from 'src/assets/images/landingpage/apps/app-note.jpg'; + +interface DemoTypes { + link: string; + img: string; + title: string; +} + +const demos: DemoTypes[] = [ + { + link: 'https://modernize-react-main.netlify.app/dashboards/modern', + img: mainDemo, + title: 'Main', + }, + { + link: 'https://modernize-react-dark.netlify.app/dashboards/ecommerce', + img: darkDemo, + title: 'Dark', + }, + { + link: 'https://modernize-react-horizontal.netlify.app/dashboards/modern', + img: horizontalDemo, + title: 'Horizontal', + }, + { + link: 'https://modernize-react-firebase.netlify.app/auth/login', + img: minisidebarDemo, + title: 'Firebase', + }, + { + link: 'https://modernize-react-rtl.netlify.app/dashboards/modern', + img: rtlDemo, + title: 'RTL', + }, +]; + +const apps: DemoTypes[] = [ + { + link: '/apps/calendar', + img: app1, + title: 'Calendar', + }, + { + link: '/apps/chats', + img: app2, + title: 'Chat', + }, + { + link: 'apps/contacts', + img: app3, + title: 'Contact', + }, + { + link: 'apps/email', + img: app4, + title: 'Email', + }, + { + link: '/apps/notes', + img: app5, + title: 'Note', + }, +]; + +const StyledBox = styled(Box)(() => ({ + overflow: 'auto', + position: 'relative', + '.MuiButton-root': { + display: 'none', + }, + '&:hover': { + '.MuiButton-root': { + display: 'block', + transform: 'translate(-50%,-50%)', + position: 'absolute', + left: '50%', + right: '50%', + top: '50%', + minWidth: '100px', + zIndex: '9', + }, + '&:before': { + content: '""', + position: 'absolute', + top: '0', + left: ' 0', + width: '100%', + height: '100%', + zIndex: '8', + backgroundColor: 'rgba(55,114,255,.2)', + }, + }, +})); + +const DemosDD = () => { + return ( + <> + + Different Demos + + Included with the package + + + + {demos.map((demo, index) => ( + + {/* */} + + + + + {/* */} + + {demo.title} + + + ))} + + + + Different Apps + + + + {apps.map((app, index) => ( + + {/* */} + + + + + + {/* */} + + + {app.title} + + + ))} + + + + ); +}; + +export default DemosDD; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/Header.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/Header.tsx new file mode 100644 index 0000000..e7aaa35 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/Header.tsx @@ -0,0 +1,107 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + AppBar, + styled, + Toolbar, + Container, + Box, + Stack, + useMediaQuery, + IconButton, + Drawer, + Theme, +} from '@mui/material'; +import Logo from 'src/layouts/full/shared/logo/Logo'; +import Navigations from './Navigations'; +import MobileSidebar from './MobileSidebar'; +import { IconMenu2 } from '@tabler/icons-react'; + +const LpHeader = () => { + const AppBarStyled = styled(AppBar)(({ theme }) => ({ + justifyContent: 'center', + [theme.breakpoints.up('lg')]: { + minHeight: '80px', + }, + backgroundColor: theme.palette.background.default, + })); + + const ToolbarStyled = styled(Toolbar)(({ theme }) => ({ + width: '100%', + paddingLeft: '0 !important', + paddingRight: '0 !important', + color: theme.palette.text.secondary, + })); + + // sidebar + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + const lgDown = useMediaQuery((theme: Theme) => theme.breakpoints.down('lg')); + + const [open, setOpen] = React.useState(false); + + const handleDrawerOpen = () => { + setOpen(true); + }; + + const toggleDrawer = (newOpen: boolean) => () => { + setOpen(newOpen); + }; + + const [y, setY] = React.useState(window.scrollY); + + const handleNavigation = React.useCallback( + (e: Event | any) => { + const window = e.currentTarget; + setY(window.scrollY); + }, + [], + ); + + React.useEffect(() => { + setY(window.scrollY); + window.addEventListener('scroll', handleNavigation); + + return () => { + window.removeEventListener('scroll', handleNavigation); + }; + }, [handleNavigation]); + + return ( + + + + + + {lgDown ? ( + + + + ) : null} + {lgUp ? ( + + + + ) : null} + + + theme.shadows[8], + }, + }} + > + + + + ); +}; + +export default LpHeader; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/MobileSidebar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/MobileSidebar.tsx new file mode 100644 index 0000000..0b304e4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/MobileSidebar.tsx @@ -0,0 +1,71 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { Button, Box, Collapse, Stack } from '@mui/material'; +import { IconChevronDown } from '@tabler/icons-react'; +import Logo from "src/layouts/full/shared/logo/Logo" +import DemosDD from './DemosDD'; +import AppLinks from 'src/layouts/full/vertical/header/AppLinks'; +import QuickLinks from 'src/layouts/full/vertical/header/QuickLinks'; + +const MobileSidebar = () => { + const [toggle, setToggle] = useState(false) + const [toggle2, setToggle2] = useState(false) + + return ( + <> + + + + + + + + {toggle && ( + + + + + + + + )} + + + {toggle2 && ( + + + + + + + )} + + + + + + + + + ); +}; + +export default MobileSidebar; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/Navigations.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/Navigations.tsx new file mode 100644 index 0000000..3699093 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/header/Navigations.tsx @@ -0,0 +1,131 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { Box, Button, Divider, Grid2 as Grid, styled, Paper } from '@mui/material'; +import { IconChevronDown } from '@tabler/icons-react'; +import AppLinks from 'src/layouts/full/vertical/header/AppLinks'; +import QuickLinks from 'src/layouts/full/vertical/header/QuickLinks'; +import DemosDD from './DemosDD'; + +const Navigations = () => { + + const StyledButton = styled(Button)(({ theme }) => ({ + fontSize: '16px', + color: theme.palette.text.secondary + })); + + // demos + const [open, setOpen] = useState(false); + + const handleOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + + // pages + + const [open2, setOpen2] = useState(false); + + const handleOpen2 = () => { + setOpen2(true); + }; + + const handleClose2 = () => { + setOpen2(false); + }; + + + + return (<> + theme.palette.text.secondary, + }} + onMouseEnter={handleOpen} onMouseLeave={handleClose} + endIcon={} + > + Demos + + {open && ( + + + + )} + + theme.palette.text.secondary, + }} + endIcon={} + > + Pages + + {open2 && ( + + + + + + + + + + + + + + + + )} + + + Documentation + + + Support + + + ); +}; + +export default Navigations; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/testimonial/Testimonial.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/testimonial/Testimonial.tsx new file mode 100644 index 0000000..dbf8dcf --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/testimonial/Testimonial.tsx @@ -0,0 +1,156 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Avatar, Box, CardContent, Container, Typography, Rating, Stack } from '@mui/material'; +import TestimonialTitle from './TestimonialTitle'; +import BlankCard from '../../shared/BlankCard'; +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import AnimationFadeIn from '../animation/Animation'; + +//Carousel slider for product +import Slider from 'react-slick'; +import 'slick-carousel/slick/slick.css'; +import 'slick-carousel/slick/slick-theme.css'; +import './testimonial.css'; + +interface SliderType { + title: string; + subtitle: string; + avatar: string; + subtext: string; +} + +const SliderData: SliderType[] = [ + { + title: 'Jenny Wilson', + subtitle: 'Features avaibility', + avatar: img1, + subtext: + 'The dashboard template from adminmart has helped me provide a clean and sleek look to my dashboard and made it look exactly the way I wanted it to, mainly without having.', + }, + { + title: 'Minshan Cui', + subtitle: 'Features avaibility', + avatar: img2, + subtext: + 'The quality of design is excellent, customizability and flexibility much better than the other products available in the market.I strongly recommend the AdminMart to other.', + }, + { + title: 'Eminson Mendoza', + subtitle: 'Features avaibility', + avatar: img3, + subtext: + 'This template is great, UI-rich and up-to-date. Although it is pretty much complete, I suggest to improve a bit of documentation. Thanks & Highly recomended!', + }, + { + title: 'Jenny Wilson', + subtitle: 'Features avaibility', + avatar: img1, + subtext: + 'The dashboard template from adminmart has helped me provide a clean and sleek look to my dashboard and made it look exactly the way I wanted it to, mainly without having.', + }, + { + title: 'Minshan Cui', + subtitle: 'Features avaibility', + avatar: img2, + subtext: + 'The quality of design is excellent, customizability and flexibility much better than the other products available in the market.I strongly recommend the AdminMart to other.', + }, + { + title: 'Eminson Mendoza', + subtitle: 'Features avaibility', + avatar: img3, + subtext: + 'This template is great, UI-rich and up-to-date. Although it is pretty much complete, I suggest to improve a bit of documentation. Thanks & Highly recomended!', + }, +]; + +const Testimonial = () => { + const [value, setValue] = React.useState(5); + + const settings = { + className: 'testimonial-slider', + dots: true, + arrows: false, + infinite: true, + speed: 500, + slidesToShow: 3, + slidesToScroll: 1, + responsive: [ + { + breakpoint: 1024, + settings: { + slidesToShow: 3, + }, + }, + { + breakpoint: 768, + settings: { + slidesToShow: 2, + }, + }, + { + breakpoint: 600, + settings: { + slidesToShow: 2, + }, + }, + { + breakpoint: 480, + settings: { + slidesToShow: 1, + }, + }, + ], + }; + + return ( + + + + + + + {SliderData.map((slider, index) => ( + + + + + + + {slider.title} + + {slider.subtitle} + + + + { + setValue(newValue); + }} + /> + + + + {slider.subtext} + + + + + ))} + + + + + + ); +}; + +export default Testimonial; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/testimonial/TestimonialTitle.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/testimonial/TestimonialTitle.tsx new file mode 100644 index 0000000..feaddf5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/testimonial/TestimonialTitle.tsx @@ -0,0 +1,40 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Typography } from '@mui/material'; +import AnimationFadeIn from '../animation/Animation'; + +const TestimonialTitle = () => { + return ( + ( + + + + Don’t just take our words for it, See what developers like you are saying + + + + ) + ); +}; + +export default TestimonialTitle; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/testimonial/testimonial.css b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/testimonial/testimonial.css new file mode 100644 index 0000000..0f916e9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/landingpage/testimonial/testimonial.css @@ -0,0 +1,17 @@ +/* .testimonial-slider .slick-slide { + margin: 0 18px; +} */ + +.slick-dots li button:before { + font-size: 10px; +} +.testimonial-slider .slick-list{ + padding:0 0 20px 0; +} +.slick-dots li { + margin: 0; +} + +.slick-dots { + bottom: -50px +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/accordion/code/BasicCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/accordion/code/BasicCode.tsx new file mode 100644 index 0000000..1cd685d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/accordion/code/BasicCode.tsx @@ -0,0 +1,66 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const BasicCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { + Accordion, + AccordionSummary, + Typography, + AccordionDetails, + Divider, +} from "@mui/material"; +import { IconChevronDown } from "@tabler/icons-react"; + + + } + aria-controls="panel1a-content" + id="panel1a-header" + > + Accordion 1 + + + + Lorem ipsum dolor sit amet, consectetur adipiscing elit. + Suspendisse malesuada lacus ex, sit amet blandit leo + lobortis eget. + + + + + + } + aria-controls="panel2a-content" + id="panel2a-header" + > + Accordion 2 + + + + Lorem ipsum dolor sit amet, consectetur adipiscing elit. + Suspendisse malesuada lacus ex, sit amet blandit leo + lobortis eget. + + + + + + } + aria-controls="panel3a-content" + id="panel3a-header" + > + Disabled Accordion + + `} + + + ); +}; + +export default BasicCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/accordion/code/ControlledCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/accordion/code/ControlledCode.tsx new file mode 100644 index 0000000..ee2ffe3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/accordion/code/ControlledCode.tsx @@ -0,0 +1,115 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ControlledCode = () => { + return ( + <> + + {` + +import * as React from 'react'; +import { + Accordion, + AccordionSummary, + Typography, + AccordionDetails, + Divider, +} from "@mui/material"; +import { IconChevronDown } from "@tabler/icons-react"; + + + } + aria-controls="panel1bh-content" + id="panel1bh-header" + > + + General settings + + + I am an accordion + + + + + Nulla facilisi. Phasellus sollicitudin nulla et quam mattis + feugiat. Aliquam eget maximus est, id dignissim quam. + + + + + } + aria-controls="panel2bh-content" + id="panel2bh-header" + > + + Users + + + You are currently not an owner + + + + + Donec placerat, lectus sed mattis semper, neque lectus + feugiat lectus, varius pulvinar diam eros in elit. + Pellentesque convallis laoreet laoreet. + + + + + } + aria-controls="panel3bh-content" + id="panel3bh-header" + > + + Advanced settings + + + Filtering has been entirely disabled for whole web server + + + + + Nunc vitae orci ultricies, auctor nunc in, volutpat nisl. + Integer sit amet egestas eros, vitae egestas augue. Duis vel + est augue. + + + + + } + aria-controls="panel4bh-content" + id="panel4bh-header" + > + + Personal data + + + + + Nunc vitae orci ultricies, auctor nunc in, volutpat nisl. + Integer sit amet egestas eros, vitae egestas augue. Duis vel + est augue. + + + `} + + + ); +}; + +export default ControlledCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/ActionCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/ActionCode.tsx new file mode 100644 index 0000000..5e19ad8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/ActionCode.tsx @@ -0,0 +1,36 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ActionCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { + Stack, + Button, + Alert, +} from "@mui/material"; + + + + This is a success alert — check it out! + + + UNDO + + } + > + This is a success alert — check it out! + +`} + + + ); +}; + +export default ActionCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/DescriptionCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/DescriptionCode.tsx new file mode 100644 index 0000000..97acb8c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/DescriptionCode.tsx @@ -0,0 +1,38 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const DescriptionCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { + Stack, + Alert, + AlertTitle, +} from "@mui/material"; + + + + Error + This is an error alert — check it out! + + + Warning + This is a warning alert — check it out! + + + Info + This is an info alert — check it out! + + + Success + This is a success alert — check it out! + +`} + + + ); +}; + +export default DescriptionCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/FilledCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/FilledCode.tsx new file mode 100644 index 0000000..1bf0f2a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/FilledCode.tsx @@ -0,0 +1,33 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const FilledCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { + Stack, + Alert, +} from "@mui/material"; + + + + This is an error alert — check it out! + + + This is a warning alert — check it out! + + + This is an info alert — check it out! + + + This is a success alert — check it out! + +`} + + + ); +}; + +export default FilledCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/OutlinedCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/OutlinedCode.tsx new file mode 100644 index 0000000..4b4f68c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/OutlinedCode.tsx @@ -0,0 +1,33 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const OutlinedCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { + Stack, + Alert, +} from "@mui/material"; + + + + This is an error alert — check it out! + + + This is a warning alert — check it out! + + + This is an info alert — check it out! + + + This is a success alert — check it out! + +`} + + + ); +}; + +export default OutlinedCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/TransitionCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/TransitionCode.tsx new file mode 100644 index 0000000..7e4bb9a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/alert/code/TransitionCode.tsx @@ -0,0 +1,54 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const TransitionCode = () => { + return ( + <> + + {` + +import * as React from 'react'; +import { + Stack, + Button, + IconButton, + Collapse, + Alert, +} from "@mui/material"; + + + + { + setOpen(false); + }} + > + + + } + > + Close me! + + + +`} + + + ); +}; + +export default TransitionCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/GroupedCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/GroupedCode.tsx new file mode 100644 index 0000000..9946c99 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/GroupedCode.tsx @@ -0,0 +1,25 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const GroupedCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { Avatar, AvatarGroup, Stack } from '@mui/material'; +import { IconMoodSmile } from '@tabler/icons-react'; + + + + + + + + +`} + + + ); +}; + +export default GroupedCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/GroupedSizeCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/GroupedSizeCode.tsx new file mode 100644 index 0000000..1093d9a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/GroupedSizeCode.tsx @@ -0,0 +1,25 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const GroupedSizeCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { Avatar, AvatarGroup, Stack} from '@mui/material'; +import { IconMoodSmile } from '@tabler/icons-react'; + + + + + + + + +`} + + + ); +}; + +export default GroupedSizeCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/IconAvatarsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/IconAvatarsCode.tsx new file mode 100644 index 0000000..1e8376e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/IconAvatarsCode.tsx @@ -0,0 +1,34 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const IconAvatarsCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { Avatar, Stack } from '@mui/material'; +import { IconMoodSmile } from '@tabler/icons-react'; + + + + + + + + + + + + + + + + + +`} + + + ); +}; + +export default IconAvatarsCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/ImageAvatarsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/ImageAvatarsCode.tsx new file mode 100644 index 0000000..85d3d79 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/ImageAvatarsCode.tsx @@ -0,0 +1,21 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ImageAvatarsCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { Avatar, Stack } from '@mui/material'; + + + + + + `} + + + ); +}; + +export default ImageAvatarsCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/LetterAvatarsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/LetterAvatarsCode.tsx new file mode 100644 index 0000000..6c675a0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/LetterAvatarsCode.tsx @@ -0,0 +1,24 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const LetterAvatarsCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { Avatar, Stack } from '@mui/material'; + + + A + B + C + D + E + +`} + + + ); +}; + +export default LetterAvatarsCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/SizesCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/SizesCode.tsx new file mode 100644 index 0000000..8990e38 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/SizesCode.tsx @@ -0,0 +1,26 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const SizesCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { Avatar, Stack } from '@mui/material'; +import { IconMoodSmile } from '@tabler/icons-react'; + + + + + + + + + +`} + + + ); +}; + +export default SizesCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/VariantCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/VariantCode.tsx new file mode 100644 index 0000000..fe43785 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/VariantCode.tsx @@ -0,0 +1,28 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const VariantCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { Avatar, Stack } from '@mui/material'; +import { IconMoodSmile } from '@tabler/icons-react'; + + + + + + + + + + + +`} + + + ); +}; + +export default VariantCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/WithBadgeCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/WithBadgeCode.tsx new file mode 100644 index 0000000..ed11f4c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/avatar/code/WithBadgeCode.tsx @@ -0,0 +1,55 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const WithBadgeCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { Avatar, AvatarGroup, Stack } from '@mui/material'; +import { IconMoodSmile } from '@tabler/icons-react'; + + + + + + } + > + + + + + + + + + + + + +`} + + + ); +}; + +export default WithBadgeCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/CustomIconCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/CustomIconCode.tsx new file mode 100644 index 0000000..2e2400c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/CustomIconCode.tsx @@ -0,0 +1,35 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const CustomIconCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { +Avatar, +Chip, + } from '@mui/material'; +import { +IconCheck, +IconChecks } from '@tabler/icons-react'; +import InlineItemCard from "@/app/components/shared/InlineItemCard"; + + + M} + onDelete={handleDelete} + deleteIcon={} + /> + S} + onDelete={handleDelete} + deleteIcon={} + /> +`} + + + ); +}; + +export default CustomIconCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/CustomOutlinedIcon.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/CustomOutlinedIcon.tsx new file mode 100644 index 0000000..2c0fcbb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/CustomOutlinedIcon.tsx @@ -0,0 +1,32 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const CustomOutlinedIcon = () => { + return ( + <> + + {` + +import React from 'react'; +import { +Avatar, +Chip, + } from '@mui/material'; +import InlineItemCard from "@/app/components/shared/InlineItemCard"; + + + M} + onDelete={handleDelete} + deleteIcon={} + /> + S} + onDelete={handleDelete} + deleteIcon={} + /> +`} + + + ); +}; + +export default CustomOutlinedIcon; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/DisabledCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/DisabledCode.tsx new file mode 100644 index 0000000..5e363e9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/DisabledCode.tsx @@ -0,0 +1,31 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const DisabledCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { +Avatar, +Chip, +} from '@mui/material'; +import { IconMoodHappy } from '@tabler/icons-react'; +import InlineItemCard from "@/app/components/shared/InlineItemCard"; + + + M} + onDelete={handleDelete} + /> + S} + onDelete={handleDelete} + /> +`} + + + ); +}; + +export default DisabledCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/FilledCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/FilledCode.tsx new file mode 100644 index 0000000..9703492 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/FilledCode.tsx @@ -0,0 +1,32 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const FilledCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { Avatar, Chip} from '@mui/material'; +import { IconMoodHappy } from '@tabler/icons-react'; +import InlineItemCard from "@/app/components/shared/InlineItemCard"; + + + M} label="Default Filled" /> + M} label="Default Deletable" onDelete={handleDelete} /> + } label="Primary Filled" color="primary" /> + } label="Primary Deletable" color="primary" onDelete={handleDelete} /> + } label="Secondary Filled" color="secondary" /> + } label="Secondary Deletable" color="secondary" onDelete={handleDelete} /> + } label="Default Filled" color="success" /> + } label="Default Deletable" color="success" onDelete={handleDelete} /> + } label="Default Filled" color="warning" /> + } label="Default Deletable" color="warning" onDelete={handleDelete} /> + } label="Default Filled" color="error" /> + } label="Default Deletable" color="error" onDelete={handleDelete} /> +`} + + + ); +}; + +export default FilledCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/OutlinedCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/OutlinedCode.tsx new file mode 100644 index 0000000..75a9941 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/OutlinedCode.tsx @@ -0,0 +1,36 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const OutlinedCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { +Avatar, +Chip, + } from '@mui/material'; +import { IconMoodHappy } from '@tabler/icons-react'; + +import InlineItemCard from "@/app/components/shared/InlineItemCard"; + + + M} label="Default Filled" /> + M} label="Default Deletable" onDelete={handleDelete} /> + } label="Default Filled" color="primary" /> + } label="Default Deletable" color="primary" onDelete={handleDelete} /> + } label="Default Filled" color="secondary" /> + } label="Default Deletable" color="secondary" onDelete={handleDelete} /> + } label="Default Filled" color="success" /> + } label="Default Deletable" color="success" onDelete={handleDelete} /> + } label="Default Filled" color="warning" /> + } label="Default Deletable" color="warning" onDelete={handleDelete} /> + } label="Default Filled" color="error" /> + } label="Default Deletable" color="error" onDelete={handleDelete} /> +`} + + + ); +}; + +export default OutlinedCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/SizesCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/SizesCode.tsx new file mode 100644 index 0000000..c12e7db --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/chip/code/SizesCode.tsx @@ -0,0 +1,24 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const SizesCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { +Avatar, +Chip, +} from '@mui/material'; +import InlineItemCard from "@/app/components/shared/InlineItemCard"; + + + + +`} + + + ); +}; + +export default SizesCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/AlertDialog.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/AlertDialog.tsx new file mode 100644 index 0000000..cfc60fd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/AlertDialog.tsx @@ -0,0 +1,49 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Button, Dialog, DialogTitle, DialogContent, DialogContentText, DialogActions } from '@mui/material'; + +const AlertDialog = () => { + const [open, setOpen] = React.useState(false); + + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + + + return ( + <> + + + + {"Use Google's location service?"} + + + + Let Google help apps determine location. This means sending anonymous + location data to Google, even when no apps are running. + + + + + + + + + ); +} + +export default AlertDialog; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/FormDialog.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/FormDialog.tsx new file mode 100644 index 0000000..67ed825 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/FormDialog.tsx @@ -0,0 +1,51 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Button, Dialog, DialogTitle, DialogContent, DialogContentText, DialogActions, Box } from '@mui/material'; + +import CustomTextField from "../../forms/theme-elements/CustomTextField"; + +const FormDialog = () => { + const [open, setOpen] = React.useState(false); + + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + + return ( + <> + + + Subscribe + + + To subscribe to this website, please enter your email address here. We + will send updates occasionally. + + + + + + + + + + + + ); +} + +export default FormDialog; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/FullscreenDialog.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/FullscreenDialog.tsx new file mode 100644 index 0000000..b3250b9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/FullscreenDialog.tsx @@ -0,0 +1,74 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Button, + Dialog, + AppBar, + Toolbar, + IconButton, + Typography, + List, + ListItemText, + Divider, + ListItemButton, +} from '@mui/material'; +import Slide from '@mui/material/Slide'; +import { IconX } from '@tabler/icons-react'; +import { TransitionProps } from '@mui/material/transitions'; + +const Transition = React.forwardRef(function Transition( + props: TransitionProps & { + children: React.ReactElement; + }, + ref: React.Ref, +) { + return ; +}); + +const FullscreenDialog = () => { + const [open, setOpen] = React.useState(false); + + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + + return ( + <> + + + + + + + + + Sound + + + + + + + + + + + + + + + + + ); +}; + +export default FullscreenDialog; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/MaxWidthDialog.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/MaxWidthDialog.tsx new file mode 100644 index 0000000..49fed93 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/MaxWidthDialog.tsx @@ -0,0 +1,101 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Button, + Dialog, + DialogTitle, + DialogContent, + DialogContentText, + DialogActions, + Box, + FormControl, + InputLabel, + MenuItem, + FormControlLabel, +} from '@mui/material'; + +import CustomSelect from '../../forms/theme-elements/CustomSelect'; +import CustomSwitch from '../../forms/theme-elements/CustomSwitch'; +import { DialogProps } from '@mui/material/Dialog'; + +const MaxWidthDialog = () => { + const [open, setOpen] = React.useState(false); + const [fullWidth, setFullWidth] = React.useState(true); + const [maxWidth, setMaxWidth] = React.useState('sm'); + + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + + const handleMaxWidthChange = (event: any) => { + setMaxWidth(event.target.value); + }; + + const handleFullWidthChange = (event: any) => { + setFullWidth(event.target.checked); + }; + + return ( + <> + + + Optional sizes + + + You can set my maximum width and whether to adapt or not. + + + + maxWidth + + false + xs + sm + md + lg + xl + + + } + label="Full width" + /> + + + + + + + + ); +}; + +export default MaxWidthDialog; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/ResponsiveDialog.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/ResponsiveDialog.tsx new file mode 100644 index 0000000..6275be2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/ResponsiveDialog.tsx @@ -0,0 +1,59 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Button, + Dialog, + DialogTitle, + DialogContent, + DialogContentText, + DialogActions, +} from '@mui/material'; +import useMediaQuery from '@mui/material/useMediaQuery'; +import { useTheme } from '@mui/material/styles'; + +const ResponsiveDialog = () => { + const [open, setOpen] = React.useState(false); + const theme = useTheme(); + const fullScreen = useMediaQuery(theme.breakpoints.down('md')); + + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + + return ( + <> + + + {"Use Google's location service?"} + + + Let Google help apps determine location. This means sending anonymous location data to + Google, even when no apps are running. + + + + + + + + + ); +}; + +export default ResponsiveDialog; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/ScrollContentDialog.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/ScrollContentDialog.tsx new file mode 100644 index 0000000..37213e2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/ScrollContentDialog.tsx @@ -0,0 +1,83 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Button, + Dialog, + DialogTitle, + DialogContent, + DialogContentText, + DialogActions, + Stack, + DialogProps, +} from '@mui/material'; + +const ScrollContentDialog = () => { + const [open, setOpen] = React.useState(false); + const [scroll, setScroll] = React.useState('paper'); + + const handleClickOpen = (scrollType: DialogProps['scroll']) => () => { + setOpen(true); + setScroll(scrollType); + }; + + const handleClose = () => { + setOpen(false); + }; + + const descriptionElementRef = React.useRef(null); + React.useEffect(() => { + if (open) { + const { current: descriptionElement } = descriptionElementRef; + if (descriptionElement !== null) { + descriptionElement.focus(); + } + } + }, [open]); + + return ( + <> + + + + + + Subscribe + + + {[...new Array(50)] + .map( + () => `Cras mattis consectetur purus sit amet fermentum. +Cras justo odio, dapibus ac facilisis in, egestas eget quam. +Morbi leo risus, porta ac consectetur ac, vestibulum at eros. +Praesent commodo cursus magna, vel scelerisque nisl consectetur et.`, + ) + .join('\n')} + + + + + + + + + ); +}; + +export default ScrollContentDialog; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/SimpleDialog.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/SimpleDialog.tsx new file mode 100644 index 0000000..6e77f3f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/SimpleDialog.tsx @@ -0,0 +1,71 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Typography, + Button, + Dialog, + DialogTitle, + List, + + ListItemAvatar, + Avatar, + ListItemText, + ListItemButton, +} from '@mui/material'; + +import { IconUser, IconPlus } from '@tabler/icons-react'; + +const emails = ['JohnDeo@gmail.com', 'SmithRocky@gmail.com']; + +const SimpleDialog = () => { + const [open, setOpen] = React.useState(false); + const [selectedValue, setSelectedValue] = React.useState(emails[1]); + + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = (value: string) => { + setOpen(false); + setSelectedValue(value); + }; + + return ( + <> + + + Selected: {selectedValue} + + handleClose(selectedValue)} open={open}> + Set backup account + + {emails.map((email) => ( + handleClose(email)} key={email}> + + + + + + + + ))} + + + handleClose('addAccount')}> + + + + + + + + + + + ); +}; + +export default SimpleDialog; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/TransitionDialog.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/TransitionDialog.tsx new file mode 100644 index 0000000..248f4ea --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/TransitionDialog.tsx @@ -0,0 +1,65 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Button, + Dialog, + DialogTitle, + DialogContent, + DialogContentText, + DialogActions, +} from '@mui/material'; +import Slide from '@mui/material/Slide'; +import { TransitionProps } from '@mui/material/transitions'; + +const Transition = React.forwardRef(function Transition( + props: TransitionProps & { + children: React.ReactElement; + }, + ref: React.Ref, +) { + return ; +}); + +const TransitionDialog = () => { + const [open, setOpen] = React.useState(false); + + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + + return ( + <> + + + {"Use Google's location service?"} + + + Let Google help apps determine location. This means sending anonymous location data to + Google, even when no apps are running. + + + + + + + + + ); +}; + +export default TransitionDialog; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/AlertCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/AlertCode.tsx new file mode 100644 index 0000000..4ff428e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/AlertCode.tsx @@ -0,0 +1,63 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const AlertCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { +Button, +Dialog, +DialogTitle, +DialogContent, +DialogContentText, +DialogActions, +} from '@mui/material'; + +const [open, setOpen] = React.useState(false); + +const handleClickOpen = () => { + setOpen(true); +}; + +const handleClose = () => { + setOpen(false); +}; + + +return ( + <> + + + + {"Use Google's location service?"} + + + + Let Google help apps determine location. This means sending anonymous + location data to Google, even when no apps are running. + + + + + + + + +);`} + + + ); +}; + +export default AlertCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/FormCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/FormCode.tsx new file mode 100644 index 0000000..c288460 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/FormCode.tsx @@ -0,0 +1,67 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const FormCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { +Button, +Dialog, +DialogTitle, +DialogContent, +DialogContentText, +DialogActions, +Box +} from '@mui/material'; + +import CustomTextField from "../../forms/theme-elements/CustomTextField"; + +const [open, setOpen] = React.useState(false); + +const handleClickOpen = () => { + setOpen(true); +}; + +const handleClose = () => { + setOpen(false); +}; + + +return ( + <> + + + Subscribe + + + To subscribe to this website, please enter your email address here. We + will send updates occasionally. + + + + + + + + + + + +);`} + + + ); +}; + +export default FormCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/FullScreenCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/FullScreenCode.tsx new file mode 100644 index 0000000..3dfbfea --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/FullScreenCode.tsx @@ -0,0 +1,81 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const FullScreenCode = () => { + return ( + <> + + {` + +import { + Button, + Dialog, + AppBar, + Toolbar, + IconButton, + Typography, + List, + ListItem, + ListItemText, + Divider, + ListItemButton, +} from '@mui/material'; +import Slide from '@mui/material/Slide'; +import { IconX } from '@tabler/icons-react'; +import { TransitionProps } from '@mui/material/transitions'; + +const Transition = React.forwardRef(function Transition( + props: TransitionProps & { + children: React.ReactElement; + }, + ref: React.Ref, +) { + return ; +}); + +const [open, setOpen] = React.useState(false); + +const handleClickOpen = () => { + setOpen(true); +}; + +const handleClose = () => { + setOpen(false); +}; + + +return ( + <> + + + + + + + + + Sound + + + + + + + + + + + + + + + +);`} + + + ); +}; + +export default FullScreenCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/MaxWidthCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/MaxWidthCode.tsx new file mode 100644 index 0000000..21b7bd2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/MaxWidthCode.tsx @@ -0,0 +1,108 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const MaxWidthCode = () => { + return ( + <> + + {` + +import { + Button, + Dialog, + DialogTitle, + DialogContent, + DialogContentText, + DialogActions, + Box, + FormControl, + InputLabel, + MenuItem, + FormControlLabel, +} from '@mui/material'; + +import CustomSelect from '../../forms/theme-elements/CustomSelect'; +import CustomSwitch from '../../forms/theme-elements/CustomSwitch'; +import { DialogProps } from '@mui/material/Dialog'; + +const [open, setOpen] = React.useState(false); +const [fullWidth, setFullWidth] = React.useState(true); +const [maxWidth, setMaxWidth] = React.useState('sm'); + +const handleClickOpen = () => { + setOpen(true); +}; + +const handleClose = () => { + setOpen(false); +}; + +const handleMaxWidthChange = (event: any) => { + setMaxWidth(event.target.value); +}; + +const handleFullWidthChange = (event: any) => { + setFullWidth(event.target.checked); +}; + + +return ( + <> + + + Optional sizes + + + You can set my maximum width and whether to adapt or not. + + + + maxWidth + + false + xs + sm + md + lg + xl + + + } + label="Full width" + /> + + + + + + + +);`} + + + ); +}; + +export default MaxWidthCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/ResponsiveFullscreenCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/ResponsiveFullscreenCode.tsx new file mode 100644 index 0000000..ee06a31 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/ResponsiveFullscreenCode.tsx @@ -0,0 +1,65 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ResponsiveFullscreenCode = () => { + return ( + <> + + {` + +import { + Button, + Dialog, + DialogTitle, + DialogContent, + DialogContentText, + DialogActions, +} from '@mui/material'; +import useMediaQuery from '@mui/material/useMediaQuery'; +import { useTheme } from '@mui/material/styles'; + +const [open, setOpen] = React.useState(false); +const theme = useTheme(); +const fullScreen = useMediaQuery(theme.breakpoints.down('md')); + +const handleClickOpen = () => { + setOpen(true); +}; + +const handleClose = () => { + setOpen(false); +}; + +return ( + <> + + + {"Use Google's location service?"} + + + Let Google help apps determine location. This means sending anonymous location data to + Google, even when no apps are running. + + + + + + + + +);`} + + + ); +}; + +export default ResponsiveFullscreenCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/ScrollingContentCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/ScrollingContentCode.tsx new file mode 100644 index 0000000..233fc45 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/ScrollingContentCode.tsx @@ -0,0 +1,89 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ScrollingContentCode = () => { + return ( + <> + + {` + +import { + Button, + Dialog, + DialogTitle, + DialogContent, + DialogContentText, + DialogActions, + Stack, + DialogProps, +} from '@mui/material'; + +const [open, setOpen] = React.useState(false); +const [scroll, setScroll] = React.useState('paper'); + +const handleClickOpen = (scrollType: DialogProps['scroll']) => () => { + setOpen(true); + setScroll(scrollType); +}; + +const handleClose = () => { + setOpen(false); +}; + +const descriptionElementRef = React.useRef(null); +React.useEffect(() => { + if (open) { + const { current: descriptionElement } = descriptionElementRef; + if (descriptionElement !== null) { + descriptionElement.focus(); + } + } +}, [open]); + +return ( + <> + + + + + + Subscribe + + + {[...new Array(50)] + .map( + () => 'Cras mattis consectetur purus sit amet fermentum. + Cras justo odio, dapibus ac facilisis in, egestas eget quam. + Morbi leo risus, porta ac consectetur ac, vestibulum at eros. + Praesent commodo cursus magna, vel scelerisque nisl consectetur et.', + ) + .join('\n')} + + + + + + + + + );`} + + + ); +}; + +export default ScrollingContentCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/SimpleCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/SimpleCode.tsx new file mode 100644 index 0000000..82f598d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/SimpleCode.tsx @@ -0,0 +1,76 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const SimpleDialogCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { + Typography, + Button, + Dialog, + DialogTitle, + List, + ListItem, + ListItemAvatar, + Avatar, + ListItemText, + ListItemButton, +} from '@mui/material'; +import { IconUser, IconPlus } from '@tabler/icons-react'; + +const emails = ['JohnDeo@gmail.com', 'SmithRocky@gmail.com']; + +const [open, setOpen] = React.useState(false); +const [selectedValue, setSelectedValue] = React.useState(emails[1]); + +const handleClickOpen = () => { + setOpen(true); +}; + +const handleClose = (value: string) => { + setOpen(false); + setSelectedValue(value); +}; + +return ( + <> + + + Selected: {selectedValue} + + handleClose(selectedValue)} open={open}> + Set backup account + + {emails.map((email) => ( + handleClose(email)} key={email}> + + + + + + + + ))} + + handleClose('addAccount')}> + + + + + + + + + + +);`} + + + ); +}; + +export default SimpleDialogCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/TransitionCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/TransitionCode.tsx new file mode 100644 index 0000000..57b22e0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/dialog/code/TransitionCode.tsx @@ -0,0 +1,73 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const TransitionCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { + Button, + Dialog, + DialogTitle, + DialogContent, + DialogContentText, + DialogActions, +} from '@mui/material'; +import Slide from '@mui/material/Slide'; +import { TransitionProps } from '@mui/material/transitions'; + +const Transition = React.forwardRef(function Transition( + props: TransitionProps & { + children: React.ReactElement; + }, + ref: React.Ref, +) { + return ; +}); + +const [open, setOpen] = React.useState(false); + +const handleClickOpen = () => { + setOpen(true); +}; + +const handleClose = () => { + setOpen(false); +}; + + +return ( + <> + + + {"Use Google's location service?"} + + + Let Google help apps determine location. This means sending anonymous location data to + Google, even when no apps are running. + + + + + + + + +);`} + + + ); +}; + +export default TransitionCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/ControlsList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/ControlsList.tsx new file mode 100644 index 0000000..63b3b10 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/ControlsList.tsx @@ -0,0 +1,72 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + List, + ListItem, + ListItemButton, + ListItemIcon, + ListItemText, + + IconButton, + Checkbox, +} from '@mui/material'; + +import { IconMessage } from '@tabler/icons-react'; +import BlankCard from '../../shared/BlankCard'; + +const ControlsList = () => { + const [checked, setChecked] = React.useState([0]); + + const handleToggle = (value: number) => () => { + const currentIndex = checked.indexOf(value); + const newChecked = [...checked]; + + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + + setChecked(newChecked); + }; + + return ( + <> + + + {[0, 1, 2, 3].map((value) => { + const labelId = `checkbox-list-label-${value}`; + + return ( + + + + } + disablePadding + > + + + + + + + + ); + })} + + + + ); +}; + +export default ControlsList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/FolderList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/FolderList.tsx new file mode 100644 index 0000000..a377d80 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/FolderList.tsx @@ -0,0 +1,44 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { List, ListItem, ListItemText, ListItemAvatar, Avatar } from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; + +import { IconPhoto, IconBriefcase, IconBeach } from '@tabler/icons-react'; + +const FolderList = () => { + return ( + <> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default FolderList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/NestedList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/NestedList.tsx new file mode 100644 index 0000000..f18f20c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/NestedList.tsx @@ -0,0 +1,77 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + List, + ListItemButton, + ListItemIcon, + ListItemText, + ListSubheader, + Collapse, +} from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; + +import { + IconInbox, + IconMailOpened, + IconSend, + IconChevronDown, + IconChevronUp, + IconStar, +} from '@tabler/icons-react'; + +const NestedList = () => { + const [open, setOpen] = React.useState(true); + + const handleClick = () => { + setOpen(!open); + }; + + return ( + <> + + + Nested List Items + + } + > + + + + + + + + + + + + + + + + + + {open ? : } + + + + + + + + + + + + + + + ); +}; + +export default NestedList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/SelectedList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/SelectedList.tsx new file mode 100644 index 0000000..5098a0c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/SelectedList.tsx @@ -0,0 +1,64 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { List, ListItemText, ListItemButton, Divider, ListItemIcon } from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; + +import { IconInbox, IconMailOpened } from '@tabler/icons-react'; + +const SelectedList = () => { + const [selectedIndex, setSelectedIndex] = React.useState(1); + + const handleListItemClick = ( + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + event: React.MouseEvent, + index: number, + ) => { + setSelectedIndex(index); + }; + + return ( + <> + + + handleListItemClick(event, 0)} + > + + + + + + handleListItemClick(event, 1)} + > + + + + + + + + + handleListItemClick(event, 2)} + > + + + handleListItemClick(event, 3)} + > + + + + + + ); +}; + +export default SelectedList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/SimpleList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/SimpleList.tsx new file mode 100644 index 0000000..b4c7479 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/SimpleList.tsx @@ -0,0 +1,56 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import BlankCard from '../../shared/BlankCard'; +import { + List, + ListItem, + ListItemButton, + ListItemIcon, + ListItemText, + Divider +} from '@mui/material'; + +import { IconInbox, IconMailOpened } from '@tabler/icons-react'; + +const SimpleList = () => { + return ( + <> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default SimpleList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/SwitchList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/SwitchList.tsx new file mode 100644 index 0000000..ad440d2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/SwitchList.tsx @@ -0,0 +1,65 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { List, ListItem, ListItemIcon, ListItemText, ListSubheader } from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; + +import { IconWifi, IconBluetooth } from '@tabler/icons-react'; + +import CustomSwitch from '../../forms/theme-elements/CustomSwitch'; + +const SwitchList = () => { + const [checked, setChecked] = React.useState(['wifi']); + + const handleToggle = (value: string) => () => { + const currentIndex = checked.indexOf(value); + const newChecked = [...checked]; + + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + + setChecked(newChecked); + }; + + return ( + <> + + Settings}> + + + + + + + + + + + + + + + + + + ); +}; + +export default SwitchList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/ControlsListCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/ControlsListCode.tsx new file mode 100644 index 0000000..ab61fce --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/ControlsListCode.tsx @@ -0,0 +1,73 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ControlsListCode = () => { + return ( + <> + + {` +import React from 'react'; +import { + List, + ListItem, + ListItemButton, + ListItemIcon, + ListItemText, + IconButton, + Checkbox, + Card +} from '@mui/material'; + +import { IconMessage } from '@tabler/icons-react'; + +const [checked, setChecked] = React.useState([0]); + +const handleToggle = (value: number) => () => { + const currentIndex = checked.indexOf(value); + const newChecked = [...checked]; + + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + + setChecked(newChecked); +}; + + + + {[0, 1, 2, 3].map((value) => { + const labelId = 'checkbox-list-label-{value}'; + + return ( + + + + } + disablePadding + > + + + + + + + + ); + })} + + `} + + + ); +}; + +export default ControlsListCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/FolderListCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/FolderListCode.tsx new file mode 100644 index 0000000..abcaa80 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/FolderListCode.tsx @@ -0,0 +1,56 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const FolderListCode = () => { + return ( + <> + + {` +import React from 'react'; +import { +List, +ListItem, +ListItemText, +ListItemAvatar, +Avatar, +Card +} from '@mui/material'; + +import { +IconPhoto, +IconBriefcase, +IconBeach +} from '@tabler/icons-react'; + + + + + + + + + + + + + + + + + + + + + + + + + + + + +`} + + + ); +}; + +export default FolderListCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/NestedListCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/NestedListCode.tsx new file mode 100644 index 0000000..56b2032 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/NestedListCode.tsx @@ -0,0 +1,79 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const NestedListCode = () => { + return ( + <> + + {` +import React from 'react'; +import { + List, + ListItemButton, + ListItemIcon, + ListItemText, + ListSubheader, + Collapse, + Card +} from '@mui/material'; + +import { + IconInbox, + IconMailOpened, + IconSend, + IconChevronDown, + IconChevronUp, + IconStar, +} from '@tabler/icons-react'; + +const [open, setOpen] = React.useState(true); + +const handleClick = () => { + setOpen(!open); +}; + + + + Nested List Items + + } + > + + + + + + + + + + + + + + + + + + {open ? : } + + + + + + + + + + + + +`} + + + ); +}; + +export default NestedListCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/SelectedListCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/SelectedListCode.tsx new file mode 100644 index 0000000..292f286 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/SelectedListCode.tsx @@ -0,0 +1,73 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const SelectedListCode = () => { + return ( + <> + + {` +import React from 'react'; +import { +List, +ListItemText, +ListItemButton, +Divider, +ListItemIcon, +Card +} from '@mui/material'; + +import { +IconInbox, +IconMailOpened +} from '@tabler/icons-react'; + +const [selectedIndex, setSelectedIndex] = React.useState(1); + +const handleListItemClick = ( + event: React.MouseEvent, + index: number, +) => { + setSelectedIndex(index); +}; + + + + handleListItemClick(event, 0)} + > + + + + + + handleListItemClick(event, 1)} + > + + + + + + + + + handleListItemClick(event, 2)} + > + + + handleListItemClick(event, 3)} + > + + + +`} + + + ); +}; + +export default SelectedListCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/SimpleListCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/SimpleListCode.tsx new file mode 100644 index 0000000..c10f93a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/SimpleListCode.tsx @@ -0,0 +1,59 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const SimpleListCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { + List, + ListItem, + ListItemButton, + ListItemIcon, + ListItemText, + Divider, + Card +} from '@mui/material'; + +import { IconInbox, IconMailOpened } from '@tabler/icons-react'; + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +`} + + + ); +}; + +export default SimpleListCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/SwitchListCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/SwitchListCode.tsx new file mode 100644 index 0000000..c7d3e46 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/lists/code/SwitchListCode.tsx @@ -0,0 +1,76 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const SwitchListCode = () => { + return ( + <> + + {` +import React from 'react'; +import { + List, + ListItem, + ListItemIcon, + ListItemText, + ListSubheader, + Card +} from '@mui/material'; + +import { + IconWifi, + IconBluetooth +} from '@tabler/icons-react'; + +import CustomSwitch from '../../forms/theme-elements/CustomSwitch'; + +const [checked, setChecked] = React.useState(['wifi']); + +const handleToggle = (value: string) => () => { + const currentIndex = checked.indexOf(value); + const newChecked = [...checked]; + + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + + setChecked(newChecked); +}; + + + Settings}> + + + + + + + + + + + + + + + +`} + + + ); +}; + +export default SwitchListCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/ClickPopover.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/ClickPopover.tsx new file mode 100644 index 0000000..fb64320 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/ClickPopover.tsx @@ -0,0 +1,47 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Popover, Typography, Button, Box } from '@mui/material'; + +const ClickPopover = () => { + const [anchorEl, setAnchorEl] = React.useState(null); + + const handleClick = (event: any) => { + setAnchorEl(event.currentTarget); + }; + + const handleClose = () => { + setAnchorEl(null); + }; + + const open = Boolean(anchorEl); + const id = open ? 'simple-popover' : undefined; + + return ( + <> + + + + + Basic Popover + + + The component is built on top of the Modal component. + + + + + ); +}; +export default ClickPopover; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/HoverPopover.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/HoverPopover.tsx new file mode 100644 index 0000000..14dc903 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/HoverPopover.tsx @@ -0,0 +1,59 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Popover, Box, Typography } from '@mui/material'; + +const HoverPopover = () => { + const [anchorEl, setAnchorEl] = React.useState(null); + + const handlePopoverOpen = (event: any) => { + setAnchorEl(event.currentTarget); + }; + + const handlePopoverClose = () => { + setAnchorEl(null); + }; + + const open = Boolean(anchorEl); + + return ( + <> + + Hover with a Popover. + + + + + Hover Popover + + + The component is built on top of the Modal component. + + + + + ); +}; +export default HoverPopover; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/code/ClickPopoverCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/code/ClickPopoverCode.tsx new file mode 100644 index 0000000..9bdd4a2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/code/ClickPopoverCode.tsx @@ -0,0 +1,61 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ClickPopoverCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { + Popover, + Typography, + Button, + Box +} from '@mui/material'; + + +const [anchorEl, setAnchorEl] = React.useState(null); + +const handleClick = (event: any) => { + setAnchorEl(event.currentTarget); +}; + +const handleClose = () => { + setAnchorEl(null); +}; + +const open = Boolean(anchorEl); +const id = open ? 'simple-popover' : undefined; + +return ( + <> + + + + + Basic Popover + + + The component is built on top of the Modal component. + + + + +);`} + + + ); +}; + +export default ClickPopoverCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/code/HoverPopoverCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/code/HoverPopoverCode.tsx new file mode 100644 index 0000000..44f3b2d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/popover/code/HoverPopoverCode.tsx @@ -0,0 +1,72 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const HoverPopoverCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { + Popover, + Box, + Typography +} from '@mui/material'; + + +const [anchorEl, setAnchorEl] = React.useState(null); +a +const handlePopoverOpen = (event: any) => { + setAnchorEl(event.currentTarget); +}; + +const handlePopoverClose = () => { + setAnchorEl(null); +}; + +const open = Boolean(anchorEl); + +return ( + <> + + Hover with a Popover. + + + + + Hover Popover + + + The component is built on top of the Modal component. + + + + +);`} + + + ); +}; + +export default HoverPopoverCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconBottomCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconBottomCode.tsx new file mode 100644 index 0000000..e4bbf31 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconBottomCode.tsx @@ -0,0 +1,49 @@ +import CodeDialog from "src/components/shared/CodeDialog"; +const IconBottomCode = () => { + return ( + <> + + {` + +import React from 'react'; +import {Box, Divider } from '@mui/material'; +import Tabs from '@mui/material/Tabs'; +import Tab from '@mui/material/Tab'; +import TabContext from '@mui/lab/TabContext'; +import TabList from '@mui/lab/TabList'; +import TabPanel from '@mui/lab/TabPanel'; + +import { IconHeart, IconPhone, IconUser } from "@tabler/icons-react"; + +const COMMON_TAB = [ + { value: '1', icon: , label: 'Item One', disabled: false }, + { value: '2', icon: , label: 'Item Two', disabled: false }, + { value: '3', icon: , label: 'Item Three', disabled: true } +]; + +const [value, setValue] = React.useState('1'); + +const handleChange = (event: React.SyntheticEvent, newValue: string) => { + setValue(newValue); +}; + + + + {COMMON_TAB.map((tab) => ( + + ))} + + + {COMMON_TAB.map((panel) => ( + + {panel.label} + + ))} + +`} + + + ); +}; + +export default IconBottomCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconCode.tsx new file mode 100644 index 0000000..d3306ad --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconCode.tsx @@ -0,0 +1,50 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const IconCode = () => { + return ( + <> + + {` + +import React from 'react'; +import {Box, Divider } from '@mui/material'; +import Tabs from '@mui/material/Tabs'; +import Tab from '@mui/material/Tab'; +import TabContext from '@mui/lab/TabContext'; +import TabList from '@mui/lab/TabList'; +import TabPanel from '@mui/lab/TabPanel'; + +import { IconHeart, IconPhone, IconUser } from "@tabler/icons-react"; + +const COMMON_TAB = [ + { value: '1', icon: , label: 'Item One', disabled: false }, + { value: '2', icon: , label: 'Item Two', disabled: false }, + { value: '3', icon: , label: 'Item Three', disabled: true } +]; + +const [value, setValue] = React.useState('1'); + +const handleChange = (event: React.SyntheticEvent, newValue: string) => { + setValue(newValue); +}; + + + + {COMMON_TAB.map((tab) => ( + + ))} + + + {COMMON_TAB.map((panel) => ( + + {panel.label} + + ))} + + +`} + + + ); +}; + +export default IconCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconLeftCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconLeftCode.tsx new file mode 100644 index 0000000..2f73a86 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconLeftCode.tsx @@ -0,0 +1,49 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const IconLeftCode = () => { + return ( + <> + + {` + +import React from 'react'; +import {Box, Divider } from '@mui/material'; +import Tabs from '@mui/material/Tabs'; +import Tab from '@mui/material/Tab'; +import TabContext from '@mui/lab/TabContext'; +import TabList from '@mui/lab/TabList'; +import TabPanel from '@mui/lab/TabPanel'; + +import { IconHeart, IconPhone, IconUser } from "@tabler/icons-react"; + +const COMMON_TAB = [ + { value: '1', icon: , label: 'Item One', disabled: false }, + { value: '2', icon: , label: 'Item Two', disabled: false }, + { value: '3', icon: , label: 'Item Three', disabled: true } +]; + +const [value, setValue] = React.useState('1'); + +const handleChange = (event: React.SyntheticEvent, newValue: string) => { + setValue(newValue); +}; + + + + {COMMON_TAB.map((tab) => ( + + ))} + + + {COMMON_TAB.map((panel) => ( + + {panel.label} + + ))} + +`} + + + ); +}; + +export default IconLeftCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconRightCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconRightCode.tsx new file mode 100644 index 0000000..02a1af8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconRightCode.tsx @@ -0,0 +1,49 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const IconRightCode = () => { + return ( + <> + + {` + +import React from 'react'; +import {Box, Divider } from '@mui/material'; +import Tabs from '@mui/material/Tabs'; +import Tab from '@mui/material/Tab'; +import TabContext from '@mui/lab/TabContext'; +import TabList from '@mui/lab/TabList'; +import TabPanel from '@mui/lab/TabPanel'; + +import { IconHeart, IconPhone, IconUser } from "@tabler/icons-react"; + +const COMMON_TAB = [ + { value: '1', icon: , label: 'Item One', disabled: false }, + { value: '2', icon: , label: 'Item Two', disabled: false }, + { value: '3', icon: , label: 'Item Three', disabled: true } +]; + +const [value, setValue] = React.useState('1'); + +const handleChange = (event: React.SyntheticEvent, newValue: string) => { + setValue(newValue); +}; + + + + {COMMON_TAB.map((tab) => ( + + ))} + + + {COMMON_TAB.map((panel) => ( + + {panel.label} + + ))} + +`} + + + ); +}; + +export default IconRightCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconWithLabelCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconWithLabelCode.tsx new file mode 100644 index 0000000..fcbba6a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/IconWithLabelCode.tsx @@ -0,0 +1,49 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const IconWithLabelCode = () => { + return ( + <> + + {` + +import React from 'react'; +import {Box, Divider } from '@mui/material'; +import Tabs from '@mui/material/Tabs'; +import Tab from '@mui/material/Tab'; +import TabContext from '@mui/lab/TabContext'; +import TabList from '@mui/lab/TabList'; +import TabPanel from '@mui/lab/TabPanel'; + +import { IconHeart, IconPhone, IconUser } from "@tabler/icons-react"; + +const COMMON_TAB = [ + { value: '1', icon: , label: 'Item One', disabled: false }, + { value: '2', icon: , label: 'Item Two', disabled: false }, + { value: '3', icon: , label: 'Item Three', disabled: true } +]; + +const [value, setValue] = React.useState('1'); + +const handleChange = (event: React.SyntheticEvent, newValue: string) => { + setValue(newValue); +}; + + + + {COMMON_TAB.map((tab) => ( + + ))} + + + {COMMON_TAB.map((panel) => ( + + {panel.label} + + ))} + +`} + + + ); +}; + +export default IconWithLabelCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/ScrollableCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/ScrollableCode.tsx new file mode 100644 index 0000000..f7c119f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/ScrollableCode.tsx @@ -0,0 +1,53 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const IconBottomCode = () => { + return ( + <> + + {` + +import React from 'react'; +import {Box, Divider } from '@mui/material'; +import Tabs from '@mui/material/Tabs'; +import Tab from '@mui/material/Tab'; +import TabContext from '@mui/lab/TabContext'; +import TabList from '@mui/lab/TabList'; +import TabPanel from '@mui/lab/TabPanel'; + +import { IconHeart, IconPhone, IconUser } from "@tabler/icons-react"; + +const SCROLLABLE_TAB = [ + { value: '1', icon: , label: 'Item 1' }, + { value: '2', icon: , label: 'Item 2' }, + { value: '3', icon: , label: 'Item 3' }, + { value: '4', icon: , label: 'Item 4' }, + { value: '5', icon: , label: 'Item 5' }, + { value: '6', icon: , label: 'Item 6' }, + { value: '7', icon: , label: 'Item 7' } +]; + +const [value, setValue] = React.useState('1'); + +const handleChange = (event: React.SyntheticEvent, newValue: string) => { + setValue(newValue); +}; + + + + {SCROLLABLE_TAB.map((tab) => ( + + ))} + + + {SCROLLABLE_TAB.map((panel) => ( + + {panel.label} + + ))} + +`} + + + ); +}; + +export default IconBottomCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/TextCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/TextCode.tsx new file mode 100644 index 0000000..d0758f3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/TextCode.tsx @@ -0,0 +1,51 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const TextCode = () => { + return ( + <> + + {` + +import React from 'react'; +import {Box, Divider } from '@mui/material'; +import Tabs from '@mui/material/Tabs'; +import Tab from '@mui/material/Tab'; +import TabContext from '@mui/lab/TabContext'; +import TabList from '@mui/lab/TabList'; +import TabPanel from '@mui/lab/TabPanel'; + +const COMMON_TAB = [ + { value: '1', icon: , label: 'Item One', disabled: false }, + { value: '2', icon: , label: 'Item Two', disabled: false }, + { value: '3', icon: , label: 'Item Three', disabled: true } +]; + +const [value, setValue] = React.useState('1'); + +const handleChange = (event: React.SyntheticEvent, newValue: string) => { + setValue(newValue); +}; + + + + + {COMMON_TAB.map((tab, index) => ( + + ))} + + + + + {COMMON_TAB.map((panel, index) => ( + + {panel.label} + + ))} + + +`} + + + ); +}; + +export default TextCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/VerticalCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/VerticalCode.tsx new file mode 100644 index 0000000..2b47421 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tabs/code/VerticalCode.tsx @@ -0,0 +1,57 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const IconBottomCode = () => { + return ( + <> + + {` + +import React from 'react'; +import {Box, Divider } from '@mui/material'; +import Tabs from '@mui/material/Tabs'; +import Tab from '@mui/material/Tab'; +import TabContext from '@mui/lab/TabContext'; +import TabList from '@mui/lab/TabList'; +import TabPanel from '@mui/lab/TabPanel'; + +import { IconHeart, IconPhone, IconUser } from "@tabler/icons-react"; + +const SCROLLABLE_TAB = [ + { value: '1', icon: , label: 'Item 1' }, + { value: '2', icon: , label: 'Item 2' }, + { value: '3', icon: , label: 'Item 3' }, + { value: '4', icon: , label: 'Item 4' }, + { value: '5', icon: , label: 'Item 5' }, + { value: '6', icon: , label: 'Item 6' }, + { value: '7', icon: , label: 'Item 7' } +]; + +const [value, setValue] = React.useState('1'); + +const handleChange = (event: React.SyntheticEvent, newValue: string) => { + setValue(newValue); +}; + + + + + {SCROLLABLE_TAB.map((tab) => ( + + ))} + + + {SCROLLABLE_TAB.map((panel) => ( + + {panel.label} + + ))} + + +`} + + + ); +}; + +export default IconBottomCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/ArrowTooltipCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/ArrowTooltipCode.tsx new file mode 100644 index 0000000..611942e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/ArrowTooltipCode.tsx @@ -0,0 +1,28 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ArrowTooltipCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { styled } from '@mui/material/styles'; +import { IconButton, Button, Stack, Fab, Box } from '@mui/material'; +import Tooltip, { TooltipProps, tooltipClasses } from '@mui/material/Tooltip'; + +import { IconPlus } from '@tabler/icons-react'; + + + + + + + + +`} + + + ); +}; + +export default ArrowTooltipCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/PositionsTooltipCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/PositionsTooltipCode.tsx new file mode 100644 index 0000000..3fef617 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/PositionsTooltipCode.tsx @@ -0,0 +1,57 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const PositionsTooltipCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { styled } from '@mui/material/styles'; +import { Button } from '@mui/material'; +import Tooltip, { TooltipProps, tooltipClasses } from '@mui/material/Tooltip'; +import InlineItemCard from "@/app/components/shared/InlineItemCard"; + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +`} + + + ); +}; + +export default PositionsTooltipCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/SimpleTooltipCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/SimpleTooltipCode.tsx new file mode 100644 index 0000000..3147c18 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/SimpleTooltipCode.tsx @@ -0,0 +1,42 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const SimpleTooltipCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { styled } from '@mui/material/styles'; +import { IconButton, Button, Stack, Fab, Box } from '@mui/material'; +import Tooltip, { TooltipProps, tooltipClasses } from '@mui/material/Tooltip'; + +import { IconPlus, IconTrash } from '@tabler/icons-react'; + + + + + + + + + + + + + + + + + + + + +`} + + + ); +}; + +export default SimpleTooltipCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/TransitionsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/TransitionsCode.tsx new file mode 100644 index 0000000..0ba7f6e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/TransitionsCode.tsx @@ -0,0 +1,35 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const TransitionsCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { styled } from '@mui/material/styles'; +import { IconButton, Button, Stack, Fab, Box } from '@mui/material'; +import Tooltip, { TooltipProps, tooltipClasses } from '@mui/material/Tooltip'; +import Fade from '@mui/material/Fade'; +import Zoom from '@mui/material/Zoom'; + + + + + + + + + + + +`} + + + ); +}; + +export default TransitionsCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/VariableWidthCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/VariableWidthCode.tsx new file mode 100644 index 0000000..a86b8a8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/tooltip/code/VariableWidthCode.tsx @@ -0,0 +1,53 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const VariableWidthCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { styled } from '@mui/material/styles'; +import { IconButton, Button, Stack, Fab, Box } from '@mui/material'; +import Tooltip, { TooltipProps, tooltipClasses } from '@mui/material/Tooltip'; + +const CustomWidthTooltip = styled(({ className, ...props }: TooltipProps) => ( + +))({ + ['& .{tooltipClasses.tooltip}']: { + maxWidth: 500, + }, +}); + +const NoMaxWidthTooltip = styled(({ className, ...props }: TooltipProps) => ( + +))({ + ['& .{tooltipClasses.tooltip}']: { + maxWidth: 'none', + }, +}); + +const longText = ' +Aliquam eget finibus ante, non facilisis lectus. Sed vitae dignissim est, vel aliquam tellus. +Praesent non nunc mollis, fermentum neque at, semper arcu. +Nullam eget est sed sem iaculis gravida eget vitae justo. +'; + +import { IconPlus, IconTrash } from '@tabler/icons-react'; + + + + + + + + + + + +`} + + + ); +}; + +export default VariableWidthCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/BasicTransferList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/BasicTransferList.tsx new file mode 100644 index 0000000..be2aab2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/BasicTransferList.tsx @@ -0,0 +1,150 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { Grid2 as Grid, List, ListItem, ListItemIcon, ListItemText, Button, Paper, ListItemButton } from '@mui/material'; + +import { + IconChevronRight, + IconChevronLeft, + IconChevronsLeft, + IconChevronsRight, +} from '@tabler/icons-react'; + +import CustomCheckbox from '../../forms/theme-elements/CustomCheckbox'; + +function not(a: readonly number[], b: readonly number[]) { + return a.filter((value) => b.indexOf(value) === -1); +} + +function intersection(a: readonly number[], b: readonly number[]) { + return a.filter((value) => b.indexOf(value) !== -1); +} + +const BasicTransferList = () => { + const [checked, setChecked] = React.useState([]); + const [left, setLeft] = React.useState([0, 1, 2, 3]); + const [right, setRight] = React.useState([4, 5, 6, 7]); + + const leftChecked = intersection(checked, left); + const rightChecked = intersection(checked, right); + + const handleToggle = (value: number) => () => { + const currentIndex = checked.indexOf(value); + const newChecked = [...checked]; + + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + + setChecked(newChecked); + }; + + const handleAllRight = () => { + setRight(right.concat(left)); + setLeft([]); + }; + + const handleCheckedRight = () => { + setRight(right.concat(leftChecked)); + setLeft(not(left, leftChecked)); + setChecked(not(checked, leftChecked)); + }; + + const handleCheckedLeft = () => { + setLeft(left.concat(rightChecked)); + setRight(not(right, rightChecked)); + setChecked(not(checked, rightChecked)); + }; + + const handleAllLeft = () => { + setLeft(left.concat(right)); + setRight([]); + }; + const theme = useTheme(); + const borderColor = theme.palette.divider; + + const customList = (items: readonly number[]) => ( + + + {items.map((value) => { + const labelId = `transfer-list-item-${value}-label`; + + return ( + + + + + + + ); + })} + + + + ); + + return ( + ( + {customList(left)} + + + + + + + + + {customList(right)} + ) + ); +}; +export default BasicTransferList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/EnhancedTransferList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/EnhancedTransferList.tsx new file mode 100644 index 0000000..73a66ec --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/EnhancedTransferList.tsx @@ -0,0 +1,163 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { + Grid2 as Grid, + List, + ListItem, + ListItemIcon, + ListItemText, + Button, + Divider, + CardHeader, + Stack, + Paper, + ListItemButton, +} from '@mui/material'; + +import { IconChevronRight, IconChevronLeft } from '@tabler/icons-react'; + +import CustomCheckbox from '../../forms/theme-elements/CustomCheckbox'; + +function not(a: readonly number[], b: readonly number[]) { + return a.filter((value) => b.indexOf(value) === -1); +} + +function intersection(a: readonly number[], b: readonly number[]) { + return a.filter((value) => b.indexOf(value) !== -1); +} + +function union(a: readonly number[], b: readonly number[]) { + return [...a, ...not(b, a)]; +} + +const EnhancedTransferList = () => { + const [checked, setChecked] = React.useState([]); + const [left, setLeft] = React.useState([0, 1, 2, 3]); + const [right, setRight] = React.useState([4, 5, 6, 7]); + + const leftChecked = intersection(checked, left); + const rightChecked = intersection(checked, right); + + const handleToggle = (value: number) => () => { + const currentIndex = checked.indexOf(value); + const newChecked = [...checked]; + + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + + setChecked(newChecked); + }; + + const numberOfChecked = (items: readonly number[]) => intersection(checked, items).length; + + const handleToggleAll = (items: readonly number[]) => () => { + if (numberOfChecked(items) === items.length) { + setChecked(not(checked, items)); + } else { + setChecked(union(checked, items)); + } + }; + + const handleCheckedRight = () => { + setRight(right.concat(leftChecked)); + setLeft(not(left, leftChecked)); + setChecked(not(checked, leftChecked)); + }; + + const handleCheckedLeft = () => { + setLeft(left.concat(rightChecked)); + setRight(not(right, rightChecked)); + setChecked(not(checked, rightChecked)); + }; + + const theme = useTheme(); + const borderColor = theme.palette.grey[100]; + + const customList = (title: React.ReactNode, items: readonly number[]) => ( + + + } + title={title} + subheader={`${numberOfChecked(items)}/${items.length} selected`} + /> + + + {items.map((value) => { + const labelId = `transfer-list-all-item-${value}-label`; + + return ( + + + + + + + ); + })} + + + + ); + + return ( + ( + {customList('Choices', left)} + + + + + + + {customList('Chosen', right)} + ) + ); +}; +export default EnhancedTransferList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/code/BasicTransferListCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/code/BasicTransferListCode.tsx new file mode 100644 index 0000000..2684e10 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/code/BasicTransferListCode.tsx @@ -0,0 +1,160 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const BasicTransferListCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { Grid2 as Grid, List, ListItem, ListItemIcon, ListItemText, Button, Paper, ListItemButton } from '@mui/material'; + +import { + IconChevronRight, + IconChevronLeft, + IconChevronsLeft, + IconChevronsRight, +} from '@tabler/icons-react'; + +import CustomCheckbox from '../../forms/theme-elements/CustomCheckbox'; + +function not(a: readonly number[], b: readonly number[]) { + return a.filter((value) => b.indexOf(value) === -1); +} + +function intersection(a: readonly number[], b: readonly number[]) { + return a.filter((value) => b.indexOf(value) !== -1); +} + +const BasicTransferList = () => { +const [checked, setChecked] = React.useState([]); +const [left, setLeft] = React.useState([0, 1, 2, 3]); +const [right, setRight] = React.useState([4, 5, 6, 7]); + +const leftChecked = intersection(checked, left); +const rightChecked = intersection(checked, right); + +const handleToggle = (value: number) => () => { + const currentIndex = checked.indexOf(value); + const newChecked = [...checked]; + + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + + setChecked(newChecked); +}; + +const handleAllRight = () => { + setRight(right.concat(left)); + setLeft([]); +}; + +const handleCheckedRight = () => { + setRight(right.concat(leftChecked)); + setLeft(not(left, leftChecked)); + setChecked(not(checked, leftChecked)); +}; + +const handleCheckedLeft = () => { + setLeft(left.concat(rightChecked)); + setRight(not(right, rightChecked)); + setChecked(not(checked, rightChecked)); +}; + +const handleAllLeft = () => { + setLeft(left.concat(right)); + setRight([]); +}; +const theme = useTheme(); +const borderColor = theme.palette.divider; + +const customList = (items: readonly number[]) => ( + + + {items.map((value) => { + const labelId = 'transfer-list-item-{value}-label'; + + + return ( + + + + + + + ); + })} + + +); + +return ( + + {customList(left)} + + + + + + + + + {customList(right)} + + ); +};`} + + + ); +}; + +export default BasicTransferListCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/code/EnhancedTransferListCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/code/EnhancedTransferListCode.tsx new file mode 100644 index 0000000..fba920d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/transfer-list/code/EnhancedTransferListCode.tsx @@ -0,0 +1,173 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const EnhancedTransferListCode = () => { + return ( + <> + + {` + +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { + Grid2 as Grid, + List, + ListItem, + ListItemIcon, + ListItemText, + Button, + Divider, + CardHeader, + Stack, + Paper,, + ListItemButton, +} from '@mui/material'; + +import { IconChevronRight, IconChevronLeft } from '@tabler/icons-react'; + +import CustomCheckbox from '../../forms/theme-elements/CustomCheckbox'; + +function not(a: readonly number[], b: readonly number[]) { + return a.filter((value) => b.indexOf(value) === -1); +} + +function intersection(a: readonly number[], b: readonly number[]) { + return a.filter((value) => b.indexOf(value) !== -1); +} + +function union(a: readonly number[], b: readonly number[]) { + return [...a, ...not(b, a)]; +} + +const EnhancedTransferList = () => { + const [checked, setChecked] = React.useState([]); + const [left, setLeft] = React.useState([0, 1, 2, 3]); + const [right, setRight] = React.useState([4, 5, 6, 7]); + + const leftChecked = intersection(checked, left); + const rightChecked = intersection(checked, right); + + const handleToggle = (value: number) => () => { + const currentIndex = checked.indexOf(value); + const newChecked = [...checked]; + + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + + setChecked(newChecked); + }; + + const numberOfChecked = (items: readonly number[]) => intersection(checked, items).length; + + const handleToggleAll = (items: readonly number[]) => () => { + if (numberOfChecked(items) === items.length) { + setChecked(not(checked, items)); + } else { + setChecked(union(checked, items)); + } + }; + + const handleCheckedRight = () => { + setRight(right.concat(leftChecked)); + setLeft(not(left, leftChecked)); + setChecked(not(checked, leftChecked)); + }; + + const handleCheckedLeft = () => { + setLeft(left.concat(rightChecked)); + setRight(not(right, rightChecked)); + setChecked(not(checked, rightChecked)); + }; + + const theme = useTheme(); + const borderColor = theme.palette.grey[100]; + + const customList = (title: React.ReactNode, items: readonly number[]) => ( + + + } + title={title} + subheader={'{numberOfChecked(items)}/{items.length} selected'} + /> + + + {items.map((value) => { + const labelId = 'transfer-list-all-item-{value}-label'; + + return ( + + + + + + + ); + })} + + + + ); + + return ( + + {customList('Choices', left)} + + + + + + + {customList('Chosen', right)} + + ); +};`} + + + ); +}; + +export default EnhancedTransferListCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading1Code.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading1Code.tsx new file mode 100644 index 0000000..75b4821 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading1Code.tsx @@ -0,0 +1,16 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const Heading1Code = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + +h1. Heading`} + + + ); +}; + +export default Heading1Code; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading2Code.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading2Code.tsx new file mode 100644 index 0000000..f012323 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading2Code.tsx @@ -0,0 +1,16 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const Heading2Code = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + +h2. Heading`} + + + ); +}; + +export default Heading2Code; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading3Code.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading3Code.tsx new file mode 100644 index 0000000..83533bd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading3Code.tsx @@ -0,0 +1,16 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const Heading3Code = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + +h3. Heading`} + + + ); +}; + +export default Heading3Code; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading4Code.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading4Code.tsx new file mode 100644 index 0000000..52ee48d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading4Code.tsx @@ -0,0 +1,16 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const Heading4Code = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + +h4. Heading`} + + + ); +}; + +export default Heading4Code; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading5Code.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading5Code.tsx new file mode 100644 index 0000000..a325ef5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading5Code.tsx @@ -0,0 +1,16 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const Heading5Code = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + +h5. Heading`} + + + ); +}; + +export default Heading5Code; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading6Code.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading6Code.tsx new file mode 100644 index 0000000..aa96bbc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Heading6Code.tsx @@ -0,0 +1,16 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const Heading6Code = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + +h6. Heading`} + + + ); +}; + +export default Heading6Code; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Subtitle1Code.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Subtitle1Code.tsx new file mode 100644 index 0000000..49e6457 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Subtitle1Code.tsx @@ -0,0 +1,19 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const Subtitle1Code = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + + + subtitle1. Lorem ipsum dolor sit amet, consectetur adipisicing elit. Quos blanditiis + tenetur +`} + + + ); +}; + +export default Subtitle1Code; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Subtitle2Code.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Subtitle2Code.tsx new file mode 100644 index 0000000..8d66cca --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/Subtitle2Code.tsx @@ -0,0 +1,19 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const Subtitle2Code = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + + + subtitle2. Lorem ipsum dolor sit amet, consectetur adipisicing elit. Quos blanditiis + tenetur +`} + + + ); +}; + +export default Subtitle2Code; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextErrorCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextErrorCode.tsx new file mode 100644 index 0000000..4c73b68 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextErrorCode.tsx @@ -0,0 +1,18 @@ +import CodeDialog from "src/components/shared/CodeDialog"; +const TextErrorCode = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + + theme.palette.error.main }}> + Lorem ipsum dolor sit amet, consectetur adipisicing elit. Quos blanditiis tenetur +`} + + + ); +}; + +export default TextErrorCode; \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextInfoCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextInfoCode.tsx new file mode 100644 index 0000000..797d086 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextInfoCode.tsx @@ -0,0 +1,18 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const TextInfoCode = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + + theme.palette.info.main }}> + Lorem ipsum dolor sit amet, consectetur adipisicing elit. Quos blanditiis tenetur +`} + + + ); +}; + +export default TextInfoCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextPrimaryCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextPrimaryCode.tsx new file mode 100644 index 0000000..5b21bcf --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextPrimaryCode.tsx @@ -0,0 +1,18 @@ +import CodeDialog from "src/components/shared/CodeDialog"; +const TextPrimaryCode = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + + theme.palette.primary.main }}> + Lorem ipsum dolor sit amet, consectetur adipisicing elit. Quos blanditiis tenetur +`} + + + ); +}; + +export default TextPrimaryCode; \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextSecondaryCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextSecondaryCode.tsx new file mode 100644 index 0000000..d2f030e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextSecondaryCode.tsx @@ -0,0 +1,18 @@ +import CodeDialog from "src/components/shared/CodeDialog"; +const TextSecondaryCode = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + + + Lorem ipsum dolor sit amet, consectetur adipisicing elit. Quos blanditiis tenetur +`} + + + ); +}; + +export default TextSecondaryCode; \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextSuccessCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextSuccessCode.tsx new file mode 100644 index 0000000..6af21e1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextSuccessCode.tsx @@ -0,0 +1,18 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const TextErrorCode = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + + theme.palette.success.main }}> + Lorem ipsum dolor sit amet, consectetur adipisicing elit. Quos blanditiis tenetur +`} + + + ); +}; + +export default TextErrorCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextWarningCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextWarningCode.tsx new file mode 100644 index 0000000..1a97729 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/material-ui/typography/code/TextWarningCode.tsx @@ -0,0 +1,18 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const TextWarningCode = () => { + return ( + <> + + {` + +import { Typography } from '@mui/material'; + + theme.palette.warning.main }}> + Lorem ipsum dolor sit amet, consectetur adipisicing elit. Quos blanditiis tenetur +`} + + + ); +}; + +export default TextWarningCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/BarChartStackedBySignChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/BarChartStackedBySignChart.tsx new file mode 100644 index 0000000..fc4627f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/BarChartStackedBySignChart.tsx @@ -0,0 +1,58 @@ + +"use client"; + +import { BarChart } from "@mui/x-charts/BarChart"; +import { useTheme } from "@mui/material"; +import ParentCard from 'src/components/shared/ParentCard'; + +import BarChartStackedBySignCode from "../code/barchartcode/BarChartStackedBySignCode"; + +function BarChartStackedBySignChart() { + const pData = [2400, 1398, -9800, 3908, 4800, -3800, 4300]; + const uData = [4000, -3000, -2000, 2780, -1890, 2390, 3490]; + + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + + return ( + } + > + + + + ); +} + +export default BarChartStackedBySignChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/BiaxialBarChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/BiaxialBarChart.tsx new file mode 100644 index 0000000..cb87b97 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/BiaxialBarChart.tsx @@ -0,0 +1,55 @@ +"use client"; + +import { BarChart } from "@mui/x-charts/BarChart"; +import { useTheme } from "@mui/material"; +import ParentCard from 'src/components/shared/ParentCard'; +import BiaxialBarCode from "../code/barchartcode/BiaxialBarCode"; + + +function BiaxialBarChart() { + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const pData = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + return ( + }> + + + ); +} + +export default BiaxialBarChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/MixedBarChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/MixedBarChart.tsx new file mode 100644 index 0000000..b49a83a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/MixedBarChart.tsx @@ -0,0 +1,40 @@ +'use client' +import { BarChart } from '@mui/x-charts/BarChart'; +import { useTheme } from '@mui/material'; +import ParentCard from 'src/components/shared/ParentCard'; +import MixedBarCode from '../code/barchartcode/MixedBarCode'; + +function MixedBarChart() { + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const pData = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const amtData = [2400, 2210, 2290, 2000, 2181, 2500, 2100]; + + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const success = theme.palette.success.main; + + return ( + }> + + + + ) +} + +export default MixedBarChart diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/PositiveAndNegativeBarChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/PositiveAndNegativeBarChart.tsx new file mode 100644 index 0000000..c544056 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/PositiveAndNegativeBarChart.tsx @@ -0,0 +1,56 @@ +'use client' + +import { BarChart } from '@mui/x-charts/BarChart'; +import { useTheme } from '@mui/material'; +import ParentCard from 'src/components/shared/ParentCard'; +import PositiveAndNegativeBarCode from '../code/barchartcode/PositiveAndNegativeBarCode' + +function PositiveAndNegativeBarChart() { + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const pData = [2400, 1398, -9800, 3908, 4800, -3800, 4300]; + + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const success = theme.palette.success.main; + + return ( + }> + + + + ) +} + +export default PositiveAndNegativeBarChart diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/SimpleBarChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/SimpleBarChart.tsx new file mode 100644 index 0000000..05d047c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/SimpleBarChart.tsx @@ -0,0 +1,42 @@ +'use client' + +import { BarChart } from '@mui/x-charts/BarChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import SimpleBarCode from '../code/barchartcode/SimpleBarCode' +import { useTheme } from '@mui/material'; + + +export default function SimpleBarChart() { + + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const pData = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + return ( + }> + + + ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/StackedBarChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/StackedBarChart.tsx new file mode 100644 index 0000000..8d9f248 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/StackedBarChart.tsx @@ -0,0 +1,40 @@ +'use client' + +import { useTheme } from '@mui/material'; +import ParentCard from 'src/components/shared/ParentCard'; +import { BarChart } from '@mui/x-charts/BarChart'; +import StackedBarCode from '../code/barchartcode/StackedBarCode'; + + +function StackedBarChart() { + + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const pData = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + + return ( + }> + + + + ) +} + +export default StackedBarChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/TinyBarChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/TinyBarChart.tsx new file mode 100644 index 0000000..ba6036c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/barcharts/TinyBarChart.tsx @@ -0,0 +1,48 @@ +"use client"; + +import { BarPlot, ChartContainer } from "@mui/x-charts"; +import { useTheme } from "@mui/material/styles"; +import ParentCard from 'src/components/shared/ParentCard'; +import TinyBarCode from "../code/barchartcode/TinyBarCode"; + +const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; +const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" +]; + +const TinyBarChart = () => { + const theme = useTheme(); + const primary = theme.palette.primary.main; + + return ( + }> + + + + + + + ); +}; + +export default TinyBarChart; + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/AreaChartConnectNullsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/AreaChartConnectNullsCode.tsx new file mode 100644 index 0000000..c64469e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/AreaChartConnectNullsCode.tsx @@ -0,0 +1,55 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function AreaChartConnectNullsCode() { + return ( + + {` +'use client' +import * as React from 'react'; +import Stack from '@mui/material/Stack'; +import { LineChart } from '@mui/x-charts/LineChart'; +import { useTheme } from '@mui/material'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'AreaChartConnectNulls ', +}, +]; + +export default function AreaChartConnectNulls() { + const data = [4000, 3000, 2000, null, 1890, 2390, 3490]; + const xData = ["January", "February", "March", "April", "May", "June", "July"]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + + return ( + + + + + + ); +} + `} + + ) +} + +export default AreaChartConnectNullsCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/AreaChartFillByValueCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/AreaChartFillByValueCode.tsx new file mode 100644 index 0000000..5b20c7b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/AreaChartFillByValueCode.tsx @@ -0,0 +1,202 @@ +import CodeDialog from "src/components/shared/CodeDialog"; + + +export default function AreaChartFillByValueCode() { + return ( + + {` +'use client' +import * as React from 'react'; +import { green, red } from '@mui/material/colors'; +import Stack from '@mui/material/Stack'; +import { useYScale, useDrawingArea } from '@mui/x-charts/hooks'; +import { LineChart, areaElementClasses } from '@mui/x-charts/LineChart'; +import { useTheme } from '@mui/material'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'AreaChartFillByValue ', +}, +]; + + + +function ColorSwich({ threshold, color1, color2, id }) { + + const { top, height, bottom } = useDrawingArea(); + const svgHeight = top + bottom + height; + + const scale = useYScale(); // You can provide the axis Id if you have multiple ones + const y0 = scale(threshold); // The coordinate of of the origine + const off = y0 !== undefined ? y0 / svgHeight : 0; + + return ( + + + + + + + ); +} + +export default function AreaChartFillByValue() { + const data = [4000, 3000, -1000, 500, -2100, -250, 3490]; + const xData = ["January", "February", "March", "April", "May", "June", "July"]; + + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const amtDatacolor = theme.palette.error.main; + + return ( + + + + + + + + + + + + + + + + + ); +} + +function ColorPalette({ id }) { + const { top, height, bottom } = useDrawingArea(); + const svgHeight = top + bottom + height; + + const scale = useYScale() // You can provide the axis Id if you have multiple ones + + return ( + + + + + + + + + + + + + + + + + + + + ); +} + +`} + + ) +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/PercentAreaCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/PercentAreaCode.tsx new file mode 100644 index 0000000..fbcea13 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/PercentAreaCode.tsx @@ -0,0 +1,97 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function PercentAreaCode() { + return ( + + {` + +"use client"; +import * as React from 'react'; +import { LineChart } from '@mui/x-charts/LineChart'; +import { useTheme } from '@mui/material'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'PercentAreaChart ', +}, +]; +const time = [ + new Date(2015, 1, 0), + new Date(2015, 2, 0), + new Date(2015, 3, 0), + new Date(2015, 4, 0), + new Date(2015, 5, 0), + new Date(2015, 6, 0), + new Date(2015, 7, 0), +]; +const a = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; +const b = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; +const c = [2400, 2210, 2290, 2000, 2181, 2500, 2100]; + +const getPercents = (array) => + array.map((v, index) => (100 * v) / (a[index] + b[index] + c[index])); + +export default function PercentAreaChart() { + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const amtDatacolor = theme.palette.error.main; + + return ( + + + ); +} +`} + + ) +} + +export default PercentAreaCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/SimpleAreaCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/SimpleAreaCode.tsx new file mode 100644 index 0000000..56f9e53 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/SimpleAreaCode.tsx @@ -0,0 +1,51 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; +function SimpleAreaCode() { + return ( + + {` + +"use client"; + +import { useTheme } from "@mui/material"; +import { LineChart, lineElementClasses } from '@mui/x-charts/LineChart'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'SimpleAreaChart ', +}, +]; +export default function SimpleAreaChart() { + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + + return ( + + + + ); +} +`} + + ) +} + +export default SimpleAreaCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/StackedAreaCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/StackedAreaCode.tsx new file mode 100644 index 0000000..125d617 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/StackedAreaCode.tsx @@ -0,0 +1,67 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function StackedAreaCode() { + return ( + + {` + +"use client"; +import * as React from 'react'; +import { LineChart, lineElementClasses } from '@mui/x-charts/LineChart'; +import { useTheme } from "@mui/material"; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'StackedAreaChart ', +}, +]; + +export default function StackedAreaChart() { + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const monthlyRevenue = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const monthlyExpenses = [2400, 2210, 0, 2000, 2181, 2500, 2100]; + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const expDatacolor = theme.palette.error.main; + + return ( + + + + ); +} +`} + + ) +} + +export default StackedAreaCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/TinyAreaCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/TinyAreaCode.tsx new file mode 100644 index 0000000..010847d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/areachartscode/TinyAreaCode.tsx @@ -0,0 +1,67 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function TinyAreaCode() { + return ( + + {` + +"use client"; +import * as React from 'react'; +import { ChartContainer } from '@mui/x-charts/ChartContainer'; +import { AreaPlot } from '@mui/x-charts/LineChart'; +import { useTheme } from "@mui/material"; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'TinyAreaChart ', +}, +]; + +export default function TinyAreaChart() { + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const xLabels = [ + ' A', + ' B', + ' C', + ' D', + ' E', + ' F', + ' G', + ]; + const theme = useTheme(); + const primary = theme.palette.primary.main; + return ( + + + + + + + ); +} + +`} + + ) +} + +export default TinyAreaCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/BarChartStackedBySignCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/BarChartStackedBySignCode.tsx new file mode 100644 index 0000000..bc1e7e5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/BarChartStackedBySignCode.tsx @@ -0,0 +1,63 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function BarChartStackedBySignCode() { + return ( + + {` + +'use client' + +import { BarChart } from '@mui/x-charts/BarChart'; +import { useTheme } from '@mui/material'; + + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'BarChartStackedBySignChart ', +}, +]; + + +function BarChartStackedBySignChart() { + const pData = [2400, 1398, -9800, 3908, 4800, -3800, 4300]; + const uData = [4000, -3000, -2000, 2780, -1890, 2390, 3490]; + + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + return ( + + + + ) +} + +export default BarChartStackedBySignChart + +`} + + ); +} + +export default BarChartStackedBySignCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/BiaxialBarCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/BiaxialBarCode.tsx new file mode 100644 index 0000000..1693a02 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/BiaxialBarCode.tsx @@ -0,0 +1,75 @@ +import CodeDialog from "src/components/shared/CodeDialog"; + + + +function BiaxialBarCode() { + return ( + + {` + +'use client' +; +import { BarChart } from '@mui/x-charts/BarChart'; +import { useTheme } from '@mui/material'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'BiaxialBarChart ', +}, +]; +function BiaxialBarChart() { + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const pData = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + return ( + + ); +} + +export default BiaxialBarChart; + +`} + + ) +} + +export default BiaxialBarCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/MixedBarCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/MixedBarCode.tsx new file mode 100644 index 0000000..d8b6b04 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/MixedBarCode.tsx @@ -0,0 +1,61 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function MixedBarCode() { + return ( + + {` + +'use client' +; +import { BarChart } from '@mui/x-charts/BarChart'; +import { useTheme } from '@mui/material'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'MixedBarChart ', +}, +]; +function MixedBarChart() { + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const pData = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const amtData = [2400, 2210, 2290, 2000, 2181, 2500, 2100]; + + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const light = theme.palette.success.main; + + return ( + + + ) +} + +export default MixedBarChart +`} + + ) +} + +export default MixedBarCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/PositiveAndNegativeBarCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/PositiveAndNegativeBarCode.tsx new file mode 100644 index 0000000..32a1898 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/PositiveAndNegativeBarCode.tsx @@ -0,0 +1,75 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function PositiveAndNegativeBarCode() { + return ( + + {` + +'use client' +; +import { BarChart } from '@mui/x-charts/BarChart'; +import { useTheme } from '@mui/material'; + + const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'PositiveAndNegativeBarChart ', + }, +]; + + +function PositiveAndNegativeBarChart() { + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const pData = [2400, 1398, -9800, 3908, 4800, -3800, 4300]; + + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + const theme = useTheme(); + const primary = theme.palette.primary.main; + const success = theme.palette.success.main; + + return ( + + + ) +} + +export default PositiveAndNegativeBarChart + +`} + + ) +} + +export default PositiveAndNegativeBarCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/SimpleBarCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/SimpleBarCode.tsx new file mode 100644 index 0000000..02c09ea --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/SimpleBarCode.tsx @@ -0,0 +1,59 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function SimpleBarCode() { + return ( + + {` + +'use client' +import * as React from 'react'; +import { BarChart } from '@mui/x-charts/BarChart'; +import { useTheme } from '@mui/material'; + + const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'SimpleBarChart ', + }, +]; + +export default function SimpleBarChart() { + + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const pData = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + return ( + + + + ); +} +`} + + ); +} + +export default SimpleBarCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/StackedBarCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/StackedBarCode.tsx new file mode 100644 index 0000000..4b6df4b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/StackedBarCode.tsx @@ -0,0 +1,60 @@ + +import CodeDialog from 'src/components/shared/CodeDialog' + +function StackedBarCode() { + return ( + + {` +"use client" + +import React from "react"; +import { BarChart } from '@mui/x-charts/BarChart'; +import { useTheme } from "@mui/material/styles"; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'StackedBarChart ', +}, +]; + +function StackedBarChart() { + + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const pData = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + return ( + + + + ) +} + +export default StackedBarChart; +`} + + ) +} + +export default StackedBarCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/TinyBarCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/TinyBarCode.tsx new file mode 100644 index 0000000..d4978f9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/barchartcode/TinyBarCode.tsx @@ -0,0 +1,63 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function TinyBarCode() { + return ( + + {` + "use client" + + import React from "react"; + import { BarPlot, ChartContainer } from "@mui/x-charts"; + import { useTheme } from "@mui/material/styles"; + + const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'TinyBarChart ', + }, +]; + +const TinyBarChart = () => { + + const theme = useTheme(); + const primary = theme.palette.primary.main; + + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const xLabels = [ + "Week 1", "Week 2", "Week 3", "Week 4", "Week 5", "Week 6", "Week 7" + ]; + + return ( + + + + + + ); +}; + +export default TinyBarChart; + `} + + ) +} + +export default TinyBarCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/gaugechartscode/ArcDesignCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/gaugechartscode/ArcDesignCode.tsx new file mode 100644 index 0000000..4f029e1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/gaugechartscode/ArcDesignCode.tsx @@ -0,0 +1,55 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function ArcDesignCode() { + return ( + + {` +import * as React from 'react'; +import { Gauge, gaugeClasses } from '@mui/x-charts/Gauge'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'ArcDesignChart ', +}, +]; +const settings = { + width: 200, + height: 200, + value: 60, +}; + +export default function ArcDesignChart() { + return ( + + + ({ + [\`& \.\${gaugeClasses.valueText}\`]: { + fontSize: 40, + }, + [\`& \.\${gaugeClasses.valueArc}\`]: { + fill: theme.palette.primary, + }, + [\`& \.\${gaugeClasses.referenceArc}\`]: { + fill: theme.palette.text.disabled, + }, + })} + /> + + ); +} + + +`} + + ); +} + +export default ArcDesignCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/gaugechartscode/BasicGaugesCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/gaugechartscode/BasicGaugesCode.tsx new file mode 100644 index 0000000..9a86139 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/gaugechartscode/BasicGaugesCode.tsx @@ -0,0 +1,38 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function BasicGaugesCode() { + return ( + + {` +import * as React from 'react'; +import Stack from '@mui/material/Stack'; +import { Gauge } from '@mui/x-charts/Gauge'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'BasicGaugesChart ', +}, +]; + +export default function BasicGaugesChart() { + return ( + + + + + + ); +} + + +`} + + ) +} + +export default BasicGaugesCode \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/gaugechartscode/GaugePointerCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/gaugechartscode/GaugePointerCode.tsx new file mode 100644 index 0000000..48004ce --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/gaugechartscode/GaugePointerCode.tsx @@ -0,0 +1,75 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function GaugePointerCode() { + return ( + + {` + +import { + GaugeContainer, + GaugeValueArc, + GaugeReferenceArc, + useGaugeState, +} from '@mui/x-charts/Gauge'; + + + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'GaugePointerChart ', +}, +]; + + + +function GaugePointer() { + const { valueAngle, outerRadius, cx, cy } = useGaugeState(); + + if (valueAngle === null) { + // No value to display + return null; + } + + const target = { + x: cx + outerRadius * Math.sin(valueAngle), + y: cy - outerRadius * Math.cos(valueAngle), + }; + return ( + + + + + ); +} + +export default function GaugePointerChart() { + return ( + + + + + + + ); +} +`} + + ) +} + +export default GaugePointerCode \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/BiaxialLineCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/BiaxialLineCode.tsx new file mode 100644 index 0000000..b422241 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/BiaxialLineCode.tsx @@ -0,0 +1,57 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function BiaxialLineCode() { + return ( + + {` + +"use client"; +import * as React from 'react'; +import { LineChart } from '@mui/x-charts/LineChart'; +import { useTheme } from "@mui/material"; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'BiaxialLineChart ', +}, +]; +export default function BiaxialLineChart() { + + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const monthlyRevenue = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + return ( + + ); +} +`} + + ) +} + +export default BiaxialLineCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/DashedLineCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/DashedLineCode.tsx new file mode 100644 index 0000000..1aa6ad4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/DashedLineCode.tsx @@ -0,0 +1,70 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; +import { markElementClasses } from '@mui/x-charts' + +function DashedLineCode() { + return ( + + {` + +'use client' +import * as React from 'react'; +import { + LineChart, + lineElementClasses, + markElementClasses, +} from '@mui/x-charts/LineChart'; +import { useTheme } from "@mui/material"; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'DashedLineChart ', +}, +]; export default function DashedLineChart() { + + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const monthlyRevenue = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + return ( + + ); +} + `} + + ) +} + +export default DashedLineCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/LineChartWithReferenceLinesCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/LineChartWithReferenceLinesCode.tsx new file mode 100644 index 0000000..51b2905 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/LineChartWithReferenceLinesCode.tsx @@ -0,0 +1,75 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function LineChartWithReferenceLinesCode() { + return ( + + {` + +"use client"; +import * as React from "react"; +import { ChartContainer } from "@mui/x-charts/ChartContainer"; +import { ChartsReferenceLine } from "@mui/x-charts/ChartsReferenceLine"; +import { LinePlot, MarkPlot } from "@mui/x-charts/LineChart"; +import { ChartsXAxis } from "@mui/x-charts/ChartsXAxis"; +import { ChartsYAxis } from "@mui/x-charts/ChartsYAxis"; +import { useTheme } from "@mui/material"; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'LineChartWithReferenceLines ', +}, +]; +export default function LineChartWithReferenceLines() { + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const monthlyRevenue = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const Linecolor = theme.palette.warning.main; + + return ( + + + + + + + + + + + ); +} + + +`} + + ) +} + +export default LineChartWithReferenceLinesCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/LinewithforecastCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/LinewithforecastCode.tsx new file mode 100644 index 0000000..645f048 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/LinewithforecastCode.tsx @@ -0,0 +1,110 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function LinewithforecastCode() { + return ( + + {` +'use client' +import * as React from 'react'; +import { LineChart, AnimatedLine, AnimatedLineProps } from '@mui/x-charts/LineChart'; +import { useChartId, useDrawingArea, useXScale } from '@mui/x-charts/hooks'; + +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from "@mui/material"; +import LinewithforecastCode from '../../code/linechartscode/LinewithforecastCode'; +import { SxProps, Theme } from '@mui/system'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'LinewithforecastChart ', + }, +]; + +interface CustomAnimatedLineProps extends AnimatedLineProps { + limit?: number; + sxBefore?: SxProps; + sxAfter?: SxProps; +} + +function CustomAnimatedLine(props) { + const { limit, sxBefore, sxAfter, ...other } = props; + const { top, bottom, height, left, width } = useDrawingArea(); + const scale = useXScale(); + const chartId = useChartId(); + + if (limit === undefined) { + return ; + } + + const limitPosition = scale(limit); // Convert value to x coordinate. + + if (limitPosition === undefined) { + return ; + } + + const clipIdLeft = \`\${chartId}-\${props.ownerState.id}-line-limit-\${limit}-1\`; + const clipIdRight = \`\${chartId}-\${props.ownerState.id}-line-limit-\${limit}-2\`; + + return ( + + {/* Clip to show the line before the limit */} + + + + {/* Clip to show the line after the limit */} + + + + + + + + + + + ); +} + +export default function LinewithforecastChart() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + + return ( + \`\${v}\${i.dataIndex > 5 ? ' (estimated)' : ''}\`, + color: primary, + }, + ]} + xAxis={[{ data: [0, 1, 2, 3, 4, 5, 6, 7, 8] }]} + height={200} + width={400} + slots={{ line: CustomAnimatedLine }} + slotProps={{ line: { limit: 5, sxAfter: { strokeDasharray: '10 5' } } as any }} + /> + ); +} +`} + + ) +} + +export default LinewithforecastCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/SimpleLineCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/SimpleLineCode.tsx new file mode 100644 index 0000000..ff3cb43 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/SimpleLineCode.tsx @@ -0,0 +1,55 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function SimpleLineCode() { + return ( + + {` + +'use client' + +import { LineChart } from '@mui/x-charts/LineChart'; +import { useTheme } from "@mui/material"; + + const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'SimpleLineChart ', + }, +]; +function SimpleLineChart() { + + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const monthlyRevenue = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + return ( + + + + + ) +} + +export default SimpleLineChart +`} + + ) +} + +export default SimpleLineCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/TinyLineCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/TinyLineCode.tsx new file mode 100644 index 0000000..a52f1df --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/linechartscode/TinyLineCode.tsx @@ -0,0 +1,53 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function TinyLineChart() { + return ( + + {` +'use client'; +; +import { useTheme } from '@mui/material'; +import { ChartContainer, LinePlot, MarkPlot } from '@mui/x-charts'; + +const BCrumb = [ + { to: '/', title: 'Home' }, + { title: 'TinyLineChart' }, +]; + +function TinyLineChart() { + const pData = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = [ + 'Page A', + 'Page B', + 'Page C', + 'Page D', + 'Page E', + 'Page F', + 'Page G', + ]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + + return ( + + + + + ); +} + +export default TinyLineChart; +`} + + ) +} + +export default TinyLineChart diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/BasicPieCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/BasicPieCode.tsx new file mode 100644 index 0000000..400c14e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/BasicPieCode.tsx @@ -0,0 +1,54 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function BasicPieCode() { + return ( + + {` +'use client' +import * as React from 'react'; +import { PieChart } from '@mui/x-charts/PieChart'; +import { useTheme } from '@mui/material'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'BasicPieChart ', +}, +]; + + +export default function BasicPieChart() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const Datacolor = theme.palette.error.main; + return ( + + + + + ); +} + `} + + ) +} + +export default BasicPieCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/OnSeriesItemClickCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/OnSeriesItemClickCode.tsx new file mode 100644 index 0000000..3778619 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/OnSeriesItemClickCode.tsx @@ -0,0 +1,89 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function OnSeriesItemClickCode() { + return ( + + {` +import * as React from 'react'; +import { PieChart } from '@mui/x-charts/PieChart'; +import Typography from '@mui/material/Typography'; +import Stack from '@mui/material/Stack'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'OnSeriesItemClickChart ', +}, +]; + +const items = [ + { value: 10, label: 'Series A ( no Id )', color: '#CCDA4E' }, + { id: 'id_B', value: 15, label: 'Series B', color: '#0074BA' }, + { id: 'id_C', value: 20, label: 'Series C', color: '#01C0C8' }, +]; + +const formatObject = (obj: null) => { + if (obj === null) { + return ' undefined'; + } + return JSON.stringify(obj, null, 2) + .split('\n') + .map((l) => {l}) + .join('\n'); +}; + export default function OnSeriesItemClickChart() { + const [identifier, setIdentifier] = React.useState(null); + const [id, setId] = React.useState(undefined); + + const handleClick = (event: any, itemIdentifier: any, item: any) => { + setId(item.id); + setIdentifier(itemIdentifier); + }; + + + return ( + + + + + {\`item id: \${id ?? 'undefined'} + + item identifier: + \${formatObject(identifier)}\`} + + + + + + ); +} + + + `} + + ) +} + +export default OnSeriesItemClickCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/PieChartWithCenterLabelCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/PieChartWithCenterLabelCode.tsx new file mode 100644 index 0000000..9f224c5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/PieChartWithCenterLabelCode.tsx @@ -0,0 +1,69 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function PieChartWithCenterLabelCode() { + return ( + + {` +import * as React from 'react'; +import { PieChart } from '@mui/x-charts/PieChart'; +import { useDrawingArea } from '@mui/x-charts/hooks'; +import { styled } from '@mui/material/styles'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'PieChartWithCenterLabelChart ', +}, +]; + + +const data = [ + { value: 5, label: 'A', color: '#5D87FF' }, + { value: 10, label: 'B', color: '#0074BA' }, + { value: 15, label: 'C', color: '#01C0C8' }, + { value: 20, label: 'D', color: '#CCDA4E' }, +]; + +const size = { + width: 400, + height: 200, +}; + +const StyledText = styled('text')(({ theme }) => ({ + fill: theme.palette.text.primary, + textAnchor: 'middle', + dominantBaseline: 'central', + fontSize: 20, +})); + +function PieCenterLabel({ children }: any) { + const { width, height, left, top } = useDrawingArea(); + return ( + + {children} + + ); +} + +export default function PieChartWithCenterLabelChart() { + return ( + + + + Center label + + + ); +} + + + `} + + ) +} + +export default PieChartWithCenterLabelCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/PieChartWithCustomizedLabelCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/PieChartWithCustomizedLabelCode.tsx new file mode 100644 index 0000000..3cca62c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/PieChartWithCustomizedLabelCode.tsx @@ -0,0 +1,68 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function PieChartWithCustomizedLabelCode() { + return ( + + {` +import * as React from 'react'; +import { PieChart, pieArcLabelClasses } from '@mui/x-charts/PieChart'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'PieChartWithCustomizedLabel ', +}, +]; + +const data = [ + { label: 'Group A', value: 400, color: '#5D87FF' }, + { label: 'Group B', value: 300, color: '#0074BA' }, + { label: 'Group C', value: 300, color: '#01C0C8' }, + { label: 'Group D', value: 200, color: '#CCDA4E' }, +]; + +const sizing = { + margin: { right: 5 }, + width: 200, + height: 200, + legend: { hidden: true }, +}; +const TOTAL = data.map((item) => item.value).reduce((a, b) => a + b, 0); + +const getArcLabel = (params: { value: number; }) => { + const percent = params.value / TOTAL; + return {(percent * 100).toFixed(0)}%; +}; + + export default function PieChartWithCustomizedLabel() { + return ( + + + + ); +} + `} + + ) +} + +export default PieChartWithCustomizedLabelCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/PieChartWithPaddingAngleCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/PieChartWithPaddingAngleCode.tsx new file mode 100644 index 0000000..e93f868 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/PieChartWithPaddingAngleCode.tsx @@ -0,0 +1,77 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function PieChartWithPaddingAngleCode() { + return ( + + {` +import * as React from 'react'; +import Stack from '@mui/material/Stack'; +import { PieChart } from '@mui/x-charts/PieChart'; +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'PieChartWithPaddingAngleChart ', +}, +]; + + +const data = [ + { label: 'Group A', value: 400, color: "#5D87FF" }, + { label: 'Group B', value: 300, color: "#FA896B" }, + { label: 'Group C', value: 300, color: "#FFCD56" }, + { label: 'Group D', value: 200, color: "#95CFD5" }, +]; + +export default function PieChartWithPaddingAngleChart() { + return ( + + + + + + + + ); +} + + `} + + ) +} + +export default PieChartWithPaddingAngleCode \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/StraightAnglePieCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/StraightAnglePieCode.tsx new file mode 100644 index 0000000..deff1e2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/StraightAnglePieCode.tsx @@ -0,0 +1,50 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function StraightAnglePieCode() { + return ( + + {` +import * as React from 'react'; +import { PieChart } from '@mui/x-charts/PieChart'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'StraightAnglePieChart ', +}, +]; + const data = [ + { label: 'Group A', value: 400, color: "#5D87FF" }, + { label: 'Group B', value: 300, color: "#0074BA" }, + { label: 'Group C', value: 300, color: "#01C0C8" }, + { label: 'Group D', value: 200, color: "#CCDA4E" }, + { label: 'Group E', value: 278, color: "#FB9678" }, + { label: 'Group F', value: 189, color: "#47D7BC" }, + ]; + + export default function StraightAnglePieChart() { + + return ( + + + ) +} + `} + + + ) +} +export default StraightAnglePieCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/TwoLevelPieCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/TwoLevelPieCode.tsx new file mode 100644 index 0000000..ab87c05 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/TwoLevelPieCode.tsx @@ -0,0 +1,77 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function TwoLevelPieCode() { + return ( + + {` +import React from "react"; +import ParentCard from 'src/components/shared/ParentCard'; +import TwoLevelPieCode from "../code/piechartcode/TwoLevelPieCode"; +import { PieChart } from "@mui/x-charts/PieChart"; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'TwoLevelPieChart ', +}, +]; + + +function TwoLevelPieChart() { + const data1 = [ + { label: "Group A", value: 400, color: "#5D87FF" }, + { label: "Group B", value: 300, color: "#0074BA" }, + { label: "Group C", value: 300, color: "#763EBD" }, + { label: "Group D", value: 200, color: "#0A7EA4" }, + ]; + const data2 = [ + { label: "A1", value: 100, color: "#01C0C8" }, + { label: "A2", value: 300, color: "#FA896B" }, + { label: "B1", value: 100, color: "#01C0C8" }, + { label: "B2", value: 80, color: "#0074BA" }, + { label: "B3", value: 40, color: "#49BEFF" }, + { label: "B4", value: 30, color: "#47D7BC" }, + { label: "B5", value: 50, color: "#FFCD56" }, + { label: "C1", value: 100, color: "#95CFD5" }, + { label: "C2", value: 200, color: "#CCDA4E" }, + { label: "D1", value: 150, color: "#0A7EA4" }, + { label: "D2", value: 50, color: "#FB9678" }, + ]; + + return ( + + + + ); + } + + export default TwoLevelPieChart; + +`} + + ) +} + +export default TwoLevelPieCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/TwoSimplePieCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/TwoSimplePieCode.tsx new file mode 100644 index 0000000..dfa3fa5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/piechartcode/TwoSimplePieCode.tsx @@ -0,0 +1,73 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function TwoSimplePieCode() { + return ( + + {` +import * as React from 'react'; +import { PieChart } from '@mui/x-charts/PieChart'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'TwoSimplePieChart ', +}, +]; + +const data1 = [ + { label: 'Group A', value: 400, color: "#5D87FF" }, + { label: 'Group B', value: 300, color: "#0074BA" }, + { label: 'Group C', value: 300, color: "#763EBD" }, + { label: 'Group D', value: 200, color: "#0A7EA4" }, + { label: 'Group E', value: 278, color: "#01C0C8" }, + { label: 'Group F', value: 189, color: "#FA896B" }, +]; + +const data2 = [ + { label: 'Group A', value: 2400, color: "#01C0C8" }, + { label: 'Group B', value: 4567, color: "#0074BA" }, + { label: 'Group C', value: 1398, color: "#49BEFF" }, + { label: 'Group D', value: 9800, color: "#47D7BC" }, + { label: 'Group E', value: 3908, color: "#FFCD56" }, + { label: 'Group F', value: 4800, color: "#95CFD5" }, +]; + + +export default function TwoSimplePieChart() { + return ( + + + + + ); +} + `} + + ) +} + +export default TwoSimplePieCode \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/BasicScatterCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/BasicScatterCode.tsx new file mode 100644 index 0000000..1556fd9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/BasicScatterCode.tsx @@ -0,0 +1,219 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function BasicScatterCode() { + return ( + + {` +import * as React from 'react'; +import { ScatterChart } from '@mui/x-charts/ScatterChart'; +import { useTheme } from "@mui/material"; + + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'BasicScatterChart ', +}, +]; + +const data = [ + { + id: 'data-0', + x1: 329.39, + x2: 391.29, + y1: 443.28, + y2: 153.9, + }, + { + id: 'data-1', + x1: 96.94, + x2: 139.6, + y1: 110.5, + y2: 217.8, + }, + { + id: 'data-2', + x1: 336.35, + x2: 282.34, + y1: 175.23, + y2: 286.32, + }, + { + id: 'data-3', + x1: 159.44, + x2: 384.85, + y1: 195.97, + y2: 325.12, + }, + { + id: 'data-4', + x1: 188.86, + x2: 182.27, + y1: 351.77, + y2: 144.58, + }, + { + id: 'data-5', + x1: 143.86, + x2: 360.22, + y1: 43.253, + y2: 146.51, + }, + { + id: 'data-6', + x1: 202.02, + x2: 209.5, + y1: 376.34, + y2: 309.69, + }, + { + id: 'data-7', + x1: 384.41, + x2: 258.93, + y1: 31.514, + y2: 236.38, + }, + { + id: 'data-8', + x1: 256.76, + x2: 70.571, + y1: 231.31, + y2: 440.72, + }, + { + id: 'data-9', + x1: 143.79, + x2: 419.02, + y1: 108.04, + y2: 20.29, + }, + { + id: 'data-10', + x1: 103.48, + x2: 15.886, + y1: 321.77, + y2: 484.17, + }, + { + id: 'data-11', + x1: 272.39, + x2: 189.03, + y1: 120.18, + y2: 54.962, + }, + { + id: 'data-12', + x1: 23.57, + x2: 456.4, + y1: 366.2, + y2: 418.5, + }, + { + id: 'data-13', + x1: 219.73, + x2: 235.96, + y1: 451.45, + y2: 181.32, + }, + { + id: 'data-14', + x1: 54.99, + x2: 434.5, + y1: 294.8, + y2: 440.9, + }, + { + id: 'data-15', + x1: 134.13, + x2: 383.8, + y1: 121.83, + y2: 273.52, + }, + { + id: 'data-16', + x1: 12.7, + x2: 270.8, + y1: 287.7, + y2: 346.7, + }, + { + id: 'data-17', + x1: 176.51, + x2: 119.17, + y1: 134.06, + y2: 74.528, + }, + { + id: 'data-18', + x1: 65.05, + x2: 78.93, + y1: 104.5, + y2: 150.9, + }, + { + id: 'data-19', + x1: 162.25, + x2: 63.707, + y1: 413.07, + y2: 26.483, + }, + { + id: 'data-20', + x1: 68.88, + x2: 150.8, + y1: 74.68, + y2: 333.2, + }, + { + id: 'data-21', + x1: 95.29, + x2: 329.1, + y1: 360.6, + y2: 422.0, + }, + { + id: 'data-22', + x1: 390.62, + x2: 10.01, + y1: 330.72, + y2: 488.06, + }, +]; + +export default function BasicScatterChart() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + return ( + + + ({ x: v.x1, y: v.y1, id: v.id })), + color: primary + }, + { + label: 'Series B', + data: data.map((v) => ({ x: v.x1, y: v.y2, id: v.id })), + color: secondary + }, + ]} + /> + + ); +} + +`} + + ) +} + +export default BasicScatterCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/ScatterClickNoSnapCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/ScatterClickNoSnapCode.tsx new file mode 100644 index 0000000..c37d619 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/ScatterClickNoSnapCode.tsx @@ -0,0 +1,162 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function ScatterClickNoSnapCode() { + return ( + + {` +import * as React from 'react'; +import Stack from '@mui/material/Stack'; +import Box from '@mui/material/Box'; +import Typography from '@mui/material/Typography'; +import IconButton from '@mui/material/IconButton'; +import UndoOutlinedIcon from '@mui/icons-material/UndoOutlined'; +import { ScatterChart } from '@mui/x-charts/ScatterChart'; +import { Light as SyntaxHighlighter } from "react-syntax-highlighter"; +import { docco } from "react-syntax-highlighter/dist/esm/styles/hljs"; +import { useTheme } from '@mui/material'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'ScatterClickNoSnapChart ', +}, +]; + + + + + +export default function ScatterClickNoSnapChart() { + + const theme = useTheme(); + const primaryColor = theme.palette.primary.main; + const secondaryColor = theme.palette.secondary.main; + + const scatterChartsParams = { + + series: [ + { + id: 'series-1', + type: 'scatter', + data: [ + { x: 6.5e-2, y: -1.3, id: 0 }, + { x: -2.1, y: -7.0e-1, id: 1 }, + { x: -7.6e-1, y: -6.7e-1, id: 2 }, + { x: -1.5e-2, y: -2.0e-1, id: 3 }, + { x: -1.4, y: -9.9e-1, id: 4 }, + { x: -1.1, y: -1.5, id: 5 }, + { x: -7.0e-1, y: -2.7e-1, id: 6 }, + { x: -5.1e-1, y: -8.8e-1, id: 7 }, + { x: -4.0e-3, y: -1.4, id: 8 }, + { x: -1.3, y: -2.2, id: 9 }, + ], + label: 'A', + highlightScope: { + highlight: 'item', + }, + color: primaryColor, + }, + { + id: 'series-2', + type: 'scatter', + data: [ + { x: 1.8, y: -1.7e-2, id: 0 }, + { x: 7.1e-1, y: 2.6e-1, id: 1 }, + { x: -1.2, y: 9.8e-1, id: 2 }, + { x: 2.0, y: -2.0e-1, id: 3 }, + { x: 9.4e-1, y: -2.7e-1, id: 4 }, + { x: -4.8e-1, y: -1.6e-1, id: 5 }, + { x: -1.5, y: 1.1, id: 6 }, + { x: 1.3, y: 3.4e-1, id: 7 }, + { x: -4.2e-1, y: 1.0e-1, id: 8 }, + { x: 5.4e-2, y: 4.0e-1, id: 9 }, + ], + label: 'B', + highlightScope: { + highlight: 'item', + }, + color: secondaryColor, + }, + ] as any[], + height: 400, + }; + const [data, setData] = React.useState(); + + const { axis, item, ...other } = data ?? {}; + const dataDisplayed = data && { + ...(item + ? { + item: { + dataIndex: item.dataIndex, + series: { + id: item.series.id, + toReplace: '', + }, + }, + } + : undefined), + ...(axis ? { axis } : undefined), + ...other, + }; + + const formattedCode = dataDisplayed + ? JSON.stringify(dataDisplayed, null, 1).replace( + '"toReplace": ""', + '// ... (entire series definition)' // Replace part of the code + ) + : '// The data will appear here'; + + return ( + + + + setData(d)} + /> + + + + Click on the chart + { + setData(null); + }} + > + + + + + {formattedCode} + + + + + ); +} + + + `} + + ) +} + +export default ScatterClickNoSnapCode \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/ScatterDatasetCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/ScatterDatasetCode.tsx new file mode 100644 index 0000000..5af5663 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/ScatterDatasetCode.tsx @@ -0,0 +1,129 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function ScatterDatasetCode() { + return ( + + {` +import * as React from 'react'; +import { ScatterChart } from '@mui/x-charts/ScatterChart'; +import { axisClasses } from '@mui/x-charts/ChartsAxis'; +import { useTheme } from "@mui/material"; +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'ScatterDataset ', +}, +]; + +const dataset = [ + { + version: 'data-0', + a1: 329.39, + a2: 391.29, + b1: 443.28, + b2: 153.9, + }, + { + version: 'data-1', + a1: 96.94, + a2: 139.6, + b1: 110.5, + b2: 217.8, + }, + { + version: 'data-2', + a1: 336.35, + a2: 282.34, + b1: 175.23, + b2: 286.32, + }, + { + version: 'data-3', + a1: 159.44, + a2: 384.85, + b1: 195.97, + b2: 325.12, + }, + { + version: 'data-4', + a1: 188.86, + a2: 182.27, + b1: 351.77, + b2: 144.58, + }, + { + version: 'data-5', + a1: 143.86, + a2: 360.22, + b1: 43.253, + b2: 146.51, + }, + { + version: 'data-6', + a1: 202.02, + a2: 209.5, + b1: 376.34, + b2: 309.69, + }, + { + version: 'data-7', + a1: 384.41, + a2: 258.93, + b1: 31.514, + b2: 236.38, + }, + { + version: 'data-8', + a1: 256.76, + a2: 70.571, + b1: 231.31, + b2: 440.72, + }, + { + version: 'data-9', + a1: 143.79, + a2: 419.02, + b1: 108.04, + b2: 20.29, + }, +]; + +const chartSetting = { + + sx: { + [\`.\${axisClasses.left} .\${axisClasses.label}\`]: { + transform: 'translate(-20px, 0)', + }, + }, + + height: 300, +}; + +export default function ScatterDataset() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + return ( + + + + ); +} + + `} + + ) +} + +export default ScatterDatasetCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/VoronoiInteractionCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/VoronoiInteractionCode.tsx new file mode 100644 index 0000000..bf0ca0f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/scatterchartscode/VoronoiInteractionCode.tsx @@ -0,0 +1,136 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function VoronoiInteractionCode() { + return ( + + {` +import * as React from 'react'; +import Stack from '@mui/material/Stack'; +import FormControlLabel from '@mui/material/FormControlLabel'; +import Checkbox from '@mui/material/Checkbox'; +import Typography from '@mui/material/Typography'; +import Slider from '@mui/material/Slider'; +import { ScatterChart } from '@mui/x-charts/ScatterChart'; +import { useTheme } from "@mui/material"; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'VoronoiInteractionChart ', +}, +]; + +const data = [ + { x1: 529.39, y1: 643.28, x2: 191.29, y2: -46.1, id: 'data-0' }, + { x1: 296.94, y1: 310.5, x2: -60.4, y2: 17.8, id: 'data-1' }, + { x1: 536.35, y1: 375.23, x2: 82.34, y2: 86.32, id: 'data-2' }, + { x1: 359.44, y1: 395.97, x2: 184.85, y2: 125.12, id: 'data-3' }, + { x1: 388.86, y1: 551.77, x2: -17.73, y2: -55.42, id: 'data-4' }, + { x1: 343.86, y1: 243.25, x2: 160.22, y2: -53.49, id: 'data-5' }, + { x1: 402.02, y1: 576.34, x2: 9.5, y2: 109.69, id: 'data-6' }, + { x1: 584.41, y1: 231.51, x2: 58.93, y2: 36.38, id: 'data-7' }, + { x1: 456.76, y1: 431.31, x2: -129.43, y2: 240.72, id: 'data-8' }, + { x1: 343.79, y1: 308.04, x2: 219.02, y2: -179.71, id: 'data-9' }, + { x1: 303.48, y1: 521.77, x2: -184.11, y2: 284.17, id: 'data-10' }, + { x1: 472.39, y1: 320.18, x2: -10.97, y2: -145.04, id: 'data-11' }, + { x1: 223.57, y1: 566.2, x2: 256.4, y2: 218.5, id: 'data-12' }, + { x1: 419.73, y1: 651.45, x2: 35.96, y2: -18.68, id: 'data-13' }, + { x1: 254.99, y1: 494.8, x2: 234.5, y2: 240.9, id: 'data-14' }, + { x1: 334.13, y1: 321.83, x2: 183.8, y2: 73.52, id: 'data-15' }, + { x1: 212.7, y1: 487.7, x2: 70.8, y2: 146.7, id: 'data-16' }, + { x1: 376.51, y1: 334.06, x2: -80.83, y2: -125.47, id: 'data-17' }, + { x1: 265.05, y1: 304.5, x2: -121.07, y2: -49.1, id: 'data-18' }, + { x1: 362.25, y1: 613.07, x2: -136.29, y2: -173.52, id: 'data-19' }, + { x1: 268.88, y1: 274.68, x2: -49.2, y2: 133.2, id: 'data-20' }, + { x1: 295.29, y1: 560.6, x2: 129.1, y2: 222, id: 'data-21' }, + { x1: 590.62, y1: 530.72, x2: -189.99, y2: 288.06, id: 'data-22' }, + ]; + + export default function VoronoiInteractionChart() { + const [voronoiMaxRadius, setVoronoiMaxRadius] = React.useState(25); + const [disableVoronoi, setDisableVoronoi] = React.useState(false); + const [undefinedRadius, setUndefinedRadius] = React.useState(true); + + const handleMaxRadiusChange = (event: any, newValue: any) => { + if (typeof newValue !== 'number') { + return; + } + setVoronoiMaxRadius(newValue); + }; + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + return ( + + + + ({ x: v.x1, y: v.y1, id: v.id })), + color: primary + }, + { + label: 'Series B', + data: data.map((v) => ({ x: v.x2, y: v.y2, id: v.id })), + color: secondary + }, + ]} + /> +
+ + max radius + + +
+ + setDisableVoronoi(event.target.checked)} + /> + } + label="disableVoronoi" + labelPlacement="end" + /> + setUndefinedRadius(event.target.checked)} + /> + } + label="undefined radius" + labelPlacement="end" + /> + +
+ + ); + } + + `} +
+ ) +} + +export default VoronoiInteractionCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/sparklinecode/AreaSparkLineCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/sparklinecode/AreaSparkLineCode.tsx new file mode 100644 index 0000000..ab370db --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/sparklinecode/AreaSparkLineCode.tsx @@ -0,0 +1,51 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function AreaSparkLineCode() { + return ( + + {` + + import * as React from 'react'; + import Stack from '@mui/material/Stack'; + import Box from '@mui/material/Box'; + import { SparkLineChart } from '@mui/x-charts/SparkLineChart'; + import { useTheme } from '@mui/material'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'AreaSparkLineChart ', +}, +]; + +export default function AreaSparkLineChart() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + return ( + + + + + + + + + + ); + } +`} + + ) +} + +export default AreaSparkLineCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/sparklinecode/BasicSparkLineCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/sparklinecode/BasicSparkLineCode.tsx new file mode 100644 index 0000000..5416628 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/sparklinecode/BasicSparkLineCode.tsx @@ -0,0 +1,54 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function BasicSparkLineCode() { + return ( + + {` + +import Stack from '@mui/material/Stack'; +import Box from '@mui/material/Box'; +import { SparkLineChart } from '@mui/x-charts/SparkLineChart'; +import { useTheme } from '@mui/material'; +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'BasicSparkLine ', +}, +]; + + function BasicSparkLine() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + + + return ( + + + + + + + + + + ) +} + +export default BasicSparkLine + + +`} + + ) +} + +export default BasicSparkLineCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/sparklinecode/BasicSparkLineCustomizationCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/sparklinecode/BasicSparkLineCustomizationCode.tsx new file mode 100644 index 0000000..2977bb7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/code/sparklinecode/BasicSparkLineCustomizationCode.tsx @@ -0,0 +1,102 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + +function BasicSparkLineCustomizationCode() { + return ( + + {` +import * as React from 'react'; +import Stack from '@mui/material/Stack'; +import Box from '@mui/material/Box'; +import FormControlLabel from '@mui/material/FormControlLabel'; +import Switch from '@mui/material/Switch'; +import { SparkLineChart } from '@mui/x-charts/SparkLineChart'; +import { useTheme } from '@mui/material'; + + const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'BasicSparkLineCustomizationChart ', +}, +]; + + +export default function BasicSparkLineCustomizationChart() { + const [showHighlight, setShowHighlight] = React.useState(true); + const [showTooltip, setShowTooltip] = React.useState(true); + + const theme = useTheme(); + const primary = theme.palette.primary.main; + + const handleHighlightChange = (event: { target: { checked: boolean | ((prevState: boolean) => boolean); }; }) => { + setShowHighlight(event.target.checked); + }; + + const handleTooltipChange = (event: { target: { checked: boolean | ((prevState: boolean) => boolean); }; }) => { + setShowTooltip(event.target.checked); + }; + + return ( + + + + + } + label="showHighlight" + labelPlacement="end" + /> + + } + label="showTooltip" + labelPlacement="end" + /> + + + + + + + + + + + + ); +} + `} + + ) +} + +export default BasicSparkLineCustomizationCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/gaugecharts/ArcDesignChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/gaugecharts/ArcDesignChart.tsx new file mode 100644 index 0000000..40fd472 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/gaugecharts/ArcDesignChart.tsx @@ -0,0 +1,35 @@ +'use client' + +import { Gauge, gaugeClasses } from '@mui/x-charts/Gauge'; +import ParentCard from 'src/components/shared/ParentCard'; +import ArcDesignCode from '../code/gaugechartscode/ArcDesignCode'; + +const settings = { + width: 200, + height: 200, + value: 60, +}; + +export default function ArcDesignChart() { + return ( + }> + + ({ + [`& .${gaugeClasses.valueText}`]: { + fontSize: 40, + }, + [`& .${gaugeClasses.valueArc}`]: { + + fill: theme.palette.primary, + }, + [`& .${gaugeClasses.referenceArc}`]: { + fill: theme.palette.text.disabled, + }, + })} + /> + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/gaugecharts/BasicGaugesChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/gaugecharts/BasicGaugesChart.tsx new file mode 100644 index 0000000..797175f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/gaugecharts/BasicGaugesChart.tsx @@ -0,0 +1,18 @@ +'use client' + +import Stack from '@mui/material/Stack'; +import { Gauge } from '@mui/x-charts/Gauge'; +import ParentCard from 'src/components/shared/ParentCard'; +import BasicGaugesCode from '../code/gaugechartscode/BasicGaugesCode'; + +export default function BasicGaugesChart() { + return ( + }> + + + + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/gaugecharts/GaugePointerChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/gaugecharts/GaugePointerChart.tsx new file mode 100644 index 0000000..ba20b64 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/gaugecharts/GaugePointerChart.tsx @@ -0,0 +1,56 @@ +'use client' + +import { + GaugeContainer, + GaugeValueArc, + GaugeReferenceArc, + useGaugeState, +} from '@mui/x-charts/Gauge'; +import ParentCard from 'src/components/shared/ParentCard'; +import GaugePointerCode from '../code/gaugechartscode/GaugePointerCode'; + + + + +function GaugePointer() { + const { valueAngle, outerRadius, cx, cy } = useGaugeState(); + + if (valueAngle === null) { + // No value to display + return null; + } + + const target = { + x: cx + outerRadius * Math.sin(valueAngle), + y: cy - outerRadius * Math.cos(valueAngle), + }; + return ( + + + + + ); +} + +export default function GaugePointerChart() { + return ( + + }> + + + + + + + ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/AreaChartConnectNullsChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/AreaChartConnectNullsChart.tsx new file mode 100644 index 0000000..f03b1a1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/AreaChartConnectNullsChart.tsx @@ -0,0 +1,36 @@ +'use client' + +import Stack from '@mui/material/Stack'; +import { LineChart } from '@mui/x-charts/LineChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from '@mui/material'; +import AreaChartConnectNullsCode from '../../code/areachartscode/AreaChartConnectNullsCode'; + + + +export default function AreaChartConnectNulls() { + const data = [4000, 3000, 2000, null, 1890, 2390, 3490]; + const xData = ["January", "February", "March", "April", "May", "June", "July"]; + const theme = useTheme(); + const primary = theme.palette.primary.main; + + return ( + }> + + + + + + + ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/AreaChartFillByValueChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/AreaChartFillByValueChart.tsx new file mode 100644 index 0000000..8ccc6ac --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/AreaChartFillByValueChart.tsx @@ -0,0 +1,187 @@ +'use client' + +import { green, red } from '@mui/material/colors'; +import Stack from '@mui/material/Stack'; +import { useYScale, useDrawingArea } from '@mui/x-charts/hooks'; +import { LineChart, areaElementClasses } from '@mui/x-charts/LineChart'; +import { useTheme } from '@mui/material'; +import ParentCard from 'src/components/shared/ParentCard'; +import AreaChartFillByValueCode from '../../code/areachartscode/AreaChartFillByValueCode'; + + + + +function ColorSwich({ threshold, color1, color2, id }: any) { + + const { top, height, bottom } = useDrawingArea(); + const svgHeight = top + bottom + height; + + const scale = useYScale(); // You can provide the axis Id if you have multiple ones + const y0 = scale(threshold); // The coordinate of of the origine + const off = y0 !== undefined ? y0 / svgHeight : 0; + + return ( + + + + + + + ); +} + +export default function AreaChartFillByValue() { + const data = [4000, 3000, -1000, 500, -2100, -250, 3490]; + const xData = ["January", "February", "March", "April", "May", "June", "July"]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const amtDatacolor = theme.palette.error.main; + + return ( + }> + + + + + + + + + + + + + + + ); +} + +function ColorPalette({ id }: any) { + const { top, height, bottom } = useDrawingArea(); + const svgHeight = top + bottom + height; + + const scale = useYScale(); + + // Function to safely get the scale value + const safeScale = (value: number) => { + const scaledValue = scale(value); + return scaledValue !== undefined ? scaledValue : 0; + }; + + return ( + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/PercentAreaChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/PercentAreaChart.tsx new file mode 100644 index 0000000..8777bdf --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/PercentAreaChart.tsx @@ -0,0 +1,80 @@ +"use client"; + +import { LineChart } from '@mui/x-charts/LineChart'; +import { useTheme } from '@mui/material'; +import ParentCard from 'src/components/shared/ParentCard'; +import PercentAreaCode from '../../code/areachartscode/PercentAreaCode'; + + +const time = [ + new Date(2015, 1, 0), + new Date(2015, 2, 0), + new Date(2015, 3, 0), + new Date(2015, 4, 0), + new Date(2015, 5, 0), + new Date(2015, 6, 0), + new Date(2015, 7, 0), +]; +const a = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; +const b = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; +const c = [2400, 2210, 2290, 2000, 2181, 2500, 2100]; + +const getPercents = (array: any[]) => + array.map((v, index) => (100 * v) / (a[index] + b[index] + c[index])); + +export default function PercentAreaChart() { + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const amtDatacolor = theme.palette.error.main; + + return ( + }> + + + + ); +} + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/SimpleAreaChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/SimpleAreaChart.tsx new file mode 100644 index 0000000..6956de2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/SimpleAreaChart.tsx @@ -0,0 +1,45 @@ +'use client' + +import SimpleAreaCode from '../../code/areachartscode/SimpleAreaCode' +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from '@mui/material' +import { LineChart, lineElementClasses } from '@mui/x-charts/LineChart' + +export default function SimpleAreaChart() { + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490] + const xLabels = [ + 'January', + 'February', + 'March', + 'April', + 'May', + 'June', + 'July', + ] + + const theme = useTheme() + const primary = theme.palette.primary.main + + return ( + }> + + + ) +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/StackedAreaChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/StackedAreaChart.tsx new file mode 100644 index 0000000..ef48005 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/StackedAreaChart.tsx @@ -0,0 +1,48 @@ +"use client"; + + +import { LineChart, lineElementClasses } from '@mui/x-charts/LineChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from "@mui/material"; +import StackedAreaCode from '../../code/areachartscode/StackedAreaCode'; + + +export default function StackedAreaChart() { + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const monthlyRevenue = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const monthlyExpenses = [2400, 2210, 0, 2000, 2181, 2500, 2100]; + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const expDatacolor = theme.palette.error.main; + + return ( + }> + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/TinyAreaChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/TinyAreaChart.tsx new file mode 100644 index 0000000..f650cf1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/areacharts/TinyAreaChart.tsx @@ -0,0 +1,45 @@ +"use client"; + +import { ChartContainer } from '@mui/x-charts/ChartContainer'; +import { AreaPlot } from '@mui/x-charts/LineChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from '@mui/material'; +import TinyAreaCode from '../../code/areachartscode/TinyAreaCode'; + + +export default function TinyAreaChart() { + const uData = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const xLabels = [ + ' A', + ' B', + ' C', + ' D', + ' E', + ' F', + ' G', + ]; + const theme = useTheme(); + const primary = theme.palette.primary.main; + return ( + }> + + + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/BiaxialLineChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/BiaxialLineChart.tsx new file mode 100644 index 0000000..aa8f83d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/BiaxialLineChart.tsx @@ -0,0 +1,36 @@ +"use client"; + +import { LineChart } from "@mui/x-charts/LineChart"; +import BiaxialLineCode from "../../code/linechartscode/BiaxialLineCode"; +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from "@mui/material"; + +export default function BiaxialLineChart() { + + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const monthlyRevenue = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + return ( + }> + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/DashedLineChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/DashedLineChart.tsx new file mode 100644 index 0000000..fdccafc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/DashedLineChart.tsx @@ -0,0 +1,52 @@ +"use client"; + + +import { + LineChart, + lineElementClasses, + markElementClasses, +} from "@mui/x-charts/LineChart"; +import { useTheme } from "@mui/material"; +import ParentCard from "../../../shared/ParentCard"; +import DashedLineCode from "../../code/linechartscode/DashedLineCode"; + +export default function DashedLineChart() { + + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const monthlyRevenue = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + return ( + }> + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/LineChartWithReferenceLinesChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/LineChartWithReferenceLinesChart.tsx new file mode 100644 index 0000000..5bf9fe3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/LineChartWithReferenceLinesChart.tsx @@ -0,0 +1,53 @@ +"use client"; +import { ChartContainer } from "@mui/x-charts/ChartContainer"; +import { ChartsReferenceLine } from "@mui/x-charts/ChartsReferenceLine"; +import { LinePlot, MarkPlot } from "@mui/x-charts/LineChart"; +import { ChartsXAxis } from "@mui/x-charts/ChartsXAxis"; +import { ChartsYAxis } from "@mui/x-charts/ChartsYAxis"; +import ParentCard from "../../../shared/ParentCard"; +import LineChartWithReferenceLinesCode from "../../code/linechartscode/LineChartWithReferenceLinesCode"; +import { useTheme } from "@mui/material"; + +export default function LineChartWithReferenceLines() { + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const monthlyRevenue = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const Linecolor = theme.palette.warning.main; + + return ( + } + > + + + + + + + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/LinewithforecastChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/LinewithforecastChart.tsx new file mode 100644 index 0000000..0563b1b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/LinewithforecastChart.tsx @@ -0,0 +1,91 @@ + + +'use client' +import React from 'react' +import { LineChart, AnimatedLine, AnimatedLineProps } from '@mui/x-charts/LineChart'; +import { useChartId, useDrawingArea, useXScale } from '@mui/x-charts/hooks'; + +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from "@mui/material"; +import LinewithforecastCode from '../../code/linechartscode/LinewithforecastCode'; +import { SxProps, Theme } from '@mui/system'; + +interface CustomAnimatedLineProps extends AnimatedLineProps { + sx?: SxProps; + limit?: number; + sxBefore?: SxProps; + sxAfter?: SxProps; +} + + +function CustomAnimatedLine(props: CustomAnimatedLineProps) { + const { limit, sxBefore, sxAfter, ...other } = props; + const { top, bottom, height, left, width } = useDrawingArea(); + const scale = useXScale(); + const chartId = useChartId(); + + if (limit === undefined) { + return ; + } + + const limitPosition = scale(limit); // Convert value to x coordinate. + + if (limitPosition === undefined) { + return ; + } + + const clipIdleft = `${chartId}-${props.ownerState.id}-line-limit-${limit}-1`; + const clipIdRight = `${chartId}-${props.ownerState.id}-line-limit-${limit}-2`; + return ( + + {/* Clip to show the line before the limit */} + + + + {/* Clip to show the line after the limit */} + + + + + + + + + + + ); +} + +export default function LinewithforecastChart() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + + return ( + }> + `${v}${i.dataIndex > 5 ? ' (estimated)' : ''}`, + color: primary + }, + ]} + xAxis={[{ data: [0, 1, 2, 3, 4, 5, 6, 7, 8] }]} + height={200} + slots={{ line: CustomAnimatedLine }} + slotProps={{ line: { limit: 5, sxAfter: { strokeDasharray: '10 5' } } as any }} + /> + + ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/SimpleLineChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/SimpleLineChart.tsx new file mode 100644 index 0000000..3c56621 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/SimpleLineChart.tsx @@ -0,0 +1,37 @@ +'use client' + +import { LineChart } from '@mui/x-charts/LineChart'; +import { useTheme } from "@mui/material"; +import ParentCard from "../../../shared/ParentCard"; +import SimpleLineCode from '../../code/linechartscode/SimpleLineCode'; + +function SimpleLineChart() { + + + + + const monthlyProfits = [4000, 3000, 2000, 2780, 1890, 2390, 3490]; + const monthlyRevenue = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + + const xLabels = ["January", "February", "March", "April", "May", "June", "July"]; + + + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + return ( + }> + + + + ) +} + +export default SimpleLineChart diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/TinyLineChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/TinyLineChart.tsx new file mode 100644 index 0000000..bd4c339 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/linescharts/linechart/TinyLineChart.tsx @@ -0,0 +1,43 @@ +'use client' + +import { useTheme } from "@mui/material"; +import ParentCard from "../../../shared/ParentCard"; +import { ChartContainer } from '@mui/x-charts/ChartContainer'; +import { + LinePlot, + MarkPlot, +} from '@mui/x-charts/LineChart'; +import TinyLineCode from '../../code/linechartscode/TinyLineCode'; + +function TinyLineChart() { + const pData = [2400, 1398, 9800, 3908, 4800, 3800, 4300]; + const xLabels = [ + 'Page A', + 'Page B', + 'Page C', + 'Page D', + 'Page E', + 'Page F', + 'Page G', + ]; + const theme = useTheme(); + const primary = theme.palette.primary.main; + + return ( + }> + + + + + + + ) +} + +export default TinyLineChart diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/BasicPieChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/BasicPieChart.tsx new file mode 100644 index 0000000..7fc4e88 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/BasicPieChart.tsx @@ -0,0 +1,32 @@ +'use client' + +import { PieChart } from '@mui/x-charts/PieChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from '@mui/material'; +import BasicPieCode from '../code/piechartcode/BasicPieCode'; + + +export default function BasicPieChart() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const Datacolor = theme.palette.error.main; + return ( + }> + + + + ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/OnSeriesItemClickChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/OnSeriesItemClickChart.tsx new file mode 100644 index 0000000..a7f7b0f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/OnSeriesItemClickChart.tsx @@ -0,0 +1,69 @@ +'use client' +import React from 'react'; + +import { PieChart } from '@mui/x-charts/PieChart'; + +import Typography from '@mui/material/Typography'; +import Stack from '@mui/material/Stack'; +import OnSeriesItemClickCode from '../code/piechartcode/OnSeriesItemClickCode'; +import ParentCard from 'src/components/shared/ParentCard'; + +const items = [ + { value: 10, label: 'Series A ( no Id )', color: '#CCDA4E' }, + { id: 'id_B', value: 15, label: 'Series B', color: '#0074BA' }, + { id: 'id_C', value: 20, label: 'Series C', color: '#01C0C8' }, +]; + +const formatObject = (obj: null) => { + if (obj === null) { + return ' undefined'; + } + return JSON.stringify(obj, null, 2) + .split('\n') + .map((l) => ` ${l}`) + .join('\n'); +}; +export default function OnSeriesItemClickChart() { + const [identifier, setIdentifier] = React.useState(null); + const [id, setId] = React.useState(undefined); + + + const handleClick = (_event: any, itemIdentifier: any, item: any) => { + setId(item.id); + setIdentifier(itemIdentifier); + }; + + return ( + }> + + + + {`item id: ${id ?? 'undefined'} + + item identifier: + ${formatObject(identifier)}`} + + + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/PieChartWithCenterLabelChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/PieChartWithCenterLabelChart.tsx new file mode 100644 index 0000000..7c5c263 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/PieChartWithCenterLabelChart.tsx @@ -0,0 +1,46 @@ +'use client' + +import { PieChart } from '@mui/x-charts/PieChart'; +import { useDrawingArea } from '@mui/x-charts/hooks'; +import { styled } from '@mui/material/styles'; +import ParentCard from 'src/components/shared/ParentCard'; +import PieChartWithCenterLabelCode from '../code/piechartcode/PieChartWithCenterLabelCode'; + +const data = [ + { value: 5, label: 'A', color: '#5D87FF' }, + { value: 10, label: 'B', color: '#0074BA' }, + { value: 15, label: 'C', color: '#01C0C8' }, + { value: 20, label: 'D', color: '#CCDA4E' }, +]; + +const size = { + width: 400, + height: 200, +}; + +const StyledText = styled('text')(({ theme }) => ({ + fill: theme.palette.text.primary, + textAnchor: 'middle', + dominantBaseline: 'central', + fontSize: 20, +})); + +function PieCenterLabel({ children }: any) { + const { width, height, left, top } = useDrawingArea(); + return ( + + {children} + + ); +} + +export default function PieChartWithCenterLabelChart() { + return ( + }> + + + Center label + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/PieChartWithCustomizedLabel.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/PieChartWithCustomizedLabel.tsx new file mode 100644 index 0000000..89daec5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/PieChartWithCustomizedLabel.tsx @@ -0,0 +1,48 @@ +'use client' + +import { PieChart, pieArcLabelClasses } from '@mui/x-charts/PieChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import PieChartWithCustomizedLabelCode from '../code/piechartcode/PieChartWithCustomizedLabelCode' + +const data = [ + { label: 'Group A', value: 400, color: '#5D87FF' }, + { label: 'Group B', value: 300, color: '#0074BA' }, + { label: 'Group C', value: 300, color: '#01C0C8' }, + { label: 'Group D', value: 200, color: '#CCDA4E' }, +]; + +const sizing = { + margin: { right: 5 }, + width: 200, + height: 200, + legend: { hidden: true }, +}; +const TOTAL = data.map((item) => item.value).reduce((a, b) => a + b, 0); + +const getArcLabel = (params: { value: number; }) => { + const percent = params.value / TOTAL; + return `${(percent * 100).toFixed(0)}%`; +}; + +export default function PieChartWithCustomizedLabel() { + return ( + }> + + + ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/PieChartWithPaddingAngleChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/PieChartWithPaddingAngleChart.tsx new file mode 100644 index 0000000..5029943 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/PieChartWithPaddingAngleChart.tsx @@ -0,0 +1,57 @@ +'use client' + +import Stack from '@mui/material/Stack'; +import { PieChart } from '@mui/x-charts/PieChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import PieChartWithPaddingAngleCode from '../code/piechartcode/PieChartWithPaddingAngleCode'; + + +const data = [ + { label: 'Group A', value: 400, color: "#5D87FF" }, + { label: 'Group B', value: 300, color: "#FA896B" }, + { label: 'Group C', value: 300, color: "#FFCD56" }, + { label: 'Group D', value: 200, color: "#95CFD5" }, +]; + +export default function PieChartWithPaddingAngleChart() { + return ( + }> + + + + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/StraightAnglePieChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/StraightAnglePieChart.tsx new file mode 100644 index 0000000..454a04a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/StraightAnglePieChart.tsx @@ -0,0 +1,34 @@ +'use client' + +import { PieChart } from '@mui/x-charts/PieChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import StraightAnglePieCode from '../code/piechartcode/StraightAnglePieCode'; + + +export default function StraightAnglePieChart() { + + const data = [ + { label: 'Group A', value: 400, color: "#5D87FF" }, + { label: 'Group B', value: 300, color: "#0074BA" }, + { label: 'Group C', value: 300, color: "#01C0C8" }, + { label: 'Group D', value: 200, color: "#CCDA4E" }, + { label: 'Group E', value: 278, color: "#FB9678" }, + { label: 'Group F', value: 189, color: "#49BEFF" }, + ]; + + + return ( + }> + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/TwoLevelPieChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/TwoLevelPieChart.tsx new file mode 100644 index 0000000..d3dbef7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/TwoLevelPieChart.tsx @@ -0,0 +1,53 @@ +'use client' + +import ParentCard from 'src/components/shared/ParentCard'; +import TwoLevelPieCode from "../code/piechartcode/TwoLevelPieCode"; +import { PieChart } from "@mui/x-charts/PieChart"; + +function TwoLevelPieChart() { + const data1 = [ + { label: "Group A", value: 400, color: "#5D87FF" }, + { label: "Group B", value: 300, color: "#0074BA" }, + { label: "Group C", value: 300, color: "#763EBD" }, + { label: "Group D", value: 200, color: "#0A7EA4" }, + ]; + const data2 = [ + { label: "A1", value: 100, color: "#01C0C8" }, + { label: "A2", value: 300, color: "#FA896B" }, + { label: "B1", value: 100, color: "#01C0C8" }, + { label: "B2", value: 80, color: "#0074BA" }, + { label: "B3", value: 40, color: "#49BEFF" }, + { label: "B4", value: 30, color: "#47D7BC" }, + { label: "B5", value: 50, color: "#FFCD56" }, + { label: "C1", value: 100, color: "#95CFD5" }, + { label: "C2", value: 200, color: "#CCDA4E" }, + { label: "D1", value: 150, color: "#0A7EA4" }, + { label: "D2", value: 50, color: "#FB9678" }, + ]; + + return ( + }> + + + ); +} + +export default TwoLevelPieChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/TwoSimplePieChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/TwoSimplePieChart.tsx new file mode 100644 index 0000000..fd302a6 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/piecharts/TwoSimplePieChart.tsx @@ -0,0 +1,53 @@ +'use client' + +import { PieChart } from '@mui/x-charts/PieChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import TwoSimplePieCode from '../code/piechartcode/TwoSimplePieCode'; + +const data1 = [ + { label: 'Group A', value: 400, color: "#5D87FF" }, + { label: 'Group B', value: 300, color: "#0074BA" }, + { label: 'Group C', value: 300, color: "#763EBD" }, + { label: 'Group D', value: 200, color: "#0A7EA4" }, + { label: 'Group E', value: 278, color: "#01C0C8" }, + { label: 'Group F', value: 189, color: "#FA896B" }, +]; + +const data2 = [ + { label: 'Group A', value: 2400, color: "#01C0C8" }, + { label: 'Group B', value: 4567, color: "#0074BA" }, + { label: 'Group C', value: 1398, color: "#49BEFF" }, + { label: 'Group D', value: 9800, color: "#47D7BC" }, + { label: 'Group E', value: 3908, color: "#FFCD56" }, + { label: 'Group F', value: 4800, color: "#95CFD5" }, +]; + +export default function TwoSimplePieChart() { + return ( + }> + + + + ); +} + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/BasicScatterChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/BasicScatterChart.tsx new file mode 100644 index 0000000..9ef4e5d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/BasicScatterChart.tsx @@ -0,0 +1,196 @@ +'use client' + +import { ScatterChart } from '@mui/x-charts/ScatterChart'; +import BasicScatterCode from '../code/scatterchartscode/BasicScatterCode' +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from "@mui/material"; + +const data = [ + { + id: 'data-0', + x1: 329.39, + x2: 391.29, + y1: 443.28, + y2: 153.9, + }, + { + id: 'data-1', + x1: 96.94, + x2: 139.6, + y1: 110.5, + y2: 217.8, + }, + { + id: 'data-2', + x1: 336.35, + x2: 282.34, + y1: 175.23, + y2: 286.32, + }, + { + id: 'data-3', + x1: 159.44, + x2: 384.85, + y1: 195.97, + y2: 325.12, + }, + { + id: 'data-4', + x1: 188.86, + x2: 182.27, + y1: 351.77, + y2: 144.58, + }, + { + id: 'data-5', + x1: 143.86, + x2: 360.22, + y1: 43.253, + y2: 146.51, + }, + { + id: 'data-6', + x1: 202.02, + x2: 209.5, + y1: 376.34, + y2: 309.69, + }, + { + id: 'data-7', + x1: 384.41, + x2: 258.93, + y1: 31.514, + y2: 236.38, + }, + { + id: 'data-8', + x1: 256.76, + x2: 70.571, + y1: 231.31, + y2: 440.72, + }, + { + id: 'data-9', + x1: 143.79, + x2: 419.02, + y1: 108.04, + y2: 20.29, + }, + { + id: 'data-10', + x1: 103.48, + x2: 15.886, + y1: 321.77, + y2: 484.17, + }, + { + id: 'data-11', + x1: 272.39, + x2: 189.03, + y1: 120.18, + y2: 54.962, + }, + { + id: 'data-12', + x1: 23.57, + x2: 456.4, + y1: 366.2, + y2: 418.5, + }, + { + id: 'data-13', + x1: 219.73, + x2: 235.96, + y1: 451.45, + y2: 181.32, + }, + { + id: 'data-14', + x1: 54.99, + x2: 434.5, + y1: 294.8, + y2: 440.9, + }, + { + id: 'data-15', + x1: 134.13, + x2: 383.8, + y1: 121.83, + y2: 273.52, + }, + { + id: 'data-16', + x1: 12.7, + x2: 270.8, + y1: 287.7, + y2: 346.7, + }, + { + id: 'data-17', + x1: 176.51, + x2: 119.17, + y1: 134.06, + y2: 74.528, + }, + { + id: 'data-18', + x1: 65.05, + x2: 78.93, + y1: 104.5, + y2: 150.9, + }, + { + id: 'data-19', + x1: 162.25, + x2: 63.707, + y1: 413.07, + y2: 26.483, + }, + { + id: 'data-20', + x1: 68.88, + x2: 150.8, + y1: 74.68, + y2: 333.2, + }, + { + id: 'data-21', + x1: 95.29, + x2: 329.1, + y1: 360.6, + y2: 422.0, + }, + { + id: 'data-22', + x1: 390.62, + x2: 10.01, + y1: 330.72, + y2: 488.06, + }, +]; + +export default function BasicScatterChart() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + return ( + }> + + ({ x: v.x1, y: v.y1, id: v.id })), + color: primary + }, + { + label: 'Series B', + data: data.map((v) => ({ x: v.x1, y: v.y2, id: v.id })), + color: secondary + }, + ]} + /> + + ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/ScatterClickNoSnapChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/ScatterClickNoSnapChart.tsx new file mode 100644 index 0000000..6e4f6ec --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/ScatterClickNoSnapChart.tsx @@ -0,0 +1,143 @@ + +'use client' +import * as React from 'react'; +import Stack from '@mui/material/Stack'; +import Box from '@mui/material/Box'; +import Typography from '@mui/material/Typography'; +import IconButton from '@mui/material/IconButton'; +import UndoOutlinedIcon from '@mui/icons-material/UndoOutlined'; +import { ScatterChart } from '@mui/x-charts/ScatterChart'; + +import { Light as SyntaxHighlighter } from "react-syntax-highlighter"; +import { docco } from "react-syntax-highlighter/dist/esm/styles/hljs"; +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from '@mui/material'; +import ScatterClickNoSnapCode from '../code/scatterchartscode/ScatterClickNoSnapCode'; + + +export default function ScatterClickNoSnapChart() { + + const theme = useTheme(); + const primaryColor = theme.palette.primary.main; + const secondaryColor = theme.palette.secondary.main; + + const scatterChartsParams = { + + series: [ + { + id: 'series-1', + type: 'scatter', + data: [ + { x: 6.5e-2, y: -1.3, id: 0 }, + { x: -2.1, y: -7.0e-1, id: 1 }, + { x: -7.6e-1, y: -6.7e-1, id: 2 }, + { x: -1.5e-2, y: -2.0e-1, id: 3 }, + { x: -1.4, y: -9.9e-1, id: 4 }, + { x: -1.1, y: -1.5, id: 5 }, + { x: -7.0e-1, y: -2.7e-1, id: 6 }, + { x: -5.1e-1, y: -8.8e-1, id: 7 }, + { x: -4.0e-3, y: -1.4, id: 8 }, + { x: -1.3, y: -2.2, id: 9 }, + ], + label: 'A', + highlightScope: { + highlight: 'item', + }, + color: primaryColor, + }, + { + id: 'series-2', + type: 'scatter', + data: [ + { x: 1.8, y: -1.7e-2, id: 0 }, + { x: 7.1e-1, y: 2.6e-1, id: 1 }, + { x: -1.2, y: 9.8e-1, id: 2 }, + { x: 2.0, y: -2.0e-1, id: 3 }, + { x: 9.4e-1, y: -2.7e-1, id: 4 }, + { x: -4.8e-1, y: -1.6e-1, id: 5 }, + { x: -1.5, y: 1.1, id: 6 }, + { x: 1.3, y: 3.4e-1, id: 7 }, + { x: -4.2e-1, y: 1.0e-1, id: 8 }, + { x: 5.4e-2, y: 4.0e-1, id: 9 }, + ], + label: 'B', + highlightScope: { + highlight: 'item', + + }, + color: secondaryColor, + }, + ] as any[], + height: 400, + }; + const [data, setData] = React.useState(); + + const { axis, item, ...other }: any = data ?? {}; + const dataDisplayed = data && { + ...(item + ? { + item: { + dataIndex: item.dataIndex, + series: { + id: item.series.id, + toReplace: '', + }, + }, + } + : undefined), + ...(axis ? { axis } : undefined), + ...other, + }; + + + const formattedCode = dataDisplayed + ? JSON.stringify(dataDisplayed, null, 1).replace( + '"toReplace": ""', + '// ... (entire series definition)' // Replace part of the code + ) + : '// The data will appear here'; + + + return ( + }> + + + + setData(d)} + /> + + + + Click on the chart + { + setData(null); + }} + > + + + + + {formattedCode} + + + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/ScatterDatasetChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/ScatterDatasetChart.tsx new file mode 100644 index 0000000..fcee648 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/ScatterDatasetChart.tsx @@ -0,0 +1,113 @@ +'use client' + +import { ScatterChart } from '@mui/x-charts/ScatterChart'; +import { axisClasses } from '@mui/x-charts/ChartsAxis'; +import { useTheme } from "@mui/material"; +import ParentCard from 'src/components/shared/ParentCard'; +import ScatterDatasetCode from '../code/scatterchartscode/ScatterDatasetCode'; + +const dataset = [ + { + version: 'data-0', + a1: 329.39, + a2: 391.29, + b1: 443.28, + b2: 153.9, + }, + { + version: 'data-1', + a1: 96.94, + a2: 139.6, + b1: 110.5, + b2: 217.8, + }, + { + version: 'data-2', + a1: 336.35, + a2: 282.34, + b1: 175.23, + b2: 286.32, + }, + { + version: 'data-3', + a1: 159.44, + a2: 384.85, + b1: 195.97, + b2: 325.12, + }, + { + version: 'data-4', + a1: 188.86, + a2: 182.27, + b1: 351.77, + b2: 144.58, + }, + { + version: 'data-5', + a1: 143.86, + a2: 360.22, + b1: 43.253, + b2: 146.51, + }, + { + version: 'data-6', + a1: 202.02, + a2: 209.5, + b1: 376.34, + b2: 309.69, + }, + { + version: 'data-7', + a1: 384.41, + a2: 258.93, + b1: 31.514, + b2: 236.38, + }, + { + version: 'data-8', + a1: 256.76, + a2: 70.571, + b1: 231.31, + b2: 440.72, + }, + { + version: 'data-9', + a1: 143.79, + a2: 419.02, + b1: 108.04, + b2: 20.29, + }, +]; + +const chartSetting = { + + sx: { + [`.${axisClasses.left} .${axisClasses.label}`]: { + transform: 'translate(-20px, 0)', + }, + }, + + height: 300, +}; + +export default function ScatterDataset() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + return ( + }> + + + ); +} + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/VoronoiInteractionChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/VoronoiInteractionChart.tsx new file mode 100644 index 0000000..5a624ce --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/scattercharts/VoronoiInteractionChart.tsx @@ -0,0 +1,115 @@ +'use client' +import * as React from 'react'; +import Stack from '@mui/material/Stack'; +import FormControlLabel from '@mui/material/FormControlLabel'; +import Checkbox from '@mui/material/Checkbox'; +import Typography from '@mui/material/Typography'; +import Slider from '@mui/material/Slider'; +import { ScatterChart } from '@mui/x-charts/ScatterChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import VoronoiInteractionCode from '../code/scatterchartscode/VoronoiInteractionCode'; +import { useTheme } from "@mui/material"; + +const data = [ + { x1: 529.39, y1: 643.28, x2: 191.29, y2: -46.1, id: 'data-0' }, + { x1: 296.94, y1: 310.5, x2: -60.4, y2: 17.8, id: 'data-1' }, + { x1: 536.35, y1: 375.23, x2: 82.34, y2: 86.32, id: 'data-2' }, + { x1: 359.44, y1: 395.97, x2: 184.85, y2: 125.12, id: 'data-3' }, + { x1: 388.86, y1: 551.77, x2: -17.73, y2: -55.42, id: 'data-4' }, + { x1: 343.86, y1: 243.25, x2: 160.22, y2: -53.49, id: 'data-5' }, + { x1: 402.02, y1: 576.34, x2: 9.5, y2: 109.69, id: 'data-6' }, + { x1: 584.41, y1: 231.51, x2: 58.93, y2: 36.38, id: 'data-7' }, + { x1: 456.76, y1: 431.31, x2: -129.43, y2: 240.72, id: 'data-8' }, + { x1: 343.79, y1: 308.04, x2: 219.02, y2: -179.71, id: 'data-9' }, + { x1: 303.48, y1: 521.77, x2: -184.11, y2: 284.17, id: 'data-10' }, + { x1: 472.39, y1: 320.18, x2: -10.97, y2: -145.04, id: 'data-11' }, + { x1: 223.57, y1: 566.2, x2: 256.4, y2: 218.5, id: 'data-12' }, + { x1: 419.73, y1: 651.45, x2: 35.96, y2: -18.68, id: 'data-13' }, + { x1: 254.99, y1: 494.8, x2: 234.5, y2: 240.9, id: 'data-14' }, + { x1: 334.13, y1: 321.83, x2: 183.8, y2: 73.52, id: 'data-15' }, + { x1: 212.7, y1: 487.7, x2: 70.8, y2: 146.7, id: 'data-16' }, + { x1: 376.51, y1: 334.06, x2: -80.83, y2: -125.47, id: 'data-17' }, + { x1: 265.05, y1: 304.5, x2: -121.07, y2: -49.1, id: 'data-18' }, + { x1: 362.25, y1: 613.07, x2: -136.29, y2: -173.52, id: 'data-19' }, + { x1: 268.88, y1: 274.68, x2: -49.2, y2: 133.2, id: 'data-20' }, + { x1: 295.29, y1: 560.6, x2: 129.1, y2: 222, id: 'data-21' }, + { x1: 590.62, y1: 530.72, x2: -189.99, y2: 288.06, id: 'data-22' }, +]; + +export default function VoronoiInteractionChart() { + const [voronoiMaxRadius, setVoronoiMaxRadius] = React.useState(25); + const [disableVoronoi, setDisableVoronoi] = React.useState(false); + const [undefinedRadius, setUndefinedRadius] = React.useState(true); + + const handleMaxRadiusChange = (_event: any, newValue: any) => { + if (typeof newValue !== 'number') { + return; + } + setVoronoiMaxRadius(newValue); + }; + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + return ( + }> + + + ({ x: v.x1, y: v.y1, id: v.id })), + color: primary + }, + { + label: 'Series B', + data: data.map((v) => ({ x: v.x2, y: v.y2, id: v.id })), + color: secondary + }, + ]} + /> +
+ + max radius + + +
+ + setDisableVoronoi(event.target.checked)} + /> + } + label="disableVoronoi" + labelPlacement="end" + /> + setUndefinedRadius(event.target.checked)} + /> + } + label="undefined radius" + labelPlacement="end" + /> + +
+
+ ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/sparklinecharts/AreaSparkLineChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/sparklinecharts/AreaSparkLineChart.tsx new file mode 100644 index 0000000..6190853 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/sparklinecharts/AreaSparkLineChart.tsx @@ -0,0 +1,35 @@ +'use client' + +import Stack from '@mui/material/Stack'; +import Box from '@mui/material/Box'; +import { SparkLineChart } from '@mui/x-charts/SparkLineChart'; +import AreaSparkLineCode from '../code/sparklinecode/AreaSparkLineCode'; +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from '@mui/material'; + +export default function AreaSparkLineChart() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + return ( + + + + }> + + + + + + + + + + + ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/sparklinecharts/BasicSparkLine.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/sparklinecharts/BasicSparkLine.tsx new file mode 100644 index 0000000..f6453e8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/sparklinecharts/BasicSparkLine.tsx @@ -0,0 +1,37 @@ +'use client' + +import Stack from '@mui/material/Stack'; +import Box from '@mui/material/Box'; +import { SparkLineChart } from '@mui/x-charts/SparkLineChart'; +import BasicSparkLineCode from '../code/sparklinecode/BasicSparkLineCode'; +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from '@mui/material'; + + + +function BasicSparkLine() { + const theme = useTheme(); + const primary = theme.palette.primary.main; + + + return ( + }> + + + + + + + + + + + ) +} + +export default BasicSparkLine \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/sparklinecharts/BasicSparkLineCustomizationChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/sparklinecharts/BasicSparkLineCustomizationChart.tsx new file mode 100644 index 0000000..2f39f6a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muicharts/sparklinecharts/BasicSparkLineCustomizationChart.tsx @@ -0,0 +1,83 @@ + +'use client' +import * as React from 'react'; +import Stack from '@mui/material/Stack'; +import Box from '@mui/material/Box'; +import FormControlLabel from '@mui/material/FormControlLabel'; +import Switch from '@mui/material/Switch'; +import { SparkLineChart } from '@mui/x-charts/SparkLineChart'; +import ParentCard from 'src/components/shared/ParentCard'; +import { useTheme } from '@mui/material'; +import BasicSparkLineCustomizationCode from '../code/sparklinecode/BasicSparkLineCustomizationCode'; + +export default function BasicSparkLineCustomizationChart() { + const [showHighlight, setShowHighlight] = React.useState(true); + const [showTooltip, setShowTooltip] = React.useState(true); + + const theme = useTheme(); + const primary = theme.palette.primary.main; + + const handleHighlightChange = (event: { target: { checked: boolean | ((prevState: boolean) => boolean); }; }) => { + setShowHighlight(event.target.checked); + }; + + const handleTooltipChange = (event: { target: { checked: boolean | ((prevState: boolean) => boolean); }; }) => { + setShowTooltip(event.target.checked); + }; + + return ( + }> + + + + + } + label="showHighlight" + labelPlacement="end" + /> + + } + label="showTooltip" + labelPlacement="end" + /> + + + + + + + + + + + + ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ApiMethodFocusItemCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ApiMethodFocusItemCode.tsx new file mode 100644 index 0000000..9db9df1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ApiMethodFocusItemCode.tsx @@ -0,0 +1,68 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function ApiMethodFocusItemCode() { + return ( + + {` +import * as React from 'react'; +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import { useTreeViewApiRef } from '@mui/x-tree-view/hooks/useTreeViewApiRef'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'ApiMethodFocusItem ', +}, +]; + +export default function ApiMethodFocusItem() { + const apiRef = useTreeViewApiRef(); + const handleButtonClick = (event: React.SyntheticEvent) => { + apiRef.current?.focusItem(event, 'pickers'); + }; + + return ( + + +
+ +
+ + + + + + + + + + + + + + + + + + + +
+ + ); +} + + `} +
+ ) +} + +export default ApiMethodFocusItemCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ApiMethodSetItemExpansionCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ApiMethodSetItemExpansionCode.tsx new file mode 100644 index 0000000..4abcf3b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ApiMethodSetItemExpansionCode.tsx @@ -0,0 +1,78 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function ApiMethodSetItemExpansionCode() { + return ( + + {` +import * as React from 'react'; +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import { useTreeViewApiRef } from '@mui/x-tree-view/hooks'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'ApiMethodSetItemExpansion ', +}, +]; + +export default function ApiMethodSetItemExpansion() { + const apiRef = useTreeViewApiRef(); + + const handleExpandClick = (event: React.SyntheticEvent) => { + if (apiRef.current) { + apiRef.current.setItemExpansion(event, 'grid', true); + } + }; + + const handleCollapseClick = (event: React.SyntheticEvent) => { + if (apiRef.current) { + apiRef.current.setItemExpansion(event, 'grid', false); + } + }; + + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +} + + +`} + + ) +} + +export default ApiMethodSetItemExpansionCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/BasicCustomIconsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/BasicCustomIconsCode.tsx new file mode 100644 index 0000000..ddcb00c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/BasicCustomIconsCode.tsx @@ -0,0 +1,89 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function BasicCustomIconsCode() { + return ( + + {` +import * as React from 'react'; +import Box from '@mui/material/Box'; +import AddBoxIcon from '@mui/icons-material/AddBox'; +import IndeterminateCheckBoxIcon from '@mui/icons-material/IndeterminateCheckBox'; +import SvgIcon, { SvgIconOwnProps } from '@mui/material/SvgIcon'; +import { styled } from '@mui/material/styles'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem, treeItemClasses } from '@mui/x-tree-view/TreeItem'; + const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'BasicCustomIcons ', +}, +]; + + +const CustomTreeItem = styled(TreeItem)({ + [\`\& .\${treeItemClasses.iconContainer}\`]: { + '& .close': { + opacity: 0.3, + }, + }, +}); + + function CloseSquare(props: React.JSX.IntrinsicAttributes & { component: React.ElementType; } & SvgIconOwnProps & CommonProps & Omit) { + return ( + + {/* tslint:disable-next-line: max-line-length */} + + + ); +} + + export default function BasicCustomIcons() { + return ( + + + + + + + + + + + + + + + + + + + + + + ); +} + + + `} + + ) +} + +export default BasicCustomIconsCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/BasicSimpleTreeViewCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/BasicSimpleTreeViewCode.tsx new file mode 100644 index 0000000..452cda4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/BasicSimpleTreeViewCode.tsx @@ -0,0 +1,56 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function BasicSimpleTreeViewCode() { + return ( + + {` +import * as React from 'react'; +import Box from '@mui/material/Box'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'BasicSimpleTreeView ', +}, +]; + + +export default function BasicSimpleTreeView() { + return ( + + + + + + + + + + + + + + + + + + + + + + + ); +} + + `} + + ) +} + +export default BasicSimpleTreeViewCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/CheckboxSelectionCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/CheckboxSelectionCode.tsx new file mode 100644 index 0000000..d93927d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/CheckboxSelectionCode.tsx @@ -0,0 +1,54 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function CheckboxSelectionCode() { + return ( + + {` +import * as React from 'react'; +import Box from '@mui/material/Box'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'CheckboxSelection ', +}, +]; + +export default function CheckboxSelection() { + return ( + + + + + + + + + + + + + + + + + + + + ); +} + + + `} + + ) +} + +export default CheckboxSelectionCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ControlledExpansionTreeCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ControlledExpansionTreeCode.tsx new file mode 100644 index 0000000..2b4b975 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ControlledExpansionTreeCode.tsx @@ -0,0 +1,93 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function ControlledExpansionTreeCode() { + return ( + + {` +import * as React from 'react'; +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'ControlledExpansionTree ', +}, +]; + + +function ControlledExpansionTree() { + const [expandedItems, setExpandedItems] = React.useState([]); + + const handleExpandedItemsChange = (event: any, itemIds: any) => { + setExpandedItems(itemIds); + }; + + const handleExpandClick = () => { + setExpandedItems((oldExpanded: string | any[]) => + oldExpanded.length === 0 + ? [ + 'grid', + 'grid-community', + 'grid-pro', + 'grid-premium', + 'pickers', + 'pickers-community', + 'pickers-pro', + 'charts', + 'charts-community', + 'tree-view', + 'tree-view-community', + ] + : [], + ); + }; + return ( + +
+ +
+ + + + + + + + + + + + + + + + + + + +
+ + ) +} + +export default ControlledExpansionTree + `} +
+ ) +} + +export default ControlledExpansionTreeCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ControlledSelectionCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ControlledSelectionCode.tsx new file mode 100644 index 0000000..c944108 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/ControlledSelectionCode.tsx @@ -0,0 +1,98 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function ControlledSelectionCode() { + return ( + + {` +import * as React from 'react'; +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import Button from '@mui/material/Button'; + + const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'ControlledSelectiontree ', +}, +]; + + +function ControlledSelectiontree() { + const [selectedItems, setSelectedItems] = React.useState([]); + + const handleSelectedItemsChange = (event: any, ids: any) => { + setSelectedItems(ids); + }; + + const handleSelectClick = () => { + setSelectedItems((oldSelected: string | any[]) => + oldSelected.length === 0 + ? [ + 'grid', + 'grid-community', + 'grid-pro', + 'grid-premium', + 'pickers', + 'pickers-community', + 'pickers-pro', + 'charts', + 'charts-community', + 'tree-view', + 'tree-view-community', + ] + : [], + ); + }; + + return ( + + + +
+ +
+ + + + + + + + + + + + + + + + + + + +
+ + ) +} + +export default ControlledSelectiontree + + `} +
+ ) +} + +export default ControlledSelectionCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/CustomTreeItemCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/CustomTreeItemCode.tsx new file mode 100644 index 0000000..350b104 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/CustomTreeItemCode.tsx @@ -0,0 +1,109 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function CustomTreeItemCode() { + return ( + + {` +import * as React from 'react'; +import { styled } from '@mui/material/styles'; +import Box from '@mui/material/Box'; +import Avatar from '@mui/material/Avatar'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { useTreeItem2, UseTreeItem2Parameters } from '@mui/x-tree-view/useTreeItem2'; +import { + TreeItem2Content, + TreeItem2IconContainer, + TreeItem2GroupTransition, + TreeItem2Label, + TreeItem2Root, + TreeItem2Checkbox, +} from '@mui/x-tree-view/TreeItem2'; +import { TreeItem2Icon } from '@mui/x-tree-view/TreeItem2Icon'; +import { TreeItem2Provider } from '@mui/x-tree-view/TreeItem2Provider'; + + const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'CustomTreeItemView ', +}, +]; + + +const CustomTreeItemContent = styled(TreeItem2Content)(({ theme }) => ({ + padding: theme.spacing(0.5, 1), + })); + + + + const CustomTreeItem = React.forwardRef(function CustomTreeItem(props: any, ref) { + const { id, itemId, label, disabled, children, ...other } = props; + + const { + getRootProps, + getContentProps, + getIconContainerProps, + getCheckboxProps, + getLabelProps, + getGroupTransitionProps, + status, + } = useTreeItem2({ id, itemId, children, label, disabled, rootRef: ref }); + + return ( + + + + + + + + + ({ + background: theme.palette.primary.main, + width: 24, + height: 24, + fontSize: '0.8rem', + })} + > + {(label )[0]} + + + + + {children && } + + + ); + }); + + export default function CustomTreeItemView() { + return ( + + + + + + + + + + + + + + + + + ); + } + `} + + ) +} + +export default CustomTreeItemCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/MultiSelectTreeViewCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/MultiSelectTreeViewCode.tsx new file mode 100644 index 0000000..89251e1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/MultiSelectTreeViewCode.tsx @@ -0,0 +1,57 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function MultiSelectTreeViewCode() { + return ( + + {` +import * as React from 'react'; +import Box from '@mui/material/Box'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; + + const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'MultiSelectTreeView ', +}, +]; + +function MultiSelectTreeView() { + return ( + + + + + + + + + + + + + + + + + + + + + + ) +} + +export default MultiSelectTreeView + + `} + + ) +} + +export default MultiSelectTreeViewCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/TrackitemclicksTreeCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/TrackitemclicksTreeCode.tsx new file mode 100644 index 0000000..20df9f7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/code/simpletreecode/TrackitemclicksTreeCode.tsx @@ -0,0 +1,66 @@ + +import CodeDialog from "src/components/shared/CodeDialog"; + + +function TrackitemclicksTreeCode() { + return ( + + {` +import * as React from 'react'; +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; + +const BCrumb = [ +{ +to: '/', +title: 'Home', +}, +{ +title: 'TrackitemclicksTree ', +}, +]; + +function TrackitemclicksTree() { + const [lastClickedItem, setLastClickedItem] = React.useState(null); + return ( + + + + {lastClickedItem == null + ? 'No item click recorded' + : \`Last clicked item: \${lastClickedItem}\`} + + + setLastClickedItem(itemId)}> + + + + + + + + + + + + + + + + + + + + ); +} + +export default TrackitemclicksTree + `} + + ) +} + +export default TrackitemclicksTreeCode diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ApiMethodFocusItem.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ApiMethodFocusItem.tsx new file mode 100644 index 0000000..e0f3f51 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ApiMethodFocusItem.tsx @@ -0,0 +1,49 @@ +'use client' +import * as React from 'react'; +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import { useTreeViewApiRef } from '@mui/x-tree-view/hooks/useTreeViewApiRef'; +import ParentCard from 'src/components/shared/ParentCard'; +import ApiMethodFocusItemCode from '../code/simpletreecode/ApiMethodFocusItemCode'; + +export default function ApiMethodFocusItem() { + const apiRef = useTreeViewApiRef(); + const handleButtonClick = (event: React.SyntheticEvent) => { + apiRef.current?.focusItem(event, 'pickers'); + }; + + return ( + } + > + +
+ +
+ + + + + + + + + + + + + + + + + + + +
+
+ ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ApiMethodSetItemExpansion.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ApiMethodSetItemExpansion.tsx new file mode 100644 index 0000000..a740eef --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ApiMethodSetItemExpansion.tsx @@ -0,0 +1,64 @@ +'use client' +import * as React from 'react' +import Box from '@mui/material/Box' +import Stack from '@mui/material/Stack' +import Button from '@mui/material/Button' +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView' +import { TreeItem } from '@mui/x-tree-view/TreeItem' +import { useTreeViewApiRef } from '@mui/x-tree-view/hooks' +import ApiMethodSetItemExpansionCode from '../code/simpletreecode/ApiMethodSetItemExpansionCode' +import ParentCard from 'src/components/shared/ParentCard'; + +export default function ApiMethodSetItemExpansion() { + const apiRef = useTreeViewApiRef() + + const handleExpandClick = (event: React.SyntheticEvent) => { + if (apiRef.current) { + apiRef.current.setItemExpansion(event, 'grid', true) + } + } + + const handleCollapseClick = (event: React.SyntheticEvent) => { + if (apiRef.current) { + apiRef.current.setItemExpansion(event, 'grid', false) + } + } + + return ( + }> + + + + + + + + + + + + + + + + + + + + + + + + + + + ) +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/BasicCustomIcons.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/BasicCustomIcons.tsx new file mode 100644 index 0000000..9660f0d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/BasicCustomIcons.tsx @@ -0,0 +1,71 @@ +'use client' + +import Box from '@mui/material/Box'; +import AddBoxIcon from '@mui/icons-material/AddBox'; +import IndeterminateCheckBoxIcon from '@mui/icons-material/IndeterminateCheckBox'; +import SvgIcon from '@mui/material/SvgIcon'; +import { styled } from '@mui/material/styles'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem, treeItemClasses } from '@mui/x-tree-view/TreeItem'; +import ParentCard from 'src/components/shared/ParentCard'; +import BasicCustomIconsCode from '../code/simpletreecode/BasicCustomIconsCode'; + + +const CustomTreeItem = styled(TreeItem)({ + [`& .${treeItemClasses.iconContainer}`]: { + '& .close': { + opacity: 0.3, + }, + }, +}); + +function CloseSquare(props: any) { + + return ( + + {/* tslint:disable-next-line: max-line-length */} + + + ); +} + +export default function BasicCustomIcons() { + return ( + } + > + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/BasicSimpleTreeView.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/BasicSimpleTreeView.tsx new file mode 100644 index 0000000..bd77ddb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/BasicSimpleTreeView.tsx @@ -0,0 +1,36 @@ +'use client' + +import Box from "@mui/material/Box"; +import { SimpleTreeView } from "@mui/x-tree-view/SimpleTreeView"; +import { TreeItem } from "@mui/x-tree-view/TreeItem"; +import ParentCard from 'src/components/shared/ParentCard'; +import BasicSimpleTreeViewCode from "../code/simpletreecode/BasicSimpleTreeViewCode"; + +export default function BasicSimpleTreeView() { + return ( + } + > + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/CheckboxSelection.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/CheckboxSelection.tsx new file mode 100644 index 0000000..f7167de --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/CheckboxSelection.tsx @@ -0,0 +1,36 @@ +'use client' + +import Box from '@mui/material/Box'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import CheckboxSelectionCode from '../code/simpletreecode/CheckboxSelectionCode'; +import ParentCard from 'src/components/shared/ParentCard'; + +export default function CheckboxSelection() { + return ( + } + > + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ControlledExpansionTree.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ControlledExpansionTree.tsx new file mode 100644 index 0000000..ab55d1d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ControlledExpansionTree.tsx @@ -0,0 +1,76 @@ +'use client' +import * as React from 'react'; +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import ControlledExpansionTreeCode from '../code/simpletreecode/ControlledExpansionTreeCode'; +import ParentCard from 'src/components/shared/ParentCard'; + + +function ControlledExpansionTree() { + const [expandedItems, setExpandedItems] = React.useState([]); + + const handleExpandedItemsChange = (_event: any, itemIds: any) => { + setExpandedItems(itemIds); + }; + const handleExpandClick = () => { + setExpandedItems((oldExpanded: string | any[]) => + oldExpanded.length === 0 + ? [ + 'grid', + 'grid-community', + 'grid-pro', + 'grid-premium', + 'pickers', + 'pickers-community', + 'pickers-pro', + 'charts', + 'charts-community', + 'tree-view', + 'tree-view-community', + ] + : [], + ); + }; + return ( + } + > + + +
+ +
+ + + + + + + + + + + + + + + + + + + +
+
+ ) +} + +export default ControlledExpansionTree \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ControlledSelectiontree.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ControlledSelectiontree.tsx new file mode 100644 index 0000000..0127d6d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/ControlledSelectiontree.tsx @@ -0,0 +1,79 @@ +'use client' +import * as React from 'react'; +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import Button from '@mui/material/Button'; +import ControlledSelectionCode from '../code/simpletreecode/ControlledSelectionCode'; +import ParentCard from 'src/components/shared/ParentCard'; + + +function ControlledSelectiontree() { + const [selectedItems, setSelectedItems] = React.useState([]); + + const handleSelectedItemsChange = (_event: any, ids: any) => { + setSelectedItems(ids); + }; + + const handleSelectClick = () => { + setSelectedItems((oldSelected: string | any[]) => + oldSelected.length === 0 + ? [ + 'grid', + 'grid-community', + 'grid-pro', + 'grid-premium', + 'pickers', + 'pickers-community', + 'pickers-pro', + 'charts', + 'charts-community', + 'tree-view', + 'tree-view-community', + ] + : [], + ); + }; + + return ( + } + > + + +
+ +
+ + + + + + + + + + + + + + + + + + + +
+
+ ) +} + +export default ControlledSelectiontree \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/CustomTreeItemView.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/CustomTreeItemView.tsx new file mode 100644 index 0000000..f1fbd10 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/CustomTreeItemView.tsx @@ -0,0 +1,91 @@ + +'use client' +import * as React from 'react'; +import { styled } from '@mui/material/styles'; +import Box from '@mui/material/Box'; +import Avatar from '@mui/material/Avatar'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { useTreeItem2 } from '@mui/x-tree-view/useTreeItem2'; +import { + TreeItem2Content, + TreeItem2IconContainer, + TreeItem2GroupTransition, + TreeItem2Label, + TreeItem2Root, + TreeItem2Checkbox, +} from '@mui/x-tree-view/TreeItem2'; +import { TreeItem2Icon } from '@mui/x-tree-view/TreeItem2Icon'; +import { TreeItem2Provider } from '@mui/x-tree-view/TreeItem2Provider'; +import ParentCard from 'src/components/shared/ParentCard'; +import CustomTreeItemCode from '../code/simpletreecode/CustomTreeItemCode'; + +const CustomTreeItemContent = styled(TreeItem2Content)(({ theme }) => ({ + padding: theme.spacing(0.5, 1), +})); + + + +const CustomTreeItem = React.forwardRef(function CustomTreeItem(props: any, ref) { + const { id, itemId, label, disabled, children, ...other } = props; + + const { + getRootProps, + getContentProps, + getIconContainerProps, + getCheckboxProps, + getLabelProps, + getGroupTransitionProps, + status, + } = useTreeItem2({ id, itemId, children, label, disabled, rootRef: ref, ...other }); + + return ( + + + + + + + + + ({ + background: theme.palette.primary.main, + width: 24, + height: 24, + fontSize: '0.8rem', + })} + > + {(label)[0]} + + + + + {children && } + + + ); +}); + +export default function CustomTreeItemView() { + return ( + } + > + + + + + + + + + + + + + + + + ); +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/MultiSelectTreeView.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/MultiSelectTreeView.tsx new file mode 100644 index 0000000..912c850 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/MultiSelectTreeView.tsx @@ -0,0 +1,38 @@ +'use client' + +import Box from '@mui/material/Box'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import MultiSelectTreeViewCode from '../code/simpletreecode/MultiSelectTreeViewCode'; +import ParentCard from 'src/components/shared/ParentCard'; + +function MultiSelectTreeView() { + return ( + } + > + + + + + + + + + + + + + + + + + + + + + ) +} + +export default MultiSelectTreeView \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/TrackitemclicksTree.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/TrackitemclicksTree.tsx new file mode 100644 index 0000000..effa880 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/muitrees/simpletree/TrackitemclicksTree.tsx @@ -0,0 +1,48 @@ +'use client' +import * as React from 'react'; +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import TrackitemclicksTreeCode from '../code/simpletreecode/TrackitemclicksTreeCode'; +import ParentCard from 'src/components/shared/ParentCard'; + +function TrackitemclicksTree() { + const [lastClickedItem, setLastClickedItem] = React.useState(null); + return ( + } + > + + + {lastClickedItem == null + ? 'No item click recorded' + : `Last clicked item: ${lastClickedItem}`} + + + setLastClickedItem(itemId)}> + + + + + + + + + + + + + + + + + + + + ); +} + +export default TrackitemclicksTree \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/AccountTab.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/AccountTab.tsx new file mode 100644 index 0000000..2eac043 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/AccountTab.tsx @@ -0,0 +1,345 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { CardContent, Grid2 as Grid, Typography, MenuItem, Box, Avatar, Button, Stack } from '@mui/material'; + +// components +import BlankCard from '../../shared/BlankCard'; +import CustomTextField from '../../forms/theme-elements/CustomTextField'; +import CustomFormLabel from '../../forms/theme-elements/CustomFormLabel'; +import CustomSelect from '../../forms/theme-elements/CustomSelect'; + +// images +import user1 from 'src/assets/images/profile/user-1.jpg'; + +interface locationType { + value: string; + label: string; +} + +// locations +const locations: locationType[] = [ + { + value: 'us', + label: 'United States', + }, + { + value: 'uk', + label: 'United Kingdom', + }, + { + value: 'india', + label: 'India', + }, + { + value: 'russia', + label: 'Russia', + }, +]; + +// currency +const currencies: locationType[] = [ + { + value: 'us', + label: 'US Dollar ($)', + }, + { + value: 'uk', + label: 'United Kingdom (Pound)', + }, + { + value: 'india', + label: 'India (INR)', + }, + { + value: 'russia', + label: 'Russia (Ruble)', + }, +]; + +const AccountTab = () => { + const [location, setLocation] = React.useState('india'); + + const handleChange1 = (event: React.ChangeEvent) => { + setLocation(event.target.value); + }; + + // currency + const [currency, setCurrency] = React.useState('india'); + + const handleChange2 = (event: React.ChangeEvent) => { + setCurrency(event.target.value); + }; + + return ( + ( + {/* Change Profile */} + + + + + Change Profile + + Change your profile picture from here + + + + + + + + + Allowed JPG, GIF or PNG. Max size of 800K + + + + + + + {/* Change Password */} + + + + + Change Password + + To change your password please confirm here +
+ + Current Password + + + {/* 2 */} + New Password + + {/* 3 */} + Confirm Password + + +
+
+
+ {/* Edit Details */} + + + + + Personal Details + + To change your personal detail , edit and save from here +
+ + + + Your Name + + + + + {/* 2 */} + + Store Name + + + + + {/* 3 */} + + Location + + + {locations.map((option) => ( + + {option.label} + + ))} + + + + {/* 4 */} + + Currency + + + {currencies.map((option) => ( + + {option.label} + + ))} + + + + {/* 5 */} + + Email + + + + + {/* 6 */} + + Phone + + + + + {/* 7 */} + + Address + + + + +
+
+
+ + + + +
+
) + ); +}; + +export default AccountTab; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/BillsTab.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/BillsTab.tsx new file mode 100644 index 0000000..1b63197 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/BillsTab.tsx @@ -0,0 +1,225 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Avatar, + Box, + CardContent, + Grid2 as Grid, + IconButton, + Typography, + Tooltip, + Button, + Stack +} from '@mui/material'; + +// components +import BlankCard from '../../shared/BlankCard'; +import CustomTextField from '../../forms/theme-elements/CustomTextField'; +import CustomFormLabel from '../../forms/theme-elements/CustomFormLabel'; +import { IconCirclePlus, IconCreditCard, IconPackage, IconPencilMinus } from '@tabler/icons-react'; + +const BillsTab = () => { + return (<> + + + + + + Billing Information + + + + + + Business Name* + + + + + + Business Sector* + + + + + + Business Address* + + + + + + Country* + + + + + + First Name* + + + + + + Last Name* + + + + + + + + + {/* 2 */} + + + + + Current Plan : + + Executive + + + + Thanks for being a premium member and supporting our development. + + + {/* list 1 */} + + + + + + + Current Plan + + + 750.000 Monthly Visits + + + + + + + + + + + + + + + + + + + + {/* 3 */} + + + + + Payment Method + + On 26 December, 2023 + {/* list 1 */} + + + + + + + Visa + + + *****2102 + + + + + + + + + + + + If you updated your payment method, it will only be dislpayed here after your next + billing cycle. + + + + + + + + + + + ); +}; + +export default BillsTab; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/NotificationTab.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/NotificationTab.tsx new file mode 100644 index 0000000..2a89c1e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/NotificationTab.tsx @@ -0,0 +1,242 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Avatar, Box, CardContent, Grid2 as Grid, IconButton, Typography, Tooltip, Button, Stack } from '@mui/material'; + +// components +import BlankCard from '../../shared/BlankCard'; +import CustomTextField from '../../forms/theme-elements/CustomTextField'; +import CustomFormLabel from '../../forms/theme-elements/CustomFormLabel'; +import CustomSwitch from '../../forms/theme-elements/CustomSwitch'; +import { + IconArticle, + IconCheckbox, + IconClock, + IconDownload, + IconMail, + IconPlayerPause, + IconTruckDelivery, +} from '@tabler/icons-react'; + +const NotificationTab = () => { + return (<> + + + + + + Notification Preferences + + + Select the notificaitons ou would like to receive via email. Please note that you + cannot opt out of receving service messages, such as payment, security or legal + notifications. + + + Email Address* + + Required for notificaitons. + + {/* list 1 */} + + + + + + + Our newsletter + + + We'll always let you know about important changes + + + + + + + + {/* list 2 */} + + + + + + + Order Confirmation + + + You will be notified when customer order any product + + + + + + + + {/* list 3 */} + + + + + + + Order Status Changed + + + You will be notified when customer make changes to the order + + + + + + + + {/* list 4 */} + + + + + + + Order Delivered + + + You will be notified once the order is delivered + + + + + + + + {/* list 5 */} + + + + + + + Email Notification + + + Turn on email notificaiton to get updates through email + + + + + + + + + + + {/* 2 */} + + + + + Date & Time + + + Time zones and calendar display settings. + + + {/* list 1 */} + + + + + + + Time zone + + + (UTC + 02:00) Athens, Bucharet + + + + + + + + + + + + + + + {/* 3 */} + + + + + Ignore Tracking + + + {/* list 1 */} + + + + + + + Ignore Browser Tracking + + + Browser Cookie + + + + + + + + + + + + + + + ); +}; + +export default NotificationTab; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/SecurityTab.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/SecurityTab.tsx new file mode 100644 index 0000000..930957f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/account-setting/SecurityTab.tsx @@ -0,0 +1,169 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Avatar, + Box, + CardContent, + Grid2 as Grid, + IconButton, + Typography, + Button, + Divider, + Stack +} from '@mui/material'; + +// components +import BlankCard from '../../shared/BlankCard'; +import { IconDeviceLaptop, IconDeviceMobile, IconDotsVertical } from '@tabler/icons-react'; + +const SecurityTab = () => { + return (<> + + + + + + Two-factor Authentication + + + + Lorem ipsum, dolor sit amet consectetur adipisicing elit. Corporis sapiente sunt + earum officiis laboriosam ut. + + + + + + + {/* list 1 */} + + + Authentication App + + Google auth app + + + + + + + + {/* list 2 */} + + + Another e-mail + + E-mail to send verification link + + + + + + + + {/* list 3 */} + + + SMS Recovery + + Your phone number or something + + + + + + + + + + + + + + + + + + Devices + + + Lorem ipsum dolor sit amet consectetur adipisicing elit Rem. + + + + {/* list 1 */} + + + + + iPhone 14 + + London UK, Oct 23 at 1:15 AM + + + + + + + + + + {/* list 2 */} + + + + + Macbook Air + + Gujarat India, Oct 24 at 3:15 AM + + + + + + + + + + + + + + + + + + + + ); +}; + +export default SecurityTab; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/faq/Questions.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/faq/Questions.tsx new file mode 100644 index 0000000..95460b5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/faq/Questions.tsx @@ -0,0 +1,92 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Typography, Accordion, AccordionSummary, AccordionDetails, Divider, Box } from '@mui/material'; +import { IconChevronDown } from '@tabler/icons-react'; + +const Questions = () => { + return ( + ( + + + Frequently asked questions + Get to know more about ready-to-use admin dashboard templates + + } + aria-controls="panel1a-content" + id="panel1a-header" + > + What is an Admin Dashboard? + + + + + Admin Dashboard is the backend interface of a website or an application that helps + to manage the website's overall content and settings. It is widely used by the site + owners to keep track of their website, make changes to their content, and more. + + + + + } + aria-controls="panel2a-content" + id="panel2a-header" + > + What should an admin dashboard template include? + + + + + Admin dashboard template should include user & SEO friendly design with a variety of + components and application designs to help create your own web application with + ease. This could include customization options, technical support and about 6 months + of future updates. + + + + + } + aria-controls="panel3a-content" + id="panel3a-header" + > + Why should I buy admin templates from AdminMart? + + + + + Adminmart offers high-quality templates that are easy to use and fully customizable. + With over 101,801 happy customers & trusted by 10,000+ Companies. AdminMart is + recognized as the leading online source for buying admin templates. + + + + + } + aria-controls="panel4a-content" + id="panel4a-header" + > + Do Adminmart offers a money back guarantee? + + + + + There is no money back guarantee in most companies, but if you are unhappy with our + product, Adminmart gives you a 100% money back guarantee. + + + + + + ) + ); +}; + +export default Questions; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/faq/StillQuestions.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/faq/StillQuestions.tsx new file mode 100644 index 0000000..b99441f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/pages/faq/StillQuestions.tsx @@ -0,0 +1,44 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Typography, AvatarGroup, Avatar, Stack, Button, Box } from '@mui/material'; + +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; + +const StillQuestions = () => { + return ( + ( + + + + + + + + + + + + Still have questions + + + Can't find the answer your're looking for ? Please chat to our friendly team. + + + + + + + ) + ); +}; + +export default StillQuestions; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/basic/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/basic/page.tsx new file mode 100644 index 0000000..7c1d872 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/basic/page.tsx @@ -0,0 +1,203 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + AvatarGroup, Grid2 as Grid +} from '@mui/material'; +import { Stack } from '@mui/system'; +import DownloadCard from 'src/components/shared/DownloadCard'; +import { basicsTableData, EnTableType } from 'src/components/tables/tableData'; + +import { + createColumnHelper, + flexRender, + getCoreRowModel, + useReactTable, +} from '@tanstack/react-table'; + + +const basics = basicsTableData; + + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor('imgsrc', { + header: () => 'Users', + cell: info => ( + + + + + {info.row.original.name} + + + {info.row.original.post} + + + + ), + }), + columnHelper.accessor('pname', { + header: () => 'Project Name', + cell: info => ( + + {info.row.original.pname} + + ), + }), + columnHelper.accessor('teams', { + header: () => 'Team', + cell: info => ( + + + {info.getValue().map((team) => ( + + {team.text} + + ))} + + + ), + }), + columnHelper.accessor('status', { + header: () => 'Status', + cell: info => ( + theme.palette.success.light + : info.getValue() === 'Pending' + ? (theme) => theme.palette.warning.light + : info.getValue() === 'Completed' + ? (theme) => theme.palette.primary.light + : info.getValue() === 'Cancel' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() === 'Active' + ? (theme) => theme.palette.success.main + : info.getValue() === 'Pending' + ? (theme) => theme.palette.warning.main + : info.getValue() === 'Completed' + ? (theme) => theme.palette.primary.main + : info.getValue() === 'Cancel' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: '8px', + }} + size="small" + label={info.getValue()} + /> + ), + }), + columnHelper.accessor('budget', { + header: () => 'Budget', + cell: info => ( + + ${info.row.original.budget} + + ), + }), +]; + +const ReactBasicTable = () => { + const [data, _setData] = React.useState(() => [...basics]); + + const table = useReactTable({ + data, + columns, + getCoreRowModel: getCoreRowModel(), + }); + + const handleDownload = () => { + const headers = ["Users", "Project Name", "Team", "Status", "Budget"]; + const rows = data.map((item: { name: any; pname: any; teams: any[]; status: any; budget: any; }) => [ + + item.name, + item.pname, + item.teams.map(team => team.text).join(", "), + item.status, + item.budget, + ]); + + const csvContent = [ + headers.join(","), + ...rows.map((e: any[]) => e.join(",")) + ].join("\n"); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement("a"); + link.href = url; + link.setAttribute("download", "table-data.csv"); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + {flexRender(cell.column.columnDef.cell, cell.getContext())} + + ))} + + ))} + +
+
+
+
+
+
) + ); +}; + +export default ReactBasicTable; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/column-visiblity/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/column-visiblity/page.tsx new file mode 100644 index 0000000..f268762 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/column-visiblity/page.tsx @@ -0,0 +1,244 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + AvatarGroup, Grid2 as Grid, + FormControlLabel, + Divider +} from '@mui/material'; +import { Stack } from '@mui/system'; + +import DownloadCard from 'src/components/shared/DownloadCard'; +import { basicsTableData, EnTableType } from 'src/components/tables/tableData'; +import { + createColumnHelper, + flexRender, + getCoreRowModel, + useReactTable, +} from '@tanstack/react-table'; +import CustomCheckbox from 'src/components/forms/theme-elements/CustomCheckbox'; + +const basics = basicsTableData; + +const columnHelper = createColumnHelper(); + + +const defaultColumns = [ + columnHelper.accessor('imgsrc', { + header: () => 'Users', + cell: info => ( + + + + + {info.row.original.name} + + + {info.row.original.post} + + + + ), + }), + columnHelper.accessor('pname', { + header: () => 'Project Name', + cell: info => ( + + {info.row.original.pname} + + ), + }), + columnHelper.accessor('teams', { + header: () => 'Team', + cell: info => ( + + + {info.getValue().map((team) => ( + + {team.text} + + ))} + + + ), + }), + columnHelper.accessor('status', { + header: () => 'Status', + cell: info => ( + theme.palette.success.light + : info.getValue() === 'Pending' + ? (theme) => theme.palette.warning.light + : info.getValue() === 'Completed' + ? (theme) => theme.palette.primary.light + : info.getValue() === 'Cancel' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() === 'Active' + ? (theme) => theme.palette.success.main + : info.getValue() === 'Pending' + ? (theme) => theme.palette.warning.main + : info.getValue() === 'Completed' + ? (theme) => theme.palette.primary.main + : info.getValue() === 'Cancel' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: '8px', + }} + size="small" + label={info.getValue()} + /> + ), + }), + columnHelper.accessor('budget', { + header: () => 'Budget', + cell: info => ( + + ${info.row.original.budget}k + + ), + }), +]; + +const ReactColumnVisibilityTable = () => { + const [data, _setData] = React.useState(() => [...basics]); + + const [columns] = React.useState(() => [ + ...defaultColumns, + ]) + const [columnVisibility, setColumnVisibility] = React.useState({}) + + + const table = useReactTable({ + data, + columns, + getCoreRowModel: getCoreRowModel(), + state: { + columnVisibility, + }, + onColumnVisibilityChange: setColumnVisibility, + }); + + const handleDownload = () => { + const headers = ["Users", "Project Name", "Team", "Status", "Budget"]; + const rows = data.map((item: { name: any; pname: any; teams: any[]; status: any; budget: any; }) => [ + + item.name, + item.pname, + item.teams.map(team => team.text).join(", "), + item.status, + item.budget, + ]); + + const csvContent = [ + headers.join(","), + ...rows.map((e: any[]) => e.join(",")) + ].join("\n"); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement("a"); + link.href = url; + link.setAttribute("download", "table-data.csv"); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + +
+ + } /> +
+ {table.getAllLeafColumns().map(column => { + return ( +
+ } label={column.id} /> +
+ ) + })} +
+ + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + {flexRender(cell.column.columnDef.cell, cell.getContext())} + + ))} + + ))} + +
+
+
+
+
+
) + ); +}; + +export default ReactColumnVisibilityTable; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/dense/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/dense/page.tsx new file mode 100644 index 0000000..cbe2f60 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/dense/page.tsx @@ -0,0 +1,289 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + Grid2 as Grid, + Button, + Divider +} from '@mui/material'; +import { Stack } from '@mui/system'; +import DownloadCard from 'src/components/shared/DownloadCard'; +import { IconCircle, IconClock } from '@tabler/icons-react'; +import { + useReactTable, + getCoreRowModel, + flexRender, + createColumnHelper, +} from '@tanstack/react-table'; +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; +import img5 from 'src/assets/images/profile/user-5.jpg'; + + +export interface EnTableType { + avatar: string; + cname: string; + tag?: string; + email: string; + teams: { + name: string; + bgcolor: string; + }[]; + status: string; +} + +const rows: EnTableType[] = [ + { + status: 'active', + avatar: img1, + tag: 'rhye', + cname: 'Olivia Rhye', + email: 'olivia@ui.com', + teams: [ + { name: 'Design', bgcolor: 'primary.main' }, + { name: 'Product', bgcolor: 'secondary.main' }, + ], + }, + { + status: 'offline', + avatar: img2, + tag: 'steele', + cname: 'Barbara Steele', + email: 'steele@ui.com', + teams: [ + { name: 'Product', bgcolor: 'secondary.main' }, + { name: 'Operations', bgcolor: 'error.main' }, + ], + }, + { + status: 'active', + avatar: img3, + tag: 'gordon', + cname: 'Leonard Gordon', + email: 'olivia@ui.com', + teams: [ + { name: 'Finance', bgcolor: 'primary.main' }, + { name: 'Customer Success', bgcolor: 'success.main' }, + ], + }, + { + status: 'offline', + avatar: img4, + tag: 'pope', + cname: 'Evelyn Pope', + email: 'steele@ui.com', + teams: [ + { name: 'Operations', bgcolor: 'error.main' }, + { name: 'Design', bgcolor: 'primary.main' }, + ], + }, + { + status: 'active', + avatar: img5, + tag: 'garza', + cname: 'Tommy Garza', + email: 'olivia@ui.com', + teams: [{ name: 'Product', bgcolor: 'secondary.main' }], + }, + { + status: 'active', + avatar: img4, + tag: 'vasquez', + cname: 'Isabel Vasquez', + email: 'steele@ui.com', + teams: [{ name: 'Customer Success', bgcolor: 'success.main' }], + }, +]; + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor('avatar', { + header: () => 'Customer', + cell: info => ( + + + + {info.row.original.cname} + + @{info.row.original.tag} + + + + ), + }), + columnHelper.accessor('status', { + header: () => 'Status', + cell: info => ( + : + } + sx={{ + backgroundColor: + info.getValue() === 'active' + ? (theme) => theme.palette.success.light + : (theme) => theme.palette.grey[100], + color: + info.getValue() === 'active' + ? (theme) => theme.palette.success.main + : (theme) => theme.palette.grey[500], + '.MuiChip-icon': { + color: 'inherit !important', + }, + }} + /> + ), + }), + columnHelper.accessor('email', { + header: () => 'Email Address', + cell: info => ( + + {info.getValue()} + + ), + }), + columnHelper.accessor('teams', { + header: () => 'Teams', + cell: info => ( + + {info.getValue().map((team, index) => ( + + ))} + + ), + }), +]; + +const ReactDenseTable = () => { + const [data] = React.useState(rows); + const [density, setDensity] = React.useState<'sm' | 'md' | 'lg'>('md'); + + const table = useReactTable({ + data, + columns, + getCoreRowModel: getCoreRowModel(), + }); + + const handleToggleDensity = () => { + setDensity(prevDensity => { + if (prevDensity === 'lg') return 'md'; + if (prevDensity === 'md') return 'sm'; + return 'lg'; + }); + }; + + const handleDownload = () => { + const headers = ["Customer", "Status", "Email Address", "Teams"]; + const rows = data.map(item => [ + item.cname, + item.status, + item.email, + item.teams.map(team => team.name).join(", "), + ]); + + const csvContent = [ + headers.join(","), + ...rows.map(e => e.join(",")) + ].join("\n"); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement("a"); + link.href = url; + link.setAttribute("download", "table-data.csv"); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + {flexRender(cell.column.columnDef.cell, cell.getContext())} + + ))} + + ))} + +
+
+
+
+
+
) + ); +}; +export default ReactDenseTable; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/drag-drop/Columndragdrop.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/drag-drop/Columndragdrop.tsx new file mode 100644 index 0000000..59212a9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/drag-drop/Columndragdrop.tsx @@ -0,0 +1,300 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + AvatarGroup, + Grid2 as Grid, + IconButton, +} from '@mui/material'; +import { Stack } from '@mui/system'; +import { + DndContext, + KeyboardSensor, + MouseSensor, + TouchSensor, + closestCenter, + useSensor, + useSensors, +} from '@dnd-kit/core'; +import { SortableContext, horizontalListSortingStrategy, useSortable } from '@dnd-kit/sortable'; +import DownloadCard from 'src/components/shared/DownloadCard'; +import { basicsTableData, EnTableType } from 'src/components/tables/tableData'; +import { CSS } from '@dnd-kit/utilities'; +import { + createColumnHelper, + flexRender, + getCoreRowModel, + useReactTable, +} from '@tanstack/react-table'; +import { IconGripHorizontal } from '@tabler/icons-react'; + +const basics = basicsTableData; + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor('imgsrc', { + id: 'imgsrc', + header: () => 'Users', + cell: (info) => ( + + + + + {info.row.original.name} + + + {info.row.original.post} + + + + ), + }), + columnHelper.accessor('pname', { + id: 'pname', + header: () => 'Project Name', + cell: (info) => ( + + {info.row.original.pname} + + ), + }), + columnHelper.accessor('teams', { + id: 'teams', + header: () => 'Team', + cell: (info) => ( + + + {info.getValue().map((team) => ( + + {team.text} + + ))} + + + ), + }), + columnHelper.accessor('status', { + id: 'status', + header: () => 'Status', + cell: (info) => ( + theme.palette.success.light + : info.getValue() === 'Pending' + ? (theme) => theme.palette.warning.light + : info.getValue() === 'Completed' + ? (theme) => theme.palette.primary.light + : info.getValue() === 'Cancel' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() === 'Active' + ? (theme) => theme.palette.success.main + : info.getValue() === 'Pending' + ? (theme) => theme.palette.warning.main + : info.getValue() === 'Completed' + ? (theme) => theme.palette.primary.main + : info.getValue() === 'Cancel' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: '8px', + }} + size="small" + label={info.getValue()} + /> + ), + }), + columnHelper.accessor('budget', { + id: 'budget', + header: () => 'Budget', + cell: (info) => ${info.row.original.budget}, + }), +]; + +const arrayMove = (array: any, from: any, to: any) => { + const item = array[from]; + const newArray = array.slice(); + newArray.splice(from, 1); + newArray.splice(to, 0, item); + return newArray; +}; +const DraggableTableHeader = ({ header }: any) => { + const { attributes, isDragging, listeners, setNodeRef, transform } = useSortable({ + id: header.id, + }); + + const style: any = { + opacity: isDragging ? 0.8 : 1, + position: 'relative', + transform: CSS.Translate.toString(transform), + transition: 'width transform 0.2s ease-in-out', + whiteSpace: 'nowrap', + width: header.column.getSize(), + zIndex: isDragging ? 1 : 0, + textAlign: 'left', + padding: '0 16px', + }; + + return ( + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + + + + + ); +}; +const DragAlongCell = ({ cell }: any) => { + const { isDragging, setNodeRef, transform } = useSortable({ + id: cell.column.id, + }); + + const style: any = { + opacity: isDragging ? 0.8 : 1, + position: 'relative', + transform: CSS.Translate.toString(transform), + transition: 'width transform 0.2s ease-in-out', + width: cell.column.getSize(), + zIndex: isDragging ? 1 : 0, + + }; + + return ( + + {flexRender(cell.column.columnDef.cell, cell.getContext())} + + ); +}; + +const Columndragdrop = () => { + const [data, _setData] = React.useState(() => [...basics]); + const [columnOrder, setColumnOrder] = React.useState(columns.map((c) => c.id)); + + const table = useReactTable({ + data, + columns, + state: { + columnOrder, + }, + onColumnOrderChange: setColumnOrder, + getCoreRowModel: getCoreRowModel(), + debugColumns: true, + debugTable: true, + debugHeaders: true, + }); + + const handleDragEnd = (event: { active: any; over: any }) => { + const { active, over } = event; + if (active && over && active.id !== over.id) { + setColumnOrder((columnOrder: string | any[]) => { + const oldIndex = columnOrder.indexOf(active.id); + const newIndex = columnOrder.indexOf(over.id); + return arrayMove(columnOrder, oldIndex, newIndex); + }); + } + }; + + const sensors = useSensors( + useSensor(MouseSensor, {}), + useSensor(TouchSensor, {}), + useSensor(KeyboardSensor, {}), + ); + + const handleDownload = () => { + const headers = ['Users', 'Project Name', 'Team', 'Status', 'Budget']; + const rows = data.map( + (item: { name: any; pname: any; teams: any[]; status: any; budget: any }) => [ + item.name, + item.pname, + item.teams.map((team) => team.text).join(', '), + item.status, + item.budget, + ], + ); + + const csvContent = [headers.join(','), ...rows.map((e: any[]) => e.join(','))].join('\n'); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement('a'); + link.href = url; + link.setAttribute('download', 'table-data.csv'); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + + {headerGroup.headers.map((header) => ( + + ))} + + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + + + ))} + + ))} + +
+
+
+
+
+
+
) + ); +}; + +export default Columndragdrop; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/drag-drop/Rowdragdrop.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/drag-drop/Rowdragdrop.tsx new file mode 100644 index 0000000..2e1fd1e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/drag-drop/Rowdragdrop.tsx @@ -0,0 +1,260 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + AvatarGroup, + Grid2 as Grid, +} from '@mui/material'; +import { Stack } from '@mui/system'; +import DownloadCard from 'src/components/shared/DownloadCard'; +import { basicsTableData, EnTableType } from 'src/components/tables/tableData'; +import { + DndContext, + MouseSensor, + TouchSensor, + KeyboardSensor, + closestCenter, + useSensor, + useSensors, +} from '@dnd-kit/core'; +import { + SortableContext, + useSortable, + verticalListSortingStrategy, + arrayMove, +} from '@dnd-kit/sortable'; +import { CSS } from '@dnd-kit/utilities'; + +import { + createColumnHelper, + flexRender, + getCoreRowModel, + useReactTable, +} from '@tanstack/react-table'; +import { IconGripVertical } from '@tabler/icons-react'; + +const basics = basicsTableData; + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor('dragHandle', { + cell: () => ( + + + + ), + header: () => , + }), + + columnHelper.accessor('imgsrc', { + header: () => 'Users', + cell: (info) => ( + + + + + {info.row.original.name} + + + {info.row.original.post} + + + + ), + }), + columnHelper.accessor('pname', { + header: () => 'Project Name', + cell: (info) => ( + + {info.row.original.pname} + + ), + }), + columnHelper.accessor('teams', { + header: () => 'Team', + cell: (info) => ( + + + {info.getValue().map((team) => ( + + {team.text} + + ))} + + + ), + }), + columnHelper.accessor('status', { + header: () => 'Status', + cell: (info) => ( + theme.palette.success.light + : info.getValue() === 'Pending' + ? (theme) => theme.palette.warning.light + : info.getValue() === 'Completed' + ? (theme) => theme.palette.primary.light + : info.getValue() === 'Cancel' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() === 'Active' + ? (theme) => theme.palette.success.main + : info.getValue() === 'Pending' + ? (theme) => theme.palette.warning.main + : info.getValue() === 'Completed' + ? (theme) => theme.palette.primary.main + : info.getValue() === 'Cancel' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: '8px', + }} + size="small" + label={info.getValue()} + /> + ), + }), + columnHelper.accessor('budget', { + header: () => 'Budget', + cell: (info) => ${info.row.original.budget}k, + }), +]; + +const DraggableRow = ({ row }: any) => { + const { attributes, listeners, setNodeRef, transform, transition } = useSortable({ + id: row.original.id, + }); + + const style: any = { + transform: CSS.Translate.toString(transform), + transition, + cursor: 'move', + }; + + return ( + + {row.getVisibleCells().map((cell: any) => ( + + {flexRender(cell.column.columnDef.cell, cell.getContext())} + + ))} + + ); +}; + +const Rowdragdrop = () => { + const [data, _setData] = React.useState(() => [...basics]); + + const table = useReactTable({ + data, + columns, + getCoreRowModel: getCoreRowModel(), + }); + const handleDragEnd = (event: { active: any; over: any }) => { + const { active, over } = event; + if (active.id !== over?.id) { + _setData((prevData: any[]) => { + const oldIndex = prevData.findIndex((item) => item.id === active.id); + const newIndex = prevData.findIndex((item) => item.id === over?.id); + return arrayMove(prevData, oldIndex, newIndex); + }); + } + }; + + const sensors = useSensors( + useSensor(MouseSensor), + useSensor(TouchSensor), + useSensor(KeyboardSensor), + ); + + const handleDownload = () => { + const headers = ['Users', 'Project Name', 'Team', 'Status', 'Budget']; + const rows = data.map( + (item: { name: any; pname: any; teams: any[]; status: any; budget: any }) => [ + item.name, + item.pname, + item.teams.map((team: { text: any }) => team.text).join(', '), + item.status, + item.budget, + ], + ); + + const csvContent = [headers.join(','), ...rows.map((e: any[]) => e.join(','))].join('\n'); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement('a'); + link.href = url; + link.setAttribute('download', 'table-data.csv'); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + + + ))} + + ))} + + + row.id)} + strategy={verticalListSortingStrategy} + > + {table.getRowModel().rows.map((row) => ( + + ))} + + +
+
+
+
+
+
+
) + ); +}; +export default Rowdragdrop; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/drag-drop/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/drag-drop/page.tsx new file mode 100644 index 0000000..523dd1c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/drag-drop/page.tsx @@ -0,0 +1,33 @@ + +import Rowdragdrop from './Rowdragdrop'; +import Columndragdrop from './Columndragdrop'; +import Grid from '@mui/material/Grid2'; +import PageContainer from 'src/components/container/PageContainer'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Drag & Drop React Table', + }, +]; + +function page() { + return ( + ( + + + + + + + + + + ) + ); +} +export default page; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/editable/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/editable/page.tsx new file mode 100644 index 0000000..c5ebedb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/editable/page.tsx @@ -0,0 +1,371 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + Grid2 as Grid, MenuItem, + Button, + Divider, + IconButton, + TextField, + Select +} from '@mui/material'; +import { Stack } from '@mui/system'; +import DownloadCard from 'src/components/shared/DownloadCard'; +import EditIcon from '@mui/icons-material/Edit'; +import CheckIcon from '@mui/icons-material/Check'; +import CloseIcon from '@mui/icons-material/Close'; + +import { + flexRender, + getCoreRowModel, + useReactTable, + createColumnHelper +} from '@tanstack/react-table' +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; +import img5 from 'src/assets/images/profile/user-5.jpg'; +import img6 from 'src/assets/images/profile/user-6.jpg'; + + +export interface EditableDataType { + id?: number; + status?: string; + avatar?: string; + name?: string; + project?: string; + percent?: number; + edit?: any; +} + +export const basicsTableData: EditableDataType[] = [ + { + id: 1, + status: 'active', + avatar: img1, + name: 'Olivia Rhye', + project: 'Xtreme admin', + percent: 60, + + }, + { + id: 2, + status: 'cancel', + avatar: img2, + name: 'Barbara Steele', + project: 'Adminpro admin', + percent: 30, + + }, + { + id: 3, + status: 'pending', + avatar: img3, + name: 'Isabel Vasquez', + project: 'Modernize admin', + percent: 32, + + }, + { + id: 4, + status: 'active', + avatar: img4, + name: 'Olivia Rhye', + project: 'Xtreme admin', + percent: 60, + + }, + { + id: 5, + status: 'cancel', + avatar: img5, + name: 'Barbara Steele', + project: 'Adminpro admin', + percent: 30, + + }, + { + id: 6, + status: 'active', + avatar: img6, + name: 'Leonard Gordon', + project: 'Monster admin', + percent: 45, + + }, + { + id: 7, + status: 'pending', + avatar: img4, + name: 'Evelyn Pope', + project: 'Materialpro admin', + percent: 37, + + }, + { + id: 8, + status: 'active', + avatar: img6, + name: 'Leonard Gordon', + project: 'Monster admin', + percent: 45, + + }, + { + id: 9, + status: 'pending', + avatar: img5, + name: 'Evelyn Pope', + project: 'Materialpro admin', + percent: 37, + }, + { + id: 10, + status: 'cancel', + avatar: img1, + name: 'Tommy Garza', + project: 'Elegant admin', + percent: 87, + }, + +]; + +const statusOptions = [ + { value: "active", label: "Active" }, + { value: "cancel", label: "Cancel" }, + { value: "pending", label: "Pending" }, +]; + +const columnHelper = createColumnHelper(); + +const columns = [ + + columnHelper.accessor('name', { + header: () => 'User', + cell: info => ( + + + + {info.getValue()} + + + ), + }), + columnHelper.accessor('project', { + header: () => 'Project Name', + cell: info => ( + + {info.getValue()} + + ), + }), + + columnHelper.accessor('status', { + header: () => 'Status', + meta: { + filterVariant: 'select', + }, + cell: info => ( + theme.palette.success.light + : info.getValue() === 'pending' + ? (theme) => theme.palette.warning.light + : info.getValue() === 'completed' + ? (theme) => theme.palette.primary.light + : info.getValue() === 'cancel' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() === 'active' + ? (theme) => theme.palette.success.main + : info.getValue() === 'pending' + ? (theme) => theme.palette.warning.main + : info.getValue() === 'completed' + ? (theme) => theme.palette.primary.main + : info.getValue() === 'cancel' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: '8px', + }} + label={info.getValue()} + /> + ), + }), + columnHelper.accessor('edit', { + header: () => 'edit', + cell: ({ row }) => ( + + ), + }), +]; + +const EditableTable = () => { + const [data, _setData] = React.useState(() => [...basicsTableData]); + const [editRowId, setEditRowId] = React.useState(null); + const [editedData, setEditedData] = React.useState(null); + + + const table = useReactTable({ + data, + columns, + getCoreRowModel: getCoreRowModel(), + }); + + //edit + const handleEdit = (row: any) => { + setEditRowId(row.id); + setEditedData({ ...row }); + }; + + const handleSave = () => { + if (editedData) { + _setData( + data.map((item) => (item.id === editedData.id ? editedData : item)) + ); + setEditRowId(null); + setEditedData(null); + } + }; + + const handleChange = (e: (Event & { target: { value: any; name: string; }; }) | React.ChangeEvent, field: string) => { + if (editedData) { + setEditedData({ + ...editedData, + [field]: e.target.value, + }); + } + }; + + const handleDownload = () => { + const headers = ["Users", "Project Name", "Status", "percent"]; + const rows = data.map(item => [ + item.name, + item.project, + item.status, + item.percent, + ]); + + const csvContent = [ + headers.join(","), + ...rows.map(e => e.join(",")) + ].join("\n"); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement("a"); + link.href = url; + link.setAttribute("download", "table-data.csv"); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + return ( + ( + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + {cell.column.id === "edit" ? ( + editRowId === row.original.id ? ( + <> + + + + setEditRowId(null)} color="error"> + + + + ) : ( + handleEdit(row.original)} color="primary"> + + + ) + ) : editRowId === row.original.id ? ( + cell.column.id === "status" ? ( + + ) : ( + + handleChange( + e, + cell.column.id + ) + } + fullWidth + /> + ) + ) : ( + flexRender(cell.column.columnDef.cell, cell.getContext()) + )} + + ))} + + ))} + +
+
+ +
+
+
+
) + ); +}; +export default EditableTable; + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/empty/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/empty/page.tsx new file mode 100644 index 0000000..ab7b197 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/empty/page.tsx @@ -0,0 +1,180 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Typography, + TableHead, + Box, + Grid2 as Grid, + FormLabel +} from '@mui/material'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; + +import DownloadCard from 'src/components/shared/DownloadCard'; + +import { + createColumnHelper, + flexRender, + getCoreRowModel, + useReactTable, +} from '@tanstack/react-table'; +import { TableType } from 'src/components/tables/tableData'; +import EmptyImage from 'src/assets/images/svgs/no-data.webp'; + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor('imgsrc', { + header: () => 'Users' + }), + columnHelper.accessor('name', { + header: () => ' Name', + }), + columnHelper.accessor('post', { + header: () => 'Post', + }), + columnHelper.accessor('pname', { + header: () => 'Project Name', + }), + columnHelper.accessor('teams', { + header: () => 'Teams', + }), + columnHelper.accessor('status', { + header: () => 'Status', + }), + columnHelper.accessor('budget', { + header: () => 'Budget', + }), +]; + +const EmptyTable = () => { + const [data, _setData] = React.useState(() => []); + + const table = useReactTable({ + data, + columns, + getCoreRowModel: getCoreRowModel(), + }); + + const handleDownload = () => { + const headers = ["Users", "Project Name", "Team", "Status", "Budget"]; + const rows = data.map((item: { name: any; pname: any; teams: any[]; status: any; budget: any; }) => [ + + item.name, + item.pname, + item.teams.map(team => team.text).join(", "), + item.status, + item.budget, + ]); + + const csvContent = [ + headers.join(","), + ...rows.map((e: any[]) => e.join(",")) + ].join("\n"); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement("a"); + link.href = url; + link.setAttribute("download", "table-data.csv"); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : ( + <> + {flexRender(header.column.columnDef.header, header.getContext())} + + + )} + + + ))} + + ))} + + + + + + No data + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + + + ))} + + ))} + +
+
+
+
+
+
) + ); +}; + +export default EmptyTable; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/expanding/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/expanding/page.tsx new file mode 100644 index 0000000..b1de0d9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/expanding/page.tsx @@ -0,0 +1,301 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + AvatarGroup, Grid2 as Grid +} from '@mui/material'; +import { Stack } from '@mui/system'; +import DownloadCard from 'src/components/shared/DownloadCard'; +import { basicsTableData, EnTableType } from 'src/components/tables/tableData'; +import { + createColumnHelper, + flexRender, + getCoreRowModel, + useReactTable, +} from '@tanstack/react-table'; +import KeyboardArrowRightIcon from '@mui/icons-material/KeyboardArrowRight'; +import KeyboardArrowDownIcon from '@mui/icons-material/KeyboardArrowDown'; + + + +const basics = basicsTableData; + + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor("actions", { + cell: ({ row }) => ( + row.toggleExpanded()}> + {row.getIsExpanded() ? ( + + ) : ( + + )} + + ), + header: () => , + }), + columnHelper.accessor("imgsrc", { + header: () => "Users", + cell: (info) => ( + + + + + {info.row.original.name} + + + {info.row.original.post} + + + + ), + }), + columnHelper.accessor("pname", { + header: () => "Project Name", + cell: (info) => ( + + {info.row.original.pname} + + ), + }), + columnHelper.accessor("teams", { + header: () => "Team", + cell: (info) => ( + + + {info.getValue().map((team) => ( + + {team.text} + + ))} + + + ), + }), + columnHelper.accessor("status", { + header: () => "Status", + cell: (info) => ( + theme.palette.success.light + : info.getValue() === "Pending" + ? (theme) => theme.palette.warning.light + : info.getValue() === "Completed" + ? (theme) => theme.palette.primary.light + : info.getValue() === "Cancel" + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() === "Active" + ? (theme) => theme.palette.success.main + : info.getValue() === "Pending" + ? (theme) => theme.palette.warning.main + : info.getValue() === "Completed" + ? (theme) => theme.palette.primary.main + : info.getValue() === "Cancel" + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: "8px", + }} + size="small" + label={info.getValue()} + /> + ), + }), + columnHelper.accessor("budget", { + header: () => "Budget", + cell: (info) => ( + ${info.row.original.budget} + ), + }), +]; + +const TableExpanding = () => { + const [data, _setData] = React.useState(() => [...basics]); + + const table = useReactTable({ + data, + columns, + getCoreRowModel: getCoreRowModel(), + }); + + const handleDownload = () => { + const headers = ["Users", "Project Name", "Team", "Status", "Budget"]; + const rows = data.map( + (item: { + name: any; + pname: any; + teams: any[]; + status: any; + budget: any; + }) => [ + item.name, + item.pname, + item.teams.map((team) => team.text).join(", "), + item.status, + item.budget, + ] + ); + + const csvContent = [ + headers.join(","), + ...rows.map((e: any[]) => e.join(",")), + ].join("\n"); + + const blob = new Blob([csvContent], { type: "text/csv;charset=utf-8;" }); + const url = URL.createObjectURL(blob); + + const link = document.createElement("a"); + link.href = url; + link.setAttribute("download", "table-data.csv"); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender( + header.column.columnDef.header, + header.getContext() + )} + + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + + {row.getVisibleCells().map((cell) => ( + + {flexRender( + cell.column.columnDef.cell, + cell.getContext() + )} + + ))} + + {row.getIsExpanded() ? ( + + + + + Details: + + + Avatar: + + + + Name: {row.original.name} + Post: {row.original.post} + Project Name: {row.original.pname} + Status: + theme.palette.success.light + : row.original.status === 'Pending' + ? (theme) => theme.palette.warning.light + : row.original.status === 'Completed' + ? (theme) => theme.palette.primary.light + : row.original.status === 'Cancel' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + row.original.status === 'Active' + ? (theme) => theme.palette.success.main + : row.original.status === 'Pending' + ? (theme) => theme.palette.warning.main + : row.original.status === 'Completed' + ? (theme) => theme.palette.primary.main + : row.original.status === 'Cancel' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: '8px', + }} + label={row.original.status} + /> + + + Teams: + + {row.original.teams.map((team) => ( + + {team.text} + + ))} + + + + Budget: ${row.original.budget} + + + + + ) : null} + + ))} + +
+
+
+
+
+
) + ); +}; +export default TableExpanding; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/filter/FilterTableData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/filter/FilterTableData.ts new file mode 100644 index 0000000..1b273dc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/filter/FilterTableData.ts @@ -0,0 +1,169 @@ +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; +import img5 from 'src/assets/images/profile/user-5.jpg'; + +export interface BasicsTableDataType { + id: string; + invoiceno: string; + imgsrc: string; + name: string; + post: string; + pname: string; + status: string; + progress: number; +} + +export const basicsTableData: BasicsTableDataType[] = [ + { + id: '1', + invoiceno: '3066', + imgsrc: img1, + name: 'Sunil Joshi', + post: 'Web Designer', + pname: 'Elite Admin', + status: 'Paid', + progress: 60, + }, + { + id: '2', + invoiceno: '3067', + imgsrc: img2, + name: 'Andrew McDownland', + post: 'Project Manager', + pname: 'Real Homes WP Theme', + status: 'Cancelled', + progress: 30, + }, + { + id: '3', + invoiceno: '3068', + imgsrc:img3, + name: 'Christopher Jamil', + post: 'Project Manager', + pname: 'MedicalPro WP Theme', + status: 'Refunded', + progress: 45, + }, + { + id: '4', + invoiceno: '3069', + imgsrc: img4, + name: 'Nirav Joshi', + post: 'Frontend Engineer', + pname: 'Hosting Press HTML', + status: 'Paid', + progress: 15, + }, + { + id: '5', + invoiceno: '3070', + imgsrc: img5, + name: 'Micheal Doe', + post: 'Content Writer', + pname: 'Helping Hands WP Theme', + status: 'Cancel', + progress: 20, + }, + { + id: '6', + invoiceno: '3071', + imgsrc:img1, + name: 'Sunil Joshi', + post: 'Web Designer', + pname: 'Elite Admin', + status: 'Paid', + progress: 65, + }, + { + id: '7', + invoiceno: '3072', + imgsrc:img2, + name: 'Andrew McDownland', + post: 'Project Manager', + pname: 'Real Homes WP Theme', + status: 'Cancelled', + progress: 45, + }, + { + id: '8', + invoiceno: '3073', + imgsrc: img3, + name: 'Christopher Jamil', + post: 'Project Manager', + pname: 'MedicalPro WP Theme', + status: 'Refunded', + progress: 54, + }, + { + id: '9', + invoiceno: '3074', + imgsrc: img4, + name: 'Nirav Joshi', + post: 'Frontend Engineer', + pname: 'Hosting Press HTML', + status: 'Paid', + progress: 86, + }, + { + id: '10', + invoiceno: '3075', + imgsrc: img5, + name: 'Sunil Joshi', + post: 'Web Designer', + pname: 'Elite Admin', + status: 'Paid', + progress: 23, + }, + { + id: '11', + invoiceno: '3076', + imgsrc: img2, + name: 'Micheal Doe', + post: 'Content Writer', + pname: 'Helping Hands WP Theme', + status: 'Cancel', + progress: 20, + }, + { + id: '12', + invoiceno: '3077', + imgsrc: img1, + name: 'Nirav Joshi', + post: 'Frontend Engineer', + pname: 'Hosting Press HTML', + status: 'Paid', + progress: 29, + }, + { + id: '13', + invoiceno: '3078', + imgsrc: img2, + name: 'Andrew McDownland', + post: 'Project Manager', + pname: 'Real Homes WP Theme', + status: 'Cancelled', + progress: 78, + }, + { + id: '14', + invoiceno: '3079', + imgsrc:img3, + name: 'Christopher Jamil', + post: 'Project Manager', + pname: 'MedicalPro WP Theme', + status: 'Refunded', + progress: 61, + }, + { + id: '15', + invoiceno: '3080', + imgsrc: img4, + name: 'Micheal Doe', + post: 'Content Writer', + pname: 'Helping Hands WP Theme', + status: 'Cancel', + progress: 89, + }, +]; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/filter/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/filter/page.tsx new file mode 100644 index 0000000..f00e9f3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/filter/page.tsx @@ -0,0 +1,386 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + Grid2 as Grid, + MenuItem, + Button, + Divider, + IconButton, + LinearProgress, + TextFieldProps, +} from '@mui/material'; +import { Stack } from '@mui/system'; +import DownloadCard from 'src/components/shared/DownloadCard'; +import { basicsTableData, BasicsTableDataType } from './FilterTableData'; + +import { + flexRender, + getCoreRowModel, + getFilteredRowModel, + getPaginationRowModel, + getSortedRowModel, + useReactTable, + createColumnHelper, +} from '@tanstack/react-table'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; +import { + IconChevronLeft, + IconChevronRight, + IconChevronsLeft, + IconChevronsRight, + IconArrowBackUp, + IconCheck, + IconX, +} from '@tabler/icons-react'; + +const basics = basicsTableData; + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor('invoiceno', { + header: () => 'Invoice', + cell: (info) => ( + + INV- {info.getValue()} + + ), + }), + columnHelper.accessor('status', { + header: () => 'Status', + meta: { + filterVariant: 'select', + }, + cell: (info) => ( + + ) : info.getValue() == 'Cancelled' ? ( + + ) : ( + + ) + } + sx={{ + backgroundColor: + info.getValue() == 'Paid' + ? (theme) => theme.palette.primary.light + : info.getValue() == 'Cancelled' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() == 'Paid' + ? (theme) => theme.palette.primary.main + : info.getValue() == 'Cancelled' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + '.MuiChip-icon': { + color: 'inherit !important', + }, + }} + /> + ), + }), + columnHelper.accessor('name', { + header: () => 'Customer', + cell: (info) => ( + + + + + {info.getValue()} + + + {info.row.original.post} + + + + ), + }), + + columnHelper.accessor('progress', { + header: () => 'Progress', + cell: (info) => ( + + + + + + {info.getValue()}% + + + ), + }), +]; + +function Filter({ column }: any) { + const columnFilterValue = column.getFilterValue(); + const { filterVariant } = column.columnDef.meta || {}; + + return filterVariant === 'select' ? ( + column.setFilterValue(e.target.value)} + value={columnFilterValue ? columnFilterValue.toString() : ''} + > + {/* See faceted column filters example for dynamic select options */} + All + Paid + Cancelled + Refunded + + ) : ( + ( column.setFilterValue(value)} + placeholder={`Search...`} + type="text" + value={columnFilterValue || ''} + />) + // See faceted column filters example for datalist search suggestions + ); +} + +interface DebouncedInputProps extends Omit { + value: string; + onChange: (value: string) => void; + debounce?: number; +} + +const DebouncedInput: React.FC = ({ + value: initialValue, + onChange, + debounce = 500, + ...props +}) => { + const [value, setValue] = React.useState(initialValue); + + React.useEffect(() => { + setValue(initialValue); + }, [initialValue]); + + React.useEffect(() => { + const timeout = setTimeout(() => { + onChange(value); + }, debounce); + + return () => clearTimeout(timeout); + }, [value, debounce, onChange]); + + // Proper typing for the event handler + const handleChange = (e: React.ChangeEvent) => { + setValue(e.target.value); + }; + + return ( + + ); +}; + +const ReactFilterTable = () => { + const [data, _setData] = React.useState(() => [...basics]); + const [columnFilters, setColumnFilters] = React.useState([]); + const rerender = React.useReducer(() => ({}), {})[1]; + + const table = useReactTable({ + data, + columns, + filterFns: {}, + state: { + columnFilters, + }, + onColumnFiltersChange: setColumnFilters, + getCoreRowModel: getCoreRowModel(), + getFilteredRowModel: getFilteredRowModel(), //client side filtering + getSortedRowModel: getSortedRowModel(), + getPaginationRowModel: getPaginationRowModel(), + debugTable: true, + debugHeaders: true, + debugColumns: false, + }); + + const handleDownload = () => { + const headers = ['Invoice', 'Status', 'Customer', 'Progress']; + const rows = data.map((item) => [item.invoiceno, item.status, item.name, item.progress]); + + const csvContent = [headers.join(','), ...rows.map((e) => e.join(','))].join('\n'); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement('a'); + link.href = url; + link.setAttribute('download', 'table-data.csv'); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + + {header.column.getCanFilter() ? ( +
+ +
+ ) : null} +
+ ))} +
+ ))} +
+ + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + {flexRender(cell.column.columnDef.cell, cell.getContext())} + + ))} + + ))} + +
+
+ + + + + + {table.getPrePaginationRowModel().rows.length} Rows + + + + + Page + + {table.getState().pagination.pageIndex + 1} of {table.getPageCount()} + + + + | Go to page: + { + const page = e.target.value ? Number(e.target.value) - 1 : 0; + table.setPageIndex(page); + }} + /> + + { + table.setPageSize(Number(e.target.value)); + }} + > + {[10, 15, 20, 25].map((pageSize) => ( + + {pageSize} + + ))} + + + table.setPageIndex(0)} + disabled={!table.getCanPreviousPage()} + > + + + table.previousPage()} + disabled={!table.getCanPreviousPage()} + > + + + table.nextPage()} + disabled={!table.getCanNextPage()} + > + + + table.setPageIndex(table.getPageCount() - 1)} + disabled={!table.getCanNextPage()} + > + + + + +
+
+
+
) + ); +}; + +export default ReactFilterTable; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/pagination/PaginationData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/pagination/PaginationData.ts new file mode 100644 index 0000000..f8a4722 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/pagination/PaginationData.ts @@ -0,0 +1,180 @@ +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; +import img5 from 'src/assets/images/profile/user-5.jpg'; +import img6 from 'src/assets/images/profile/user-6.jpg'; + +export interface PaginationDataType { + status?: string; + avatar?: string; + name?: string; + project?: string; + percent?: number; + users:{ + img:string; + }[]; +} + +export const basicsTableData: PaginationDataType[] = [ + { + status: 'active', + avatar: img1, + name: 'Olivia Rhye', + project: 'Xtreme admin', + percent: 60, + users: [{ img: img1 }, { img: img2}], + }, + { + status: 'cancel', + avatar: img2, + name: 'Barbara Steele', + project: 'Adminpro admin', + percent: 30, + users: [ + { img: img1}, + { img: img2 }, + { img: img3 }, + ], + }, + { + status: 'pending', + avatar: img5, + name: 'Isabel Vasquez', + project: 'Modernize admin', + percent: 32, + users: [{ img: img2 }, { img: img4 }], + }, + { + status: 'active', + avatar: img1, + name: 'Olivia Rhye', + project: 'Xtreme admin', + percent: 60, + users: [{ img: img1 }, { img: img2 }], + }, + { + status: 'cancel', + avatar: img2, + name: 'Barbara Steele', + project: 'Adminpro admin', + percent: 30, + users: [ + { img: img1 }, + { img: img2}, + { img: img3 }, + ], + }, + { + status: 'active', + avatar: img3, + name: 'Leonard Gordon', + project: 'Monster admin', + percent: 45, + users: [{ img: img3 }, { img: img2}], + }, + { + status: 'pending', + avatar:img4, + name: 'Evelyn Pope', + project: 'Materialpro admin', + percent: 37, + users: [ + { img: img1 }, + { img: img2}, + { img: img5 }, + ], + }, + { + status: 'active', + avatar: img3, + name: 'Leonard Gordon', + project: 'Monster admin', + percent: 45, + users: [{ img: img3 }, { img: img2}], + }, + { + status: 'pending', + avatar:img4, + name: 'Evelyn Pope', + project: 'Materialpro admin', + percent: 37, + users: [ + { img: img1 }, + { img: img2}, + { img: img5 }, + ], + }, + { + status: 'cancel', + avatar: img5, + name: 'Tommy Garza', + project: 'Elegant admin', + percent: 87, + users: [{ img: img5 }, { img: img6 }], + }, + { + status: 'pending', + avatar: img6, + name: 'Isabel Vasquez', + project: 'Modernize admin', + percent: 32, + users: [{ img: img2}, { img:img4 }], + }, + { + status: 'active', + avatar: img1, + name: 'Olivia Rhye', + project: 'Xtreme admin', + percent: 60, + users: [{ img: img1 }, { img: img2}], + }, + { + status: 'cancel', + avatar: img2, + name: 'Barbara Steele', + project: 'Adminpro admin', + percent: 30, + users: [ + { img: img1 }, + { img: img2}, + { img: img3 }, + ], + }, + { + status: 'active', + avatar: img3, + name: 'Leonard Gordon', + project: 'Monster admin', + percent: 45, + users: [{ img: img3 }, { img: img2}], + }, + { + status: 'pending', + avatar: img4, + name: 'Evelyn Pope', + project: 'Materialpro admin', + percent: 37, + users: [ + { img: img1 }, + { img: img2}, + { img: img5 }, + ], + }, + { + status: 'cancel', + avatar: img5, + name: 'Tommy Garza', + project: 'Elegant admin', + percent: 87, + users: [{ img: img5 }, { img: img6 }], + }, + { + status: 'pending', + avatar: img6, + name: 'Isabel Vasquez', + project: 'Modernize admin', + percent: 32, + users: [{ img: img2}, { img: img4 }], + }, +]; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/pagination/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/pagination/page.tsx new file mode 100644 index 0000000..13e1048 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/pagination/page.tsx @@ -0,0 +1,310 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + Grid2 as Grid, + MenuItem, + Button, + Divider, + IconButton, + AvatarGroup, +} from '@mui/material'; +import { Stack } from '@mui/system'; +import DownloadCard from 'src/components/shared/DownloadCard'; +import { basicsTableData, PaginationDataType } from './PaginationData'; + +import { + flexRender, + getCoreRowModel, + getFilteredRowModel, + getPaginationRowModel, + getSortedRowModel, + useReactTable, + createColumnHelper, +} from '@tanstack/react-table'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; +import { + IconChevronLeft, + IconChevronRight, + IconChevronsLeft, + IconChevronsRight, +} from '@tabler/icons-react'; + +const basics = basicsTableData; + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor('name', { + header: () => 'User', + cell: (info) => ( + + + + {info.getValue()} + + + ), + }), + columnHelper.accessor('project', { + header: () => 'Project Name', + cell: (info) => ( + + {info.getValue()} + + ), + }), + columnHelper.accessor('users', { + header: () => 'Users', + cell: (info) => ( + + {info.getValue().map((user, i) => ( + + ))} + + ), + }), + columnHelper.accessor('status', { + header: () => 'Status', + meta: { + filterVariant: 'select', + }, + cell: (info) => ( + theme.palette.success.light + : info.getValue() === 'pending' + ? (theme) => theme.palette.warning.light + : info.getValue() === 'completed' + ? (theme) => theme.palette.primary.light + : info.getValue() === 'cancel' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() === 'active' + ? (theme) => theme.palette.success.main + : info.getValue() === 'pending' + ? (theme) => theme.palette.warning.main + : info.getValue() === 'completed' + ? (theme) => theme.palette.primary.main + : info.getValue() === 'cancel' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: '8px', + }} + label={info.getValue()} + /> + ), + }), +]; + +const ReactPaginationTable = () => { + const [data, _setData] = React.useState(() => [...basics]); + const [columnFilters, setColumnFilters] = React.useState([]); + const rerender = React.useReducer(() => ({}), {})[1]; + + const table = useReactTable({ + data, + columns, + filterFns: {}, + state: { + columnFilters, + }, + onColumnFiltersChange: setColumnFilters, + getCoreRowModel: getCoreRowModel(), + getFilteredRowModel: getFilteredRowModel(), //client side filtering + getSortedRowModel: getSortedRowModel(), + getPaginationRowModel: getPaginationRowModel(), + debugTable: true, + debugHeaders: true, + debugColumns: false, + }); + + const handleDownload = () => { + const headers = ['avatar', 'name', 'project', 'percent', 'status', 'users']; + const rows = data.map((item) => [ + item.name, + item.project, + item.percent, + item.status, + item.avatar, + item.users.map((user) => user.img).join(','), + ]); + + const csvContent = [headers.join(','), ...rows.map((e) => e.join(','))].join('\n'); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement('a'); + link.href = url; + link.setAttribute('download', 'table-data.csv'); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + {(() => { + const sortState = header.column.getIsSorted(); + if (sortState === 'asc') return ' 🔼'; + if (sortState === 'desc') return ' 🔽'; + return null; + })()} + + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + {flexRender(cell.column.columnDef.cell, cell.getContext())} + + ))} + + ))} + +
+
+ + + + + + {table.getPrePaginationRowModel().rows.length} Rows + + + + + Page + + {table.getState().pagination.pageIndex + 1} of {table.getPageCount()} + + + + | Go to page: + { + const page = e.target.value ? Number(e.target.value) - 1 : 0; + table.setPageIndex(page); + }} + /> + + { + table.setPageSize(Number(e.target.value)); + }} + > + {[10, 15, 20, 25].map((pageSize) => ( + + {pageSize} + + ))} + + + table.setPageIndex(0)} + disabled={!table.getCanPreviousPage()} + > + + + table.previousPage()} + disabled={!table.getCanPreviousPage()} + > + + + table.nextPage()} + disabled={!table.getCanNextPage()} + > + + + table.setPageIndex(table.getPageCount() - 1)} + disabled={!table.getCanNextPage()} + > + + + + +
+
+
+
) + ); +}; + +export default ReactPaginationTable; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/row-selection/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/row-selection/page.tsx new file mode 100644 index 0000000..a860ce9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/row-selection/page.tsx @@ -0,0 +1,269 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + AvatarGroup, + Grid2 as Grid, + CheckboxProps, +} from '@mui/material'; +import { Stack } from '@mui/system'; +import DownloadCard from 'src/components/shared/DownloadCard'; +import { basicsTableData, EnTableType } from 'src/components/tables/tableData'; +import { + createColumnHelper, + flexRender, + getCoreRowModel, + useReactTable, +} from '@tanstack/react-table'; +import CustomCheckbox from 'src/components/forms/theme-elements/CustomCheckbox'; + +const basics = basicsTableData; + +interface IndeterminateCheckboxProps extends Omit { + indeterminate?: boolean; +} + +const IndeterminateCheckbox: React.FC = ({ + indeterminate, + className = '', + ...rest +}) => { + const ref = React.useRef(null); + + React.useEffect(() => { + if (ref.current && typeof indeterminate === 'boolean') { + (ref.current as any).indeterminate = !rest.checked && indeterminate; + } + }, [indeterminate, rest.checked]); + + return ; +}; + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor("checkboxes", { + header: ({ table }) => ( + + ), + cell: ({ row }) => ( +
+ +
+ ), + }), + + columnHelper.accessor("imgsrc", { + header: () => "Users", + cell: (info) => ( + + + + + {info.row.original.name} + + + {info.row.original.post} + + + + ), + }), + columnHelper.accessor("pname", { + header: () => "Project Name", + cell: (info) => ( + + {info.row.original.pname} + + ), + }), + columnHelper.accessor("teams", { + header: () => "Team", + cell: (info) => ( + + + {info.getValue().map((team) => ( + + {team.text} + + ))} + + + ), + }), + columnHelper.accessor("status", { + header: () => "Status", + cell: (info) => ( + theme.palette.success.light + : info.getValue() === "Pending" + ? (theme) => theme.palette.warning.light + : info.getValue() === "Completed" + ? (theme) => theme.palette.primary.light + : info.getValue() === "Cancel" + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() === "Active" + ? (theme) => theme.palette.success.main + : info.getValue() === "Pending" + ? (theme) => theme.palette.warning.main + : info.getValue() === "Completed" + ? (theme) => theme.palette.primary.main + : info.getValue() === "Cancel" + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: "8px", + }} + size="small" + label={info.getValue()} + /> + ), + }), + columnHelper.accessor("budget", { + header: () => "Budget", + cell: (info) => ( + ${info.row.original.budget}k + ), + }), +]; + +const TableRowSelection = () => { + const [data, _setData] = React.useState(() => [...basics]); + + const [rowSelection, setRowSelection] = React.useState({}); + + const table = useReactTable({ + data, + columns, + getCoreRowModel: getCoreRowModel(), + enableRowSelection: true, + onRowSelectionChange: setRowSelection, + state: { + rowSelection, + }, + }); + + const handleDownload = () => { + const headers = ["Users", "Project Name", "Team", "Status", "Budget"]; + const rows = data.map( + (item: { + name: any; + pname: any; + teams: any[]; + status: any; + budget: any; + }) => [ + item.name, + item.pname, + item.teams.map((team) => team.text).join(", "), + item.status, + item.budget, + ] + ); + + const csvContent = [ + headers.join(","), + ...rows.map((e: any[]) => e.join(",")), + ].join("\n"); + + const blob = new Blob([csvContent], { type: "text/csv;charset=utf-8;" }); + const url = URL.createObjectURL(blob); + + const link = document.createElement("a"); + link.href = url; + link.setAttribute("download", "table-data.csv"); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender( + header.column.columnDef.header, + header.getContext() + )} + + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + {flexRender( + cell.column.columnDef.cell, + cell.getContext() + )} + + ))} + + ))} + +
+
+
+
+
+
) + ); +}; + +export default TableRowSelection; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/sorting/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/sorting/page.tsx new file mode 100644 index 0000000..0213ff2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/sorting/page.tsx @@ -0,0 +1,318 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + Grid2 as Grid, + MenuItem, + Button, + Divider, + IconButton, + LinearProgress, +} from '@mui/material'; +import { Stack } from '@mui/system'; +import DownloadCard from 'src/components/shared/DownloadCard'; +import { basicsTableData, BasicsTableDataType } from '../filter/FilterTableData'; + +import { + flexRender, + getCoreRowModel, + getFilteredRowModel, + getPaginationRowModel, + getSortedRowModel, + useReactTable, + createColumnHelper, +} from '@tanstack/react-table'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; +import { + IconChevronLeft, + IconChevronRight, + IconChevronsLeft, + IconChevronsRight, + IconArrowBackUp, + IconCheck, + IconX, +} from '@tabler/icons-react'; + +const basics = basicsTableData; + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor('invoiceno', { + header: () => 'Invoice', + cell: (info) => ( + + INV- {info.getValue()} + + ), + }), + columnHelper.accessor('status', { + header: () => 'Status', + meta: { + filterVariant: 'select', + }, + cell: (info) => ( + + ) : info.getValue() == 'Cancelled' ? ( + + ) : ( + + ) + } + sx={{ + backgroundColor: + info.getValue() == 'Paid' + ? (theme) => theme.palette.primary.light + : info.getValue() == 'Cancelled' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() == 'Paid' + ? (theme) => theme.palette.primary.main + : info.getValue() == 'Cancelled' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + '.MuiChip-icon': { + color: 'inherit !important', + }, + }} + /> + ), + }), + columnHelper.accessor('name', { + header: () => 'Customer', + cell: (info) => ( + + + + + {info.getValue()} + + + {info.row.original.post} + + + + ), + }), + + columnHelper.accessor('progress', { + header: () => 'Progress', + cell: (info) => ( + + + + + + {info.getValue()}% + + + ), + }), +]; + +const ReactSortingTable = () => { + const [data, _setData] = React.useState(() => [...basics]); + const [columnFilters, setColumnFilters] = React.useState([]); + const rerender = React.useReducer(() => ({}), {})[1]; + + const table = useReactTable({ + data, + columns, + filterFns: {}, + state: { + columnFilters, + }, + onColumnFiltersChange: setColumnFilters, + getCoreRowModel: getCoreRowModel(), + getFilteredRowModel: getFilteredRowModel(), //client side filtering + getSortedRowModel: getSortedRowModel(), + getPaginationRowModel: getPaginationRowModel(), + debugTable: true, + debugHeaders: true, + debugColumns: false, + }); + + const handleDownload = () => { + const headers = ['Invoice', 'Status', 'Customer', 'Progress']; + const rows = data.map((item) => [item.invoiceno, item.status, item.name, item.progress]); + + const csvContent = [headers.join(','), ...rows.map((e) => e.join(','))].join('\n'); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement('a'); + link.href = url; + link.setAttribute('download', 'table-data.csv'); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + {(() => { + const sortState = header.column.getIsSorted(); + if (sortState === 'asc') return ' 🔼'; + if (sortState === 'desc') return ' 🔽'; + return null; + })()} + + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + {flexRender(cell.column.columnDef.cell, cell.getContext())} + + ))} + + ))} + +
+
+ + + + + + {table.getPrePaginationRowModel().rows.length} Rows + + + + + Page + + {table.getState().pagination.pageIndex + 1} of {table.getPageCount()} + + + + | Go to page: + { + const page = e.target.value ? Number(e.target.value) - 1 : 0; + table.setPageIndex(page); + }} + /> + + { + table.setPageSize(Number(e.target.value)); + }} + > + {[10, 15, 20, 25].map((pageSize) => ( + + {pageSize} + + ))} + + + table.setPageIndex(0)} + disabled={!table.getCanPreviousPage()} + > + + + table.previousPage()} + disabled={!table.getCanPreviousPage()} + > + + + table.nextPage()} + disabled={!table.getCanNextPage()} + > + + + table.setPageIndex(table.getPageCount() - 1)} + disabled={!table.getCanNextPage()} + > + + + + +
+
+
+
) + ); +}; + +export default ReactSortingTable; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/sticky/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/sticky/page.tsx new file mode 100644 index 0000000..165ad0d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/react-tables/sticky/page.tsx @@ -0,0 +1,208 @@ + +import * as React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + AvatarGroup, Grid2 as Grid +} from '@mui/material'; +import { Stack } from '@mui/system'; + +import DownloadCard from 'src/components/shared/DownloadCard'; +import { basicsTableData, EnTableType } from 'src/components/tables/tableData'; + +import { + createColumnHelper, + flexRender, + getCoreRowModel, + useReactTable, +} from '@tanstack/react-table'; + +const basics = basicsTableData; + + +const columnHelper = createColumnHelper(); + +const columns = [ + columnHelper.accessor('imgsrc', { + header: () => 'Users', + cell: info => ( + + + + + {info.row.original.name} + + + {info.row.original.post} + + + + ), + }), + columnHelper.accessor('pname', { + header: () => 'Project Name', + cell: info => ( + + {info.row.original.pname} + + ), + }), + columnHelper.accessor('teams', { + header: () => 'Team', + cell: info => ( + + + {info.getValue().map((team) => ( + + {team.text} + + ))} + + + ), + }), + columnHelper.accessor('status', { + header: () => 'Status', + cell: info => ( + theme.palette.success.light + : info.getValue() === 'Pending' + ? (theme) => theme.palette.warning.light + : info.getValue() === 'Completed' + ? (theme) => theme.palette.primary.light + : info.getValue() === 'Cancel' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + info.getValue() === 'Active' + ? (theme) => theme.palette.success.main + : info.getValue() === 'Pending' + ? (theme) => theme.palette.warning.main + : info.getValue() === 'Completed' + ? (theme) => theme.palette.primary.main + : info.getValue() === 'Cancel' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: '8px', + }} + size="small" + label={info.getValue()} + /> + ), + }), + columnHelper.accessor('budget', { + header: () => 'Budget', + cell: info => ( + + ${info.row.original.budget}k + + ), + }), +]; + +const StickyTable = () => { + const [data, _setData] = React.useState(() => [...basics]); + + const table = useReactTable({ + data, + columns, + getCoreRowModel: getCoreRowModel(), + }); + + const handleDownload = () => { + const headers = ["Users", "Project Name", "Team", "Status", "Budget"]; + const rows = data.map((item: { name: any; pname: any; teams: any[]; status: any; budget: any; }) => [ + + item.name, + item.pname, + item.teams.map(team => team.text).join(", "), + item.status, + item.budget, + ]); + + const csvContent = [ + headers.join(","), + ...rows.map((e: any[]) => e.join(",")) + ].join("\n"); + + const blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8;' }); + const url = URL.createObjectURL(blob); + + const link = document.createElement("a"); + link.href = url; + link.setAttribute("download", "table-data.csv"); + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }; + + return ( + ( + + + + + + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + + {header.isPlaceholder + ? null + : flexRender(header.column.columnDef.header, header.getContext())} + + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + {flexRender(cell.column.columnDef.cell, cell.getContext())} + + ))} + + ))} + +
+
+
+
+
+
) + ); +}; + +export default StickyTable; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/AppCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/AppCard.tsx new file mode 100644 index 0000000..b22eb4c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/AppCard.tsx @@ -0,0 +1,27 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +import { Card } from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import { AppState } from 'src/store/Store'; + +type Props = { + children: any | any[] +}; + +const AppCard = ({ children }: Props) => { + const customizer = useSelector((state: AppState) => state.customizer); + + return ( + + {children} + + ); +}; + +export default AppCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/BaseCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/BaseCard.tsx new file mode 100644 index 0000000..17ac2cd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/BaseCard.tsx @@ -0,0 +1,30 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +import { Card, CardHeader, CardContent, Divider } from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import { AppState } from 'src/store/Store'; + +type Props = { + title: string; + children: any | any[] +}; + +const BaseCard = ({ title, children }: Props) => { + const customizer = useSelector((state: AppState) => state.customizer); + + return ( + + + + {children} + + ); +}; + +export default BaseCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/BlankCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/BlankCard.tsx new file mode 100644 index 0000000..21b0dae --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/BlankCard.tsx @@ -0,0 +1,32 @@ +import { Card } from '@mui/material'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { AppState, useSelector } from 'src/store/Store'; + +type Props = { + className?: string; + children: any | any[] + sx?: any; +}; + +const BlankCard = ({ children, className, sx }: Props) => { + const customizer = useSelector((state: AppState) => state.customizer); + + const theme = useTheme(); + const borderColor = theme.palette.divider; + + return ( + + {children} + + ); +}; + +export default BlankCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ChildCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ChildCard.tsx new file mode 100644 index 0000000..b4bdb3b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ChildCard.tsx @@ -0,0 +1,28 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +import { Card, CardHeader, CardContent, Divider } from '@mui/material'; + +type Props = { + title?: string; + children: any | any[] + codeModel?: any | any[] +}; + +const ChildCard = ({ title, children, codeModel }: Props) => ( + theme.palette.divider }} variant="outlined"> + {title ? ( + <> + + {' '} + + ) : ( + '' + )} + + {children} + +); + +export default ChildCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/CodeDialog.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/CodeDialog.tsx new file mode 100644 index 0000000..485fb27 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/CodeDialog.tsx @@ -0,0 +1,62 @@ +import React from "react"; +import { IconCode, IconX } from "@tabler/icons-react"; +import SyntaxHighlighter from "react-syntax-highlighter"; +import { docco } from "react-syntax-highlighter/dist/esm/styles/hljs"; + +import Dialog from "@mui/material/Dialog"; +import DialogContent from "@mui/material/DialogContent"; +import DialogTitle from "@mui/material/DialogTitle"; +import Tooltip from "@mui/material/Tooltip"; +import IconButton from "@mui/material/IconButton"; +import Box from "@mui/material/Box"; + +const CodeDialog = ({ children }: any) => { + const [open, setOpen] = React.useState(false); + + const handleClickOpen = () => { + setOpen(true); + }; + + const handleClose = () => { + setOpen(false); + }; + return ( +
+ + + + + + + + + Sample Code + + + + + + + + + {children} + + + +
+ ); +}; + +export default CodeDialog; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/DashboardCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/DashboardCard.tsx new file mode 100644 index 0000000..f8ca8f0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/DashboardCard.tsx @@ -0,0 +1,85 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { Card, CardContent, Typography, Stack, Box } from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import { AppState } from 'src/store/Store'; + +type Props = { + title?: string; + subtitle?: string; + action?: any; + footer?: any; + cardheading?: string | any; + headtitle?: string | any; + headsubtitle?: string | any; + children?: any; + middlecontent?: string | any; +}; + +const DashboardCard = ({ + title, + subtitle, + children, + action, + footer, + cardheading, + headtitle, + headsubtitle, + middlecontent, +}: Props) => { + const customizer = useSelector((state: AppState) => state.customizer); + + const theme = useTheme(); + const borderColor = theme.palette.divider; + + return ( + + {cardheading ? ( + + {headtitle} + + {headsubtitle} + + + ) : ( + + {title ? ( + + + {title ? {title} : ''} + + {subtitle ? ( + + {subtitle} + + ) : ( + '' + )} + + {action} + + ) : null} + + {children} + + )} + + {middlecontent} + {footer} + + ); +}; + +export default DashboardCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/DashboardWidgetCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/DashboardWidgetCard.tsx new file mode 100644 index 0000000..12e89ae --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/DashboardWidgetCard.tsx @@ -0,0 +1,118 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { Card, CardContent, Typography, Box, Stack } from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import { AppState } from 'src/store/Store'; +import { IconGridDots } from '@tabler/icons-react'; + +type Props = { + title: string; + subtitle: string; + dataLabel1: string; + dataItem1: string; + dataLabel2: string; + dataItem2: string; + children: any; +}; + +const DashboardWidgetCard = ({ + title, + subtitle, + children, + dataLabel1, + dataItem1, + dataLabel2, + dataItem2, +}: Props) => { + const customizer = useSelector((state: AppState) => state.customizer); + + const theme = useTheme(); + const borderColor = theme.palette.grey[100]; + + return ( + + + {title ? ( + + {title ? {title} : ''} + + {subtitle ? ( + + {subtitle} + + ) : ( + '' + )} + + ) : null} + + {children} + + + + + + + + + + + {dataLabel1} + + + {dataItem1} + + + + + + + + + + + + {dataLabel2} + + + {dataItem2} + + + + + + + ); +}; + +export default DashboardWidgetCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/DownloadCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/DownloadCard.tsx new file mode 100644 index 0000000..079a2af --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/DownloadCard.tsx @@ -0,0 +1,37 @@ +import { useTheme } from '@mui/material/styles'; +import { Card, CardHeader, Tooltip, Divider, IconButton } from '@mui/material'; +import { useSelector } from 'react-redux'; +import { IconDownload } from '@tabler/icons-react'; + +const DownloadCard = ({ title, children, onDownload }: any) => { + const customizer = useSelector((state: any) => state.customizer); + + const theme = useTheme(); + const borderColor = theme.palette.divider; + + return ( + + + + + + + } + /> + + {children} + + ); +}; + +export default DownloadCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/InlineItemCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/InlineItemCard.tsx new file mode 100644 index 0000000..fcb6f33 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/InlineItemCard.tsx @@ -0,0 +1,31 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +import { Box } from '@mui/material'; + +type Props = { + children: any | any[]; +}; + +const InlineItemCard = ({ children }: Props) => ( + + {children} + +); + +export default InlineItemCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ParentCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ParentCard.tsx new file mode 100644 index 0000000..232cfa0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ParentCard.tsx @@ -0,0 +1,44 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { Card, CardHeader, CardContent, Divider, Box } from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import { AppState } from 'src/store/Store'; + +type Props = { + title: string; + footer?: string | any; + codeModel?: any | any[] + children: any; +}; + +const ParentCard = ({ title, children, footer, codeModel }: Props) => { + const customizer = useSelector((state: AppState) => state.customizer); + + const theme = useTheme(); + const borderColor = theme.palette.divider; + + return ( + + + + + {children} + {footer ? ( + <> + + {footer} + + ) : ( + '' + )} + + ); +}; + +export default ParentCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ScrollToTop.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ScrollToTop.tsx new file mode 100644 index 0000000..0113c32 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ScrollToTop.tsx @@ -0,0 +1,16 @@ +import { useEffect, ReactElement } from 'react'; +import { useLocation } from 'react-router'; + +export default function ScrollToTop({ children }: { children: ReactElement | null }) { + const { pathname } = useLocation(); + + useEffect(() => { + window.scrollTo({ + top: 0, + left: 0, + behavior: 'smooth', + }); + }, [pathname]); + + return children || null; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ThreeColumn.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ThreeColumn.tsx new file mode 100644 index 0000000..a242bc0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/shared/ThreeColumn.tsx @@ -0,0 +1,89 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { Button, Box, Drawer, useMediaQuery, Paper, Theme } from '@mui/material'; + + +const drawerWidth = 240; +const secdrawerWidth = 320; + +type Props = { + middleChild: any | string; + leftChild: any | string; + rightChild: any; +}; + +const ThreeColumn = ({ leftChild, middleChild, rightChild }: Props) => { + const [isLeftSidebarOpen, setLeftSidebarOpen] = useState(false); + const [isRightSidebarOpen, setRightSidebarOpen] = useState(false); + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + const mdUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('md')); + + return ( + + {/* ------------------------------------------- */} + {/* Left Part */} + {/* ------------------------------------------- */} + + setLeftSidebarOpen(false)} + sx={{ + width: drawerWidth, + [`& .MuiDrawer-paper`]: { width: drawerWidth, position: 'relative' }, + flexShrink: 0, + }} + variant={lgUp ? 'permanent' : 'temporary'} + > + {leftChild} + + {/* ------------------------------------------- */} + {/* Middle part */} + {/* ------------------------------------------- */} + + {middleChild} + + {/* ------------------------------------------- */} + {/* Right part */} + {/* ------------------------------------------- */} + setRightSidebarOpen(false)} + sx={{ + flexShrink: 0, + width: drawerWidth, + flex: mdUp ? 'auto' : '', + [`& .MuiDrawer-paper`]: { width: '100%', position: 'relative' }, + }} + variant={mdUp ? 'permanent' : 'temporary'} + > + {/* back btn Part */} + {mdUp ? ( + '' + ) : ( + + + + )} + {rightChild} + + + ); +}; + +export default ThreeColumn; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table1.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table1.tsx new file mode 100644 index 0000000..7494392 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table1.tsx @@ -0,0 +1,238 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + TableContainer, + Table, + TableHead, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + Chip, + LinearProgress, + Menu, + MenuItem, + IconButton, + ListItemIcon, + Box, Stack +} from '@mui/material'; +import BlankCard from '../shared/BlankCard'; +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; +import img5 from 'src/assets/images/profile/user-5.jpg'; +import img6 from 'src/assets/images/profile/user-6.jpg'; +import { + IconArrowBackUp, + IconCheck, + IconDotsVertical, + IconEdit, + IconPlus, + IconTrash, + IconX, +} from '@tabler/icons-react'; + + +interface rowsType { + no: number; + status: string; + avatar: string; + cname: string; + email: string; + percent: number; +} + +const rows: rowsType[] = [ + { + no: 3066, + status: 'paid', + avatar: img1, + cname: 'Olivia Rhye', + email: 'olivia@ui.com', + percent: 60, + }, + { + no: 3067, + status: 'cancelled', + avatar: img2, + cname: 'Barbara Steele', + email: 'steele@ui.com', + percent: 30, + }, + { + no: 3068, + status: 'paid', + avatar: img3, + cname: 'Leonard Gordon', + email: 'olivia@ui.com', + percent: 45, + }, + { + no: 3069, + status: 'refunded', + avatar: img4, + cname: 'Evelyn Pope', + email: 'steele@ui.com', + percent: 37, + }, + { + no: 3070, + status: 'cancelled', + avatar: img5, + cname: 'Tommy Garza', + email: 'olivia@ui.com', + percent: 87, + }, + { + no: 3071, + status: 'refunded', + avatar: img6, + cname: 'Isabel Vasquez', + email: 'steele@ui.com', + percent: 32, + }, +]; + +const Table1 = () => { + const [anchorEl, setAnchorEl] = React.useState(null); + const open = Boolean(anchorEl); + const handleClick = (event: React.MouseEvent) => { + setAnchorEl(event.currentTarget); + }; + const handleClose = () => { + setAnchorEl(null); + }; + + return ( + + + + + + + Invoice + + + Status + + + Customer + + + Progress + + + + + + {rows.map((row) => ( + + + + INV-{row.no} + + + + + ) : row.status == 'cancelled' ? ( + + ) : ( + + ) + } + sx={{ + backgroundColor: + row.status == 'paid' + ? (theme) => theme.palette.primary.light + : row.status == 'cancelled' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + row.status == 'paid' + ? (theme) => theme.palette.primary.main + : row.status == 'cancelled' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + '.MuiChip-icon': { + color: 'inherit !important', + }, + }} + /> + + + + + + {row.cname} + + {row.email} + + + + + + + + + + + {row.percent}% + + + + + + + + + + + + + Add + + + + + + Edit + + + + + + Delete + + + + + ))} + +
+
+
+ ); +}; + +export default Table1; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table2.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table2.tsx new file mode 100644 index 0000000..7c91fc0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table2.tsx @@ -0,0 +1,217 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + TableContainer, + Table, + TableHead, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + Chip, + Menu, + MenuItem, + IconButton, + ListItemIcon, + AvatarGroup, + Box, Stack +} from '@mui/material'; +import BlankCard from '../shared/BlankCard'; +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; +import img5 from 'src/assets/images/profile/user-5.jpg'; +import img6 from 'src/assets/images/profile/user-6.jpg'; +import { IconDotsVertical, IconEdit, IconPlus, IconTrash } from '@tabler/icons-react'; + +interface rowsType { + status: string; + avatar: string; + name: string; + project: string; + percent: number; + users: Array<{ img: string }>; +} + +const rows:rowsType[] = [ + { + status: 'active', + avatar: img1, + name: 'Olivia Rhye', + project: 'Xtreme admin', + percent: 60, + users: [{ img: img1 }, { img: img2 }], + }, + { + status: 'cancel', + avatar: img2, + name: 'Barbara Steele', + project: 'Adminpro admin', + percent: 30, + users: [{ img: img1 }, { img: img2 }, { img: img3 }], + }, + { + status: 'active', + avatar: img3, + name: 'Leonard Gordon', + project: 'Monster admin', + percent: 45, + users: [{ img: img3 }, { img: img2 }], + }, + { + status: 'pending', + avatar: img4, + name: 'Evelyn Pope', + project: 'Materialpro admin', + percent: 37, + users: [{ img: img1 }, { img: img2 }, { img: img5 }], + }, + { + status: 'cancel', + avatar: img5, + name: 'Tommy Garza', + project: 'Elegant admin', + percent: 87, + users: [{ img: img5 }, { img: img6 }], + }, + { + status: 'pending', + avatar: img6, + name: 'Isabel Vasquez', + project: 'Modernize admin', + percent: 32, + users: [{ img: img2 }, { img: img4 }], + }, +]; + +const Table2 = () => { + const [anchorEl, setAnchorEl] = React.useState(null); + const open = Boolean(anchorEl); + const handleClick = (event: React.MouseEvent) => { + setAnchorEl(event.currentTarget); + }; + const handleClose = () => { + setAnchorEl(null); + }; + + return ( + + + + + + + User + + + Project Name + + + Users + + + Status + + + + + + {rows.map((row) => ( + + + + + + {row.name} + + + + + + {row.project} + + + + + {row.users.map((user, i) => ( + + ))} + + + + theme.palette.primary.light + : row.status == 'cancel' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.success.light, + color: + row.status == 'active' + ? (theme) => theme.palette.primary.main + : row.status == 'cancel' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.success.main, + }} + /> + + + + + + + + + + + + Add + + + + + + Edit + + + + + + Delete + + + + + ))} + +
+
+
+ ); +}; + +export default Table2; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table3.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table3.tsx new file mode 100644 index 0000000..f612a7c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table3.tsx @@ -0,0 +1,234 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + TableContainer, + Table, + TableHead, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + Chip, + Menu, + MenuItem, + IconButton, + ListItemIcon, + Box, Stack +} from '@mui/material'; +import BlankCard from '../shared/BlankCard'; +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; +import img5 from 'src/assets/images/profile/user-5.jpg'; +import img6 from 'src/assets/images/profile/user-6.jpg'; +import { IconCircle, IconClock, IconDots, IconEdit, IconPlus, IconTrash } from '@tabler/icons-react'; + +interface rowsType { + status: string; + avatar: string; + tag: string; + cname: string; + email: string; + teams: Array<{ name: string; bgcolor: string }>; +} + +const rows: rowsType[] = [ + { + status: 'active', + avatar: img1, + tag: 'rhye', + cname: 'Olivia Rhye', + email: 'olivia@ui.com', + teams: [ + { name: 'Design', bgcolor: 'primary.main' }, + { name: 'Product', bgcolor: 'secondary.main' }, + ], + }, + { + status: 'offline', + avatar: img2, + tag: 'steele', + cname: 'Barbara Steele', + email: 'steele@ui.com', + teams: [ + { name: 'Product', bgcolor: 'secondary.main' }, + { name: 'Operations', bgcolor: 'error.main' }, + ], + }, + { + status: 'active', + avatar: img3, + tag: 'gordon', + cname: 'Leonard Gordon', + email: 'olivia@ui.com', + teams: [ + { name: 'Finance', bgcolor: 'primary.main' }, + { name: 'Customer Success', bgcolor: 'success.main' }, + ], + }, + { + status: 'offline', + avatar: img4, + tag: 'pope', + cname: 'Evelyn Pope', + email: 'steele@ui.com', + teams: [ + { name: 'Operations', bgcolor: 'error.main' }, + { name: 'Design', bgcolor: 'primary.main' }, + ], + }, + { + status: 'active', + avatar: img5, + tag: 'garza', + cname: 'Tommy Garza', + email: 'olivia@ui.com', + teams: [{ name: 'Product', bgcolor: 'secondary.main' }], + }, + { + status: 'active', + avatar: img6, + tag: 'vasquez', + cname: 'Isabel Vasquez', + email: 'steele@ui.com', + teams: [{ name: 'Customer Success', bgcolor: 'success.main' }], + }, +]; + +const Table3 = () => { + const [anchorEl, setAnchorEl] = React.useState(null); + const open = Boolean(anchorEl); + const handleClick = (event: React.MouseEvent) => { + setAnchorEl(event.currentTarget); + }; + const handleClose = () => { + setAnchorEl(null); + }; + + return ( + + + + + + + Customer + + + Status + + + Email Address + + + Teams + + + + + + + {rows.map((row) => ( + + + + + + {row.cname} + + @{row.tag} + + + + + + : + } + sx={{ + backgroundColor: + row.status == 'active' + ? (theme) => theme.palette.success.light + : (theme) => theme.palette.grey[100], + color: + row.status == 'active' + ? (theme) => theme.palette.success.main + : (theme) => theme.palette.grey[500], + '.MuiChip-icon': { + color: 'inherit !important', + }, + }} + /> + + + + {row.email} + + + + + {row.teams.map((team, i) => ( + + ))} + + + + + + + + + + + + Add + + + + + + Edit + + + + + + Delete + + + + + ))} + +
+
+
+ ); +}; + +export default Table3; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table4.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table4.tsx new file mode 100644 index 0000000..8ff6d8b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table4.tsx @@ -0,0 +1,213 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + Chip, + Menu, + MenuItem, + IconButton, + ListItemIcon, + TableHead, + Box, Stack +} from '@mui/material'; +import BlankCard from '../shared/BlankCard'; +import img1 from 'src/assets/images/blog/blog-img1.jpg'; +import img2 from 'src/assets/images/blog/blog-img2.jpg'; +import img3 from 'src/assets/images/blog/blog-img3.jpg'; +import img4 from 'src/assets/images/blog/blog-img4.jpg'; +import img5 from 'src/assets/images/blog/blog-img5.jpg'; +import { IconDots, IconEdit, IconPlus, IconTrash } from '@tabler/icons-react'; + +interface Team { + name: string; + bgcolor: string; + textcolor: string; +} + +interface rowType { + status: 'active' | 'offline'; + avatar: string; + users: string; + title: string; + subtitle: string; + teams: Team[]; +} + +const rows: rowType[] = [ + { + status: 'active', + avatar: img1, + users: '4300', + title: 'Top Authors', + subtitle: 'Successful Fellas', + teams: [ + { name: 'Angular', bgcolor: 'error.light', textcolor: 'error.main' }, + { name: 'PHP', bgcolor: 'primary.light', textcolor: 'primary.main' }, + ], + }, + { + status: 'offline', + avatar: img2, + users: '1200', + title: 'Popular Authors', + subtitle: 'Most Successful', + teams: [{ name: 'Bootstrap', bgcolor: 'primary.light', textcolor: 'primary.main' }], + }, + { + status: 'active', + avatar: img3, + users: '2000', + title: 'New Users', + subtitle: 'Awesome Users', + teams: [ + { name: 'Reactjs', bgcolor: 'success.light', textcolor: 'success.main' }, + { name: 'Angular', bgcolor: 'error.light', textcolor: 'error.main' }, + ], + }, + { + status: 'offline', + avatar: img4, + users: '1500', + title: 'Active Customers', + subtitle: 'Best Customers', + teams: [{ name: 'Bootstrap', bgcolor: 'primary.light', textcolor: 'primary.main' }], + }, + { + status: 'active', + avatar: img5, + users: '9500', + title: 'Bestseller Theme', + subtitle: 'Amazing Templates', + teams: [ + { name: 'Angular', bgcolor: 'error.light', textcolor: 'error.main' }, + { name: 'Reactjs', bgcolor: 'success.light', textcolor: 'success.main' }, + ], + }, +]; + +const Table4 = () => { + const [anchorEl, setAnchorEl] = React.useState(null); + const open = Boolean(anchorEl); + const handleClick = (event: React.MouseEvent) => { + setAnchorEl(event.currentTarget); + }; + const handleClose = () => { + setAnchorEl(null); + }; + + return ( + + + + + + + Authors + + + Courses + + + Users + + + + + + {rows.map((row) => ( + + + + + + + {row.title} + + + {row.subtitle} + + + + + + + {row.teams.map((team, i) => ( + + ))} + + + + + {row.users} Users + + + + + + + + + + + + Add + + + + + + Edit + + + + + + Delete + + + + + ))} + +
+
+
+ ); +}; + +export default Table4; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table5.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table5.tsx new file mode 100644 index 0000000..2546773 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/Table5.tsx @@ -0,0 +1,133 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + TableContainer, + Table, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + TableHead, + Chip, + Box, + AvatarGroup, + Stack +} from '@mui/material'; +import BlankCard from '../shared/BlankCard'; +import { basicsTableData, TableType } from './tableData'; + +const basics: TableType[] = basicsTableData; + +const Table5 = () => { + return ( + + + + + + + Users + + + Project Name + + + Team + + + Status + + + Budget + + + + + {basics.map((basic) => ( + + + + + + + {basic.name} + + + {basic.post} + + + + + + + {basic.pname} + + + + + + {basic.teams?.map((team) => ( + + {team.text} + + ))} + + + + + {/* theme.palette.success.light + : basic.status === 'Pending' + ? (theme) => theme.palette.warning.light + : basic.status === 'Completed' + ? (theme) => theme.palette.primary.light + : basic.status === 'Cancel' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + basic.status === 'Active' + ? (theme) => theme.palette.success.main + : basic.status === 'Pending' + ? (theme) => theme.palette.warning.main + : basic.status === 'Completed' + ? (theme) => theme.palette.primary.main + : basic.status === 'Cancel' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + borderRadius: '8px', + }} + size="small" + label={basic.status} + /> + + + ${basic.budget}k + + + ))} + +
+
+
+ ); +}; + +export default Table5; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/code/BasicTableCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/code/BasicTableCode.tsx new file mode 100644 index 0000000..c2139f7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/code/BasicTableCode.tsx @@ -0,0 +1,250 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const BasicTableCode = () => { + return ( + <> + + {` +import React from 'react'; +import { + TableContainer, + Table, + TableHead, + TableRow, + TableCell, + TableBody, + Avatar, + Typography, + Chip, + LinearProgress, + Menu, + MenuItem, + IconButton, + ListItemIcon, + Box, Stack +} from '@mui/material'; +import BlankCard from '../shared/BlankCard'; +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; +import img5 from 'src/assets/images/profile/user-5.jpg'; +import img6 from 'src/assets/images/profile/user-6.jpg'; +import { + IconArrowBackUp, + IconCheck, + IconDotsVertical, + IconEdit, + IconPlus, + IconTrash, + IconX, +} from '@tabler/icons-react'; + + +interface rowsType { + no: number; + status: string; + avatar: string; + cname: string; + email: string; + percent: number; +} + +const rows: rowsType[] = [ + { + no: 3066, + status: 'paid', + avatar: img1, + cname: 'Olivia Rhye', + email: 'olivia@ui.com', + percent: 60, + }, + { + no: 3067, + status: 'cancelled', + avatar: img2, + cname: 'Barbara Steele', + email: 'steele@ui.com', + percent: 30, + }, + { + no: 3068, + status: 'paid', + avatar: img3, + cname: 'Leonard Gordon', + email: 'olivia@ui.com', + percent: 45, + }, + { + no: 3069, + status: 'refunded', + avatar: img4, + cname: 'Evelyn Pope', + email: 'steele@ui.com', + percent: 37, + }, + { + no: 3070, + status: 'cancelled', + avatar: img5, + cname: 'Tommy Garza', + email: 'olivia@ui.com', + percent: 87, + }, + { + no: 3071, + status: 'refunded', + avatar: img6, + cname: 'Isabel Vasquez', + email: 'steele@ui.com', + percent: 32, + }, +]; + +const Table1 = () => { + const [anchorEl, setAnchorEl] = React.useState(null); + const open = Boolean(anchorEl); + const handleClick = (event: React.MouseEvent) => { + setAnchorEl(event.currentTarget); + }; + const handleClose = () => { + setAnchorEl(null); + }; + + return ( + + + + + + + Invoice + + + Status + + + Customer + + + Progress + + + + + + {rows.map((row) => ( + + + + INV-{row.no} + + + + + ) : row.status == 'cancelled' ? ( + + ) : ( + + ) + } + sx={{ + backgroundColor: + row.status == 'paid' + ? (theme) => theme.palette.primary.light + : row.status == 'cancelled' + ? (theme) => theme.palette.error.light + : (theme) => theme.palette.secondary.light, + color: + row.status == 'paid' + ? (theme) => theme.palette.primary.main + : row.status == 'cancelled' + ? (theme) => theme.palette.error.main + : (theme) => theme.palette.secondary.main, + '.MuiChip-icon': { + color: 'inherit !important', + }, + }} + /> + + + + + + {row.cname} + + {row.email} + + + + + + + + + + + {row.percent}% + + + + + + + + + + + + + Add + + + + + + Edit + + + + + + Delete + + + + + ))} + +
+
+
+ ); +}; + +export default Table1; + +`} +
+ + ); +}; + +export default BasicTableCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/tableData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/tableData.ts new file mode 100644 index 0000000..f02c247 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/tables/tableData.ts @@ -0,0 +1,354 @@ +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; +import img5 from 'src/assets/images/profile/user-5.jpg'; + +export interface TableType { + id?: string; + imgsrc?: string; + name?: string; + post?: string; + pname?: string; + teams?: any[]; + status?: string; + budget?: string; +} + +export interface EnTableType { + id: string; + imgsrc: string; + name: string; + email: string; + pname: string; + teams: { + id: string; + color: string; + text: string; + }[]; + status: string; + weeks: string; + budget: string; + post?: string; + dragHandle?: any; + actions?: any; + checkboxes?: any; +} + +const basicsTableData: TableType[] = [ + { + id: '1', + imgsrc: img1, + name: 'Sunil Joshi', + post: 'Web Designer', + pname: 'Elite Admin', + teams: [ + { + id: '1.1', + color: 'secondary.main', + text: 'S', + }, + { + id: '1.2', + color: 'error.main', + text: 'D', + }, + ], + status: 'Active', + budget: '3.9', + }, + { + id: '2', + imgsrc: img2, + name: 'Andrew McDownland', + post: 'Project Manager', + pname: 'Real Homes WP Theme', + teams: [ + { + id: '2.1', + color: 'primary.main', + text: 'A', + }, + { + id: '2.2', + color: 'warning.main', + text: 'X', + }, + { + id: '2.3', + color: 'secondary.main', + text: 'N', + }, + ], + status: 'Pending', + budget: '24.5', + }, + { + id: '3', + imgsrc: img3, + name: 'Christopher Jamil', + post: 'Project Manager', + pname: 'MedicalPro WP Theme', + teams: [ + { + id: '3.1', + color: 'error.main', + text: 'X', + }, + ], + status: 'Completed', + budget: '12.8', + }, + { + id: '4', + imgsrc: img4, + name: 'Mathew Anderson', + post: 'Frontend Engineer', + pname: 'Hosting Press HTML', + teams: [ + { + id: '4.1', + color: 'primary.main', + text: 'Y', + }, + { + id: '4.2', + color: 'error.main', + text: 'X', + }, + ], + status: 'Active', + budget: '2.4', + }, + { + id: '5', + imgsrc: img5, + name: 'Micheal Doe', + post: 'Content Writer', + pname: 'Helping Hands WP Theme', + teams: [ + { + id: '5.1', + color: 'secondary.main', + text: 'S', + }, + ], + status: 'Cancel', + budget: '9.3', + }, +]; + +const EnhancedTableData: EnTableType[] = [ + { + id: '1', + imgsrc: img1, + name: 'Sunil Joshi', + email: 'sunil@gmail.com', + pname: 'Elite Admin', + teams: [ + { + id: '1.1', + color: 'secondary.main', + text: 'S', + }, + { + id: '1.2', + color: 'error.main', + text: 'D', + }, + ], + status: 'Active', + weeks: '11', + budget: '3.9', + }, + { + id: '2', + imgsrc: img2, + name: 'Andrew McDownland', + email: 'andrew@gmail.com', + pname: 'Real Homes WP Theme', + teams: [ + { + id: '2.1', + color: 'primary.main', + text: 'A', + }, + { + id: '2.2', + color: 'warning.main', + text: 'X', + }, + { + id: '2.3', + color: 'secondary.main', + text: 'N', + }, + ], + status: 'Pending', + weeks: '19', + budget: '24.5', + }, + { + id: '3', + imgsrc: img3, + name: 'Christopher Jamil', + email: 'jamil@gmail.com', + pname: 'MedicalPro WP Theme', + teams: [ + { + id: '3.1', + color: 'error.main', + text: 'X', + }, + ], + status: 'Completed', + weeks: '30', + budget: '12.8', + }, + { + id: '4', + imgsrc: img4, + name: 'Mathew Anderson', + email: 'nirav@gmail.com', + pname: 'Hosting Press HTML', + teams: [ + { + id: '4.1', + color: 'primary.main', + text: 'Y', + }, + { + id: '4.2', + color: 'error.main', + text: 'X', + }, + ], + status: 'Active', + weeks: '40', + budget: '2.4', + }, + { + id: '5', + imgsrc: img5, + name: 'Micheal Doe', + email: 'micheal@gmail.com', + pname: 'Helping Hands WP Theme', + teams: [ + { + id: '5.1', + color: 'secondary.main', + text: 'S', + }, + ], + status: 'Cancel', + weeks: '1', + budget: '9.3', + }, + { + id: '6', + imgsrc: img4, + name: 'Mathew Anderson', + email: 'nirav@gmail.com', + pname: 'Hosting Press HTML', + teams: [ + { + id: '6.1', + color: 'primary.main', + text: 'Y', + }, + { + id: '6.2', + color: 'error.main', + text: 'X', + }, + ], + status: 'Active', + weeks: '16', + budget: '2.4', + }, + { + id: '7', + imgsrc: img1, + name: 'Sunil Joshi', + email: 'sunil@gmail.com', + pname: 'Elite Admin', + teams: [ + { + id: '7.1', + color: 'secondary.main', + text: 'S', + }, + { + id: '7.2', + color: 'error.main', + text: 'D', + }, + ], + status: 'Active', + weeks: '12', + budget: '3.9', + }, + { + id: '8', + imgsrc: img2, + name: 'Andrew McDownland', + email: 'andrew@gmail.com', + pname: 'Real Homes WP Theme', + teams: [ + { + id: '8.1', + color: 'primary.main', + text: 'A', + }, + { + id: '8.2', + color: 'warning.main', + text: 'X', + }, + { + id: '8.3', + color: 'secondary.main', + text: 'N', + }, + ], + status: 'Pending', + weeks: '14', + budget: '24.5', + }, + { + id: '9', + imgsrc: img3, + name: 'Christopher Jamil', + email: 'jamil@gmail.com', + pname: 'MedicalPro WP Theme', + teams: [ + { + id: '9.1', + color: 'error.main', + text: 'X', + }, + ], + status: 'Completed', + weeks: '12', + budget: '12.8', + }, + + { + id: '10', + imgsrc: img5, + name: 'Micheal Doe', + email: 'micheal@gmail.com', + pname: 'Helping Hands WP Theme', + teams: [ + { + id: '10.1', + color: 'secondary.main', + text: 'S', + }, + ], + status: 'Cancel', + weeks: '9', + budget: '9.3', + }, +]; +export { basicsTableData, EnhancedTableData }; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner1.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner1.tsx new file mode 100644 index 0000000..28567e3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner1.tsx @@ -0,0 +1,62 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Card, CardContent, Typography, Button, Box, Grid2 as Grid } from '@mui/material'; +import trackBg from 'src/assets/images/backgrounds/login-bg.svg'; +import ParentCard from '../../shared/ParentCard'; + +import Transection from './code/TransectionCode'; + +const Banner1 = () => { + return ( + (}> + theme.palette.secondary.light, + py: 0, + overflow: 'hidden', + position: 'relative', + }} + > + + + + + Track your every Transaction Easily + + Track and record your every income and expence easily to control your balance + + + + + + + {trackBg} + + + + + + ) + ); +}; + +export default Banner1; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner2.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner2.tsx new file mode 100644 index 0000000..0fbb15c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner2.tsx @@ -0,0 +1,32 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { CardContent, Typography, Button, Box } from '@mui/material'; +import starBg from 'src/assets/images/backgrounds/gold.png'; +import ParentCard from '../../shared/ParentCard'; + +import NotificationCode from './code/NotificationCode'; + +const Banner2 = () => { + return ( + }> + + + Level Up + + + star + + You reach all Notifications + Congratulations,
Tap to continue next task.
+ + +
+
+
+ ); +}; + +export default Banner2; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner3.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner3.tsx new file mode 100644 index 0000000..01b18f0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner3.tsx @@ -0,0 +1,43 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { CardContent, Typography, Button, Avatar, Badge, Box, Stack } from '@mui/material'; +import userBg from 'src/assets/images/profile/user-1.jpg'; +import ParentCard from '../../shared/ParentCard'; + +import FriendCardCode from './code/FriendCardCode'; + +const Banner3 = () => { + return ( + }> + + + Mutual Friend Revealed + + + + + + + + Tommoie Henderson + + + Accept the request and
type a message +
+ + + + + +
+
+
+ ); +}; + +export default Banner3; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner4.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner4.tsx new file mode 100644 index 0000000..335623f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner4.tsx @@ -0,0 +1,34 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { CardContent, Typography, Button, Box } from '@mui/material'; +import oopsBg from 'src/assets/images/backgrounds/maintenance.svg'; +import ParentCard from 'src/components/shared/ParentCard'; + +import ErrorBannerCode from './code/ErrorBannerCode'; + +const Banner4 = () => { + return ( + }> + + + star + + + Oops something went wrong! + + + Trying again to bypasses these +
temporary error. +
+ + +
+
+
+ ); +}; + +export default Banner4; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner5.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner5.tsx new file mode 100644 index 0000000..86d10d4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/Banner5.tsx @@ -0,0 +1,34 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { CardContent, Typography, Button, Box } from '@mui/material'; +import shopBg from 'src/assets/images/products/empty-shopping-cart.svg'; +import ParentCard from '../../shared/ParentCard'; + +import EmptyCartCode from './code/EmptyCartCode'; + +const Banner5 = () => { + return ( + }> + + + star + + + Oop, Your cart is empty! + + + Get back to shopping and get +
rewards from it. +
+ + +
+
+
+ ); +}; + +export default Banner5; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/EmptyCartCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/EmptyCartCode.tsx new file mode 100644 index 0000000..549cdb5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/EmptyCartCode.tsx @@ -0,0 +1,40 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const EmptyCartCode = () => { + return ( + <> + + {` +import React from 'react'; +import { CardContent, Typography, Button, Card } from '@mui/material'; +import { Box } from '@mui/system'; + +const Banner5 = () => { + return ( + + + + + + Oop, Your cart is empty! + + Get back to shopping and get
rewards from it. +
+ + +
+
+
+ ); +}; + +export default Banner5; + +`} +
+ + ); +}; + +export default EmptyCartCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/ErrorBannerCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/ErrorBannerCode.tsx new file mode 100644 index 0000000..511e372 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/ErrorBannerCode.tsx @@ -0,0 +1,39 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ErrorBannerCode = () => { + return ( + <> + + {` +import React from 'react'; +import { CardContent, Typography, Button, Card } from '@mui/material'; +import { Box } from '@mui/system'; + +const Banner4 = () => { + return ( + + + + star + + Oops something went wrong! + + Trying again to bypasses these
temporary error. +
+ + +
+
+
+ ); +}; + +export default Banner4; +`} +
+ + ); +}; + +export default ErrorBannerCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/FriendCardCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/FriendCardCode.tsx new file mode 100644 index 0000000..7edc75c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/FriendCardCode.tsx @@ -0,0 +1,51 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const FriendCard = () => { + return ( + <> + + {` +import React from 'react'; +import { CardContent, Typography, Button, Avatar, Badge, Card } from '@mui/material'; +import { Box, Stack } from '@mui/system'; + +const Banner3 = () => { + return ( + + + + Mutual Friend Revealed + + + + + + + + Tommoie Henderson + + + Accept the request and
type a message +
+ + + + + +
+
+
+ ); +}; + +export default Banner3; +`} +
+ + ); +}; + +export default FriendCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/NotificationCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/NotificationCode.tsx new file mode 100644 index 0000000..048e070 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/NotificationCode.tsx @@ -0,0 +1,40 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const NotificationCode = () => { + return ( + <> + + {` +import React from 'react'; +import { CardContent, Typography, Button, Card } from '@mui/material'; +import { Box } from '@mui/system'; + +const Banner2 = () => { + return ( + + + + Level Up + + + star + + You reach all Notifications + Congratulations,
Tap to continue next task.
+ + +
+
+
+ ); +}; + +export default Banner2; +`} +
+ + ); +}; + +export default NotificationCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/TransectionCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/TransectionCode.tsx new file mode 100644 index 0000000..39f1a24 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/banners/code/TransectionCode.tsx @@ -0,0 +1,66 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const Transection = () => { + return ( + <> + + {` +import { Card, CardContent, Typography, Button, Box, Grid2 as Grid } from '@mui/material'; + +const Banner1 = () => { + return ( + theme.palette.secondary.light, + py: 0, + overflow: 'hidden', + position: 'relative', + }} + > + + + + + Track your every Transaction Easily + + Track and record your every income and expence easily to control your balance + + + + + + + {"trackBg"} + + + + + + ); +}; + +export default Banner1; +`} + + + ); +}; + +export default Transection; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/ComplexCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/ComplexCard.tsx new file mode 100644 index 0000000..66cc5dd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/ComplexCard.tsx @@ -0,0 +1,155 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { Link } from 'react-router'; +import { + CardContent, + Typography, + Avatar, + Grid2 as Grid, + CardMedia, + Stack, + Tooltip, + Chip, + Box, + Skeleton +} from '@mui/material'; +import ParentCard from 'src/components/shared/ParentCard'; +import { IconMessage2, IconEye, IconPoint } from '@tabler/icons-react'; +import user1 from 'src/assets/images/profile/user-1.jpg'; +import user2 from 'src/assets/images/profile/user-2.jpg'; +import user3 from 'src/assets/images/profile/user-3.jpg'; +import img1 from 'src/assets/images/blog/blog-img1.jpg'; +import img2 from 'src/assets/images/blog/blog-img2.jpg'; +import img3 from 'src/assets/images/blog/blog-img3.jpg'; + +import ComplexCardCode from './code/ComplexCardCode'; +import BlankCard from '../../shared/BlankCard'; + +interface cardType { + avatar: string; + coveravatar: string; + title: string; + category: string; + name: string; + view: string; + comments: string; + time: string; +} + +const complexCard: cardType[] = [ + { + avatar: user1, + coveravatar: img1, + title: 'As yen tumbles, gadget-loving Japan goes for secondhand iPhones', + category: 'Social', + name: 'Georgeanna Ramero', + view: '9,125', + comments: '3', + time: 'Mon, Dec 19', + }, + { + avatar: user2, + coveravatar: img2, + title: 'Intel loses bid to revive antitrust case against patent foe Fortress', + category: 'Gadget', + name: 'Georgeanna Ramero', + view: '4,150', + comments: '38', + time: 'Sun, Dec 18', + }, + { + avatar: user3, + coveravatar: img3, + title: 'COVID outbreak deepens as more lockdowns loom in China', + category: 'Health', + name: 'Georgeanna Ramero', + view: '9,480', + comments: '12', + time: 'Sat, Dec 17', + }, +]; + +const ComplexCard = () => { + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 700); + + return () => clearTimeout(timer); + }, []); + + return ( + (} > + + {complexCard.map((author, index) => ( + + + <> + + {isLoading ? ( + + ) : ( + + )} + + + + + + + theme.palette.mode === 'dark' ? theme.palette.background.default : 'white', }} + label="2 min Read" + size="small" + > + + + + + {author.title} + + + + + {author.view} + + + {author.comments} + + + + + {author.time} + + + + + + + ))} + + ) + ); +}; + +export default ComplexCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/EcommerceCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/EcommerceCard.tsx new file mode 100644 index 0000000..de8ced3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/EcommerceCard.tsx @@ -0,0 +1,119 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { Link } from 'react-router'; +import { CardContent, Typography, Grid2 as Grid, Rating, Tooltip, Fab, Stack, Skeleton } from '@mui/material'; +import img1 from 'src/assets/images/products/s4.jpg'; +import img2 from 'src/assets/images/products/s5.jpg'; +import img3 from 'src/assets/images/products/s7.jpg'; +import img4 from 'src/assets/images/products/s11.jpg'; +import BlankCard from '../../shared/BlankCard'; +import ParentCard from '../../shared/ParentCard'; +import { IconBasket } from '@tabler/icons-react'; + +import EcommerceCardCode from './code/EcommerceCardCode'; + +interface ecocardType { + title: string; + subheader: string; + photo: string; + salesPrice: number; + price: number; + rating: number; +} + +const ecoCard: ecocardType[] = [ + { + title: 'Boat Headphone', + subheader: 'September 14, 2023', + photo: img1, + salesPrice: 375, + price: 285, + rating: 4, + }, + { + title: 'MacBook Air Pro', + subheader: 'September 14, 2023', + photo: img2, + salesPrice: 650, + price: 900, + rating: 5, + }, + { + title: 'Red Valvet Dress', + subheader: 'September 14, 2023', + photo: img3, + salesPrice: 150, + price: 200, + rating: 3, + }, + { + title: 'Cute Soft Teddybear', + subheader: 'September 14, 2023', + photo: img4, + salesPrice: 285, + price: 345, + rating: 2, + }, +]; + +const EcommerceCard = () => { + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 700); + + return () => clearTimeout(timer); + }, []); + + return ( + (}> + + {ecoCard.map((product, index) => ( + + + + {isLoading ? ( + + ) : ( + img + )} + + + + + + + + {product.title} + + + ${product.price} + + ${product.salesPrice} + + + + + + + + ))} + + ) + ); +}; + +export default EcommerceCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/FollowerCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/FollowerCard.tsx new file mode 100644 index 0000000..1877375 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/FollowerCard.tsx @@ -0,0 +1,80 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { CardContent, Typography, Grid2 as Grid, Button, Avatar, Box, Stack } from '@mui/material'; +import { IconMapPin } from '@tabler/icons-react'; +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import BlankCard from '../../shared/BlankCard'; +import ParentCard from 'src/components/shared/ParentCard'; + +import FollowerCardCode from './code/FollowerCardCode'; + +interface Follower { + title: string; + location: string; + avatar: string; +} + +const followerCard: Follower[] = [ + { + title: 'Andrew Grant', + location: 'El Salvador', + avatar: img1, + }, + { + title: 'Leo Pratt', + location: 'Bulgaria', + avatar: img2, + }, + { + title: 'Charles Nunez', + location: 'Nepal', + avatar: img3, + }, +]; + +const FollowerCard = () => { + return ( + (}> + + {followerCard.map((card, index) => ( + + + + + + + + {card.title} + + {card.location} + + + + + + + + + ))} + + ) + ); +}; + +export default FollowerCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/FriendCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/FriendCard.tsx new file mode 100644 index 0000000..5da41b6 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/FriendCard.tsx @@ -0,0 +1,91 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { CardContent, Typography, Grid2 as Grid, Button, Box, AvatarGroup, Avatar, Stack } from '@mui/material'; +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; +import BlankCard from '../../shared/BlankCard'; +import ParentCard from '../../shared/ParentCard'; +import FriendCardCode from './code/FriendCardCode'; + +interface Follower { + title: string; + location: string; + avatar: string; +} + +const followerCard: Follower[] = [ + { + title: 'Andrew Grant', + location: 'El Salvador', + avatar: img1, + }, + { + title: 'Leo Pratt', + location: 'Bulgaria', + avatar: img2, + }, + { + title: 'Charles Nunez', + location: 'Nepal', + avatar: img3, + }, + { + title: 'Lora Powers', + location: 'Nepal', + avatar: img4, + }, +]; + +const FriendCard = () => { + return ( + (}> + + {followerCard.map((card, index) => ( + + + + + + + + {card.title} + + + + + + + + + 3 mutual friends + + + + + + + + + + + + ))} + + ) + ); +}; + +export default FriendCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/GiftCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/GiftCard.tsx new file mode 100644 index 0000000..1b3c8d0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/GiftCard.tsx @@ -0,0 +1,80 @@ +import React, { useEffect } from 'react'; +import { CardContent, Typography, Grid2 as Grid, Button, CardMedia, IconButton, Stack, Skeleton } from '@mui/material'; +import img1 from 'src/assets/images/products/s1.jpg'; +import img2 from 'src/assets/images/products/s2.jpg'; +import BlankCard from '../../shared/BlankCard'; +import { IconGift } from '@tabler/icons-react'; + +import ParentCard from '../../shared/ParentCard'; + +import GiftCardCode from './code/GiftCardCode'; + +interface giftType { + title: string; + avatar: string; +} + +const giftCard: giftType[] = [ + { + title: 'Andrew Grant', + avatar: img1, + }, + { + title: 'Leo Pratt', + avatar: img2, + }, +]; + +const GiftCard = () => { + + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 700); + + return () => clearTimeout(timer); + }, []); + + return ( + (}> + + {giftCard.map((card, index) => ( + + + + + + {card.title} + + + + + + + {isLoading ? ( + + ) : ( + + )} + + + + + + + ))} + + ) + ); +}; + +export default GiftCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/MusicCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/MusicCard.tsx new file mode 100644 index 0000000..4ea9268 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/MusicCard.tsx @@ -0,0 +1,97 @@ +import React, { useEffect } from 'react'; +import { CardContent, Typography, Grid2 as Grid, Card, CardMedia, Box, IconButton, Stack, Skeleton } from '@mui/material'; +import img1 from 'src/assets/images/blog/blog-img5.jpg'; +import img2 from 'src/assets/images/blog/blog-img4.jpg'; +import img3 from 'src/assets/images/blog/blog-img3.jpg'; +import { IconPlayerPlay, IconPlayerSkipBack, IconPlayerSkipForward } from '@tabler/icons-react'; +import ParentCard from '../../shared/ParentCard'; + +import MusicCardCode from './code/MusicCardCode'; + +interface musiccardType { + title: string; + subheader: string; + img: string; +} + + +const musicCard: musiccardType[] = [ + { + title: 'Uptown Funk', + subheader: 'Jon Bon Jovi', + img: img1, + }, + { + title: 'Blank Space', + subheader: 'Madonna', + img: img2, + }, + { + title: 'Lean On', + subheader: 'Jennifer Lopez', + img: img3, + }, +]; + +const MusicCard = () => { + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 700); + + return () => clearTimeout(timer); + }, []); + + return ( + (}> + + {musicCard.map((card, index) => ( + + + + + + {card.title} + + + {card.subheader} + + + + + + + + + + + + + + + {isLoading ? ( + + ) : ( + + )} + + + ))} + + ) + ); +}; + +export default MusicCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/ProfileCard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/ProfileCard.tsx new file mode 100644 index 0000000..f5b6ad7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/ProfileCard.tsx @@ -0,0 +1,127 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; +import { CardContent, Typography, Grid2 as Grid, IconButton, Divider, Avatar, Box, Stack, Skeleton } from '@mui/material'; +import { useTheme } from '@mui/material/styles'; +import { + IconBrandFacebook, + IconBrandGithub, + IconBrandInstagram, + IconBrandTwitter, +} from '@tabler/icons-react'; +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import BlankCard from '../../shared/BlankCard'; +import ParentCard from '../../shared/ParentCard'; + +import ProfileCardCode from './code/ProfileCardCode'; + +interface SocialIcon { + name: string; + icon: any; +} + +interface ProfileCard { + name: string; + role: string; + avatar: string; +} + +const SocialIcons: SocialIcon[] = [ + { + name: 'Facebook', + icon: , + }, + { + name: 'Instagram', + icon: , + }, + { + name: 'Github', + icon: , + }, + { + name: 'Twitter', + icon: , + }, +]; + +const profileCard: ProfileCard[] = [ + { + name: 'Andrew Grant', + role: 'Technology Director', + avatar: img1, + }, + { + name: 'Leo Pratt', + role: 'Telecom Analyst', + avatar: img2, + }, + { + name: 'Charles Nunez', + role: 'Environmental Specialist', + avatar: img3, + }, +]; + +const ProfileCard = () => { + + const theme = useTheme(); + const [isLoading, setLoading] = React.useState(true); + + useEffect(() => { + const timer = setTimeout(() => { + setLoading(false); + }, 700); + + return () => clearTimeout(timer); + }, []); + + + return ( + (}> + + {profileCard.map((card, index) => ( + + + + + {isLoading ? ( + + ) : ( + + )} + + {card.name} + {card.role} + + + + + + {SocialIcons.map((sicon) => { + return {sicon.icon}; + })} + + + + ))} + + ) + ); +}; + +export default ProfileCard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/Settings.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/Settings.tsx new file mode 100644 index 0000000..89f7c24 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/Settings.tsx @@ -0,0 +1,68 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { CardContent, Typography, Avatar, Divider, Button, Box, Stack } from '@mui/material'; +import ParentCard from '../../shared/ParentCard'; +import { IconMessage, IconVolume } from '@tabler/icons-react'; + +import CustomSlider from '../../forms/theme-elements/CustomSlider'; +import CustomSwitch from '../../forms/theme-elements/CustomSwitch'; + +import SettingsCode from './code/SettingsCode'; + +const Settings = () => { + const [value3, setValue3] = React.useState(45); + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const handleChange6 = (event: any, newValue: any) => { + setValue3(newValue); + }; + + return ( + }> + + Settings + + + + + + + + Sound + + 45% + + + + + + + + + + + + + Chat + + Turn on chat during call + + + + + + + + + + + + + + + + ); +}; + +export default Settings; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/UpcomingActivity.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/UpcomingActivity.tsx new file mode 100644 index 0000000..8e31022 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/UpcomingActivity.tsx @@ -0,0 +1,117 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { Stack, Typography, Avatar, Box } from '@mui/material'; +import ParentCard from '../../shared/ParentCard'; +import { IconDatabase, IconMail, IconMapPin, IconPhone, IconScreenShare } from '@tabler/icons-react'; + +import UpcomingActivityCode from './code/UpcomingActivityCode'; + +const UpcomingActivity = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.primary.light; + const error = theme.palette.error.main; + const errorlight = theme.palette.error.light; + const warning = theme.palette.warning.main; + const warninglight = theme.palette.warning.light; + const secondary = theme.palette.secondary.main; + const secondarylight = theme.palette.secondary.light; + const success = theme.palette.success.main; + const successlight = theme.palette.success.light; + + interface statType { + title: string; + subtitle: string; + time: number; + color: string; + lightcolor: string; + icon: any; + } + + const stats: statType[] = [ + { + title: 'Trip to singapore', + subtitle: 'working on', + time: 5, + color: primary, + lightcolor: primarylight, + icon: , + }, + { + title: 'Archived Data', + subtitle: 'working on', + time: 10, + color: secondary, + lightcolor: secondarylight, + icon: , + }, + { + title: 'Meeting with client', + subtitle: 'pending', + time: 15, + color: warning, + lightcolor: warninglight, + icon: , + }, + { + title: 'Screening Task Team', + subtitle: 'working on', + time: 20, + color: error, + lightcolor: errorlight, + icon: , + }, + { + title: 'Send envelope to John', + subtitle: 'done', + time: 20, + color: success, + lightcolor: successlight, + icon: , + }, + ]; + + return ( + }> + <> + + {stats.map((stat, i) => ( + + + + {stat.icon} + + + + {stat.title} + + + {stat.subtitle} + + + + + + {stat.time} mins + + + ))} + + + + ); +}; + +export default UpcomingActivity; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/ComplexCardCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/ComplexCardCode.tsx new file mode 100644 index 0000000..0b2307f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/ComplexCardCode.tsx @@ -0,0 +1,129 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ComplexCardCode = () => { + return ( + <> + + {` +import React, { useEffect } from 'react'; +import { Link } from 'react-router'; +import { + CardContent, + Typography, + Avatar, + Grid2 as Grid, + Card + CardMedia, + Stack, + Tooltip, + Chip, + Box, +} from '@mui/material'; +import { IconMessage2, IconEye, IconPoint } from '@tabler/icons-react'; + +const complexCard = [ + { + avatar: "/images/profile/user-4.jpg", + coveravatar: "/images/blog/blog-img1.jpg", + title: 'As yen tumbles, gadget-loving Japan goes for secondhand iPhones', + category: 'Social', + name: 'Georgeanna Ramero', + view: '9,125', + comments: '3', + time: 'Mon, Dec 19', + }, + { + avatar: "/images/profile/user-5.jpg", + coveravatar: "/images/blog/blog-img2.jpg", + title: 'Intel loses bid to revive antitrust case against patent foe Fortress', + category: 'Gadget', + name: 'Georgeanna Ramero', + view: '4,150', + comments: '38', + time: 'Sun, Dec 18', + }, + { + avatar: "/images/profile/user-3.jpg", + coveravatar: "/images/blog/blog-img3.jpg", + title: 'COVID outbreak deepens as more lockdowns loom in China', + category: 'Health', + name: 'Georgeanna Ramero', + view: '9,480', + comments: '12', + time: 'Sat, Dec 17', + }, +]; + +const ComplexCard = () => { + return ( + + {complexCard.map((author, index) => ( + + + <> + + + + + + + + + + + + + + {author.title} + + + + + {author.view} + + + {author.comments} + + + + + {author.time} + + + + + + + ))} + + ); +}; + +export default ComplexCard; +`} + + + ); +}; + +export default ComplexCardCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/EcommerceCardCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/EcommerceCardCode.tsx new file mode 100644 index 0000000..a22e3d8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/EcommerceCardCode.tsx @@ -0,0 +1,100 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const EcommerceCardCode = () => { + return ( + <> + + {` +import React, { useEffect } from 'react'; +import { Link } from 'react-router'; +import { CardContent, Typography, Grid2 as Grid, Rating, Tooltip, Fab, Card } from '@mui/material'; +import { Stack } from '@mui/system'; +import { IconBasket } from '@tabler/icons-react'; +import Image from 'next/image'; + +const ecoCard = [ + { + title: 'Boat Headphone', + subheader: 'September 14, 2023', + photo: "/images/products/s4.jpg", + salesPrice: 375, + price: 285, + rating: 4, + }, + { + title: 'MacBook Air Pro', + subheader: 'September 14, 2023', + photo: "/images/products/s5.jpg", + salesPrice: 650, + price: 900, + rating: 5, + }, + { + title: 'Red Valvet Dress', + subheader: 'September 14, 2023', + photo: "/images/products/s7.jpg", + salesPrice: 150, + price: 200, + rating: 3, + }, + { + title: 'Cute Soft Teddybear', + subheader: 'September 14, 2023', + photo: "/images/products/s11.jpg", + salesPrice: 285, + price: 345, + rating: 2, + }, +]; + +const EcommerceCard = () => { + return ( + + {ecoCard.map((product, index) => ( + + + + img + + + + + + + + {product.title} + + + {product.price} + + {product.salesPrice} + + + + + + + + ))} + + ); +}; + +export default EcommerceCard; + +`} + + + ); +}; + +export default EcommerceCardCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/FollowerCardCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/FollowerCardCode.tsx new file mode 100644 index 0000000..41030b7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/FollowerCardCode.tsx @@ -0,0 +1,77 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const FollowerCardCode = () => { + return ( + <> + + {` +import React from 'react'; +import { CardContent, Typography, Grid2 as Grid, Button, Avatar, Box, Card } from '@mui/material'; +import { Stack } from '@mui/system'; +import { IconMapPin } from '@tabler/icons-react'; + +const followerCard = [ + { + title: 'Andrew Grant', + location: 'El Salvador', + avatar: "/images/profile/user-4.jpg", + }, + { + title: 'Leo Pratt', + location: 'Bulgaria', + avatar: "/images/profile/user-2.jpg", + }, + { + title: 'Charles Nunez', + location: 'Nepal', + avatar: "/images/profile/user-3.jpg", + }, +]; + +const FollowerCard = () => { + return ( + + {followerCard.map((card, index) => ( + + + + + + + + {card.title} + + {card.location} + + + + + + + + + ))} + + ); +}; + +export default FollowerCard; +`} + + + ); +}; + +export default FollowerCardCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/FriendCardCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/FriendCardCode.tsx new file mode 100644 index 0000000..3c8535c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/FriendCardCode.tsx @@ -0,0 +1,82 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const FriendCardCode = () => { + return ( + <> + + {` +import React from 'react'; +import { CardContent, Typography, Grid2 as Grid, Button, Box, AvatarGroup, Avatar, Card } from '@mui/material'; +import { Stack } from '@mui/system'; + +const followerCard = [ + { + title: 'Andrew Grant', + location: 'El Salvador', + avatar: "/images/profile/user-5.jpg", + }, + { + title: 'Leo Pratt', + location: 'Bulgaria', + avatar: "/images/profile/user-2.jpg", + }, + { + title: 'Charles Nunez', + location: 'Nepal', + avatar: "/images/profile/user-3.jpg", + }, + { + title: 'Lora Powers', + location: 'Nepal', + avatar: "/images/profile/user-2.jpg", + }, +]; + +const FriendCard = () => { + return ( + + {followerCard.map((card, index) => ( + + + + + + + + {card.title} + + + + + + + + + 3 mutual friends + + + + + + + + + + + + ))} + + ); +}; + +export default FriendCard; +`} + + + ); +}; + +export default FriendCardCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/GiftCardCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/GiftCardCode.tsx new file mode 100644 index 0000000..780afa1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/GiftCardCode.tsx @@ -0,0 +1,66 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const GiftCardCode = () => { + return ( + <> + + {` +import React, { useEffect } from 'react'; +import { CardContent, Typography, Grid2 as Grid, Button, CardMedia, IconButton, Card } from '@mui/material'; +import { Stack } from '@mui/system'; +import { IconGift } from '@tabler/icons-react'; + +const giftCard = [ + { + title: 'Andrew Grant', + avatar: "/images/products/s1.jpg", + }, + { + title: 'Leo Pratt', + avatar: "/images/products/s2.jpg", + }, +]; + +const GiftCard = () => { + return ( + + {giftCard.map((card, index) => ( + + + + + + {card.title} + + + + + + + + + + + + + + + ))} + + ); +}; + +export default GiftCard; +`} + + + ); +}; + +export default GiftCardCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/MusicCardCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/MusicCardCode.tsx new file mode 100644 index 0000000..2c5e514 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/MusicCardCode.tsx @@ -0,0 +1,85 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const MusicCardCode = () => { + return ( + <> + + {` +import React, { useEffect } from 'react'; +import { CardContent, Typography, Grid2 as Grid, Card, CardMedia, Box, IconButton, Stack, Skeleton } from '@mui/material'; +import { IconPlayerPlay, IconPlayerSkipBack, IconPlayerSkipForward } from '@tabler/icons-react'; + +const musicCard = [ + { + title: 'Uptown Funk', + subheader: 'Jon Bon Jovi', + img: "/images/blog/blog-img5.jpg", + }, + { + title: 'Blank Space', + subheader: 'Madonna', + img: "/images/blog/blog-img4.jpg", + }, + { + title: 'Lean On', + subheader: 'Jennifer Lopez', + img: "/images/blog/blog-img3.jpg", + }, +]; + +const MusicCard = () => { + return ( + + {musicCard.map((card, index) => ( + + + + + + {card.title} + + + {card.subheader} + + + + + + + + + + + + + + + {isLoading ? ( + + ) : ( + + )} + + + ))} + + ); +}; + +export default MusicCard; +`} + + + ); +}; + +export default MusicCardCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/ProfileCardCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/ProfileCardCode.tsx new file mode 100644 index 0000000..e8ba494 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/ProfileCardCode.tsx @@ -0,0 +1,104 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const ProfileCardCode = () => { + return ( + <> + + {` +import React, { useEffect } from 'react'; +import { CardContent, Typography, Grid2 as Grid, IconButton, Divider, Avatar, Box, Card } from '@mui/material'; +import { useTheme } from '@mui/material/styles'; +import { Stack } from '@mui/system'; +import { + IconBrandFacebook, + IconBrandGithub, + IconBrandInstagram, + IconBrandTwitter, +} from '@tabler/icons-react'; + +const SocialIcons = [ + { + name: 'Facebook', + icon: , + }, + { + name: 'Instagram', + icon: , + }, + { + name: 'Github', + icon: , + }, + { + name: 'Twitter', + icon: , + }, +]; + +const profileCard = [ + { + name: 'Andrew Grant', + role: 'Technology Director', + avatar: "/images/profile/user-3.jpg", + }, + { + name: 'Leo Pratt', + role: 'Telecom Analyst', + avatar: "/images/profile/user-4.jpg", + }, + { + name: 'Charles Nunez', + role: 'Environmental Specialist', + avatar: "/images/profile/user-5.jpg", + }, +]; + +const ProfileCard = () => { + const theme = useTheme(); + + return ( + + {profileCard.map((card, index) => ( + + + + + + + {card.name} + {card.role} + + + + + + {SocialIcons.map((sicon) => { + return {sicon.icon}; + })} + + + + ))} + + ); +}; + +export default ProfileCard; +`} + + + ); +}; + +export default ProfileCardCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/SettingsCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/SettingsCode.tsx new file mode 100644 index 0000000..a02a273 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/SettingsCode.tsx @@ -0,0 +1,127 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const SettingsCode = () => { + return ( + <> + + {` +import React from 'react'; +import { CardContent, Typography, Avatar, Divider, Button, Card } from '@mui/material'; +import { Box, Stack } from '@mui/system'; +import { IconMessage, IconVolume } from '@tabler/icons-react'; +import { styled } from '@mui/material/styles'; +import { Slider } from '@mui/material'; +import { Switch } from '@mui/material'; + +const CustomSlider = styled(Slider)(({ theme }) => ({ + '& .MuiSlider-rail': { + height: '9px', + borderRadius: '9px', + opacity: '1', + backgroundColor: theme.palette.grey[200], + }, + '& .MuiSlider-thumb': { + borderRadius: '50%', + backgroundColor: () => theme.palette.secondary.main, + width: '23px', + height: '23px', + }, + '& .MuiSlider-track': { + height: '9px', + borderRadius: '9px', + }, +})); + +const CustomSwitch = styled((props: any) => )(({ theme }) => ({ + '&.MuiSwitch-root': { + width: '68px', + height: '49px', + }, + '& .MuiButtonBase-root': { + top: '6px', + left: '6px', + }, + '& .MuiButtonBase-root.Mui-checked .MuiSwitch-thumb': { + backgroundColor: 'primary.main', + }, + '& .MuiSwitch-thumb': { + width: '18px', + height: '18px', + borderRadius: '6px', + }, + + '& .MuiSwitch-track': { + backgroundColor: theme.palette.grey[200], + opacity: 1, + borderRadius: '5px', + }, + '& .MuiSwitch-switchBase': { + '&.Mui-checked': { + '& + .MuiSwitch-track': { + backgroundColor: 'primary', + opacity: 0.18, + }, + }, + }, +})); + +const Settings = () => { + const [value3, setValue3] = React.useState(45); + const handleChange6 = (event: any, newValue: any) => { + setValue3(newValue); + }; + + return ( + + + Settings + + + + + + + + Sound + + 45% + + + + + + + + + + + + + Chat + + Turn on chat during call + + + + + + + + + + + + + + + + ); +}; + +export default Settings; +`} + + + ); +}; + +export default SettingsCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/UpcomingActivityCode.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/UpcomingActivityCode.tsx new file mode 100644 index 0000000..bed2e8c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/cards/code/UpcomingActivityCode.tsx @@ -0,0 +1,115 @@ +import CodeDialog from 'src/components/shared/CodeDialog'; +const UpcomingActivityCode = () => { + return ( + <> + + {` +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { Stack, Typography, Avatar, Box } from '@mui/material'; +import { IconDatabase, IconMail, IconMapPin, IconPhone, IconScreenShare } from '@tabler/icons-react'; + + +const UpcomingActivity = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.primary.light; + const error = theme.palette.error.main; + const errorlight = theme.palette.error.light; + const warning = theme.palette.warning.main; + const warninglight = theme.palette.warning.light; + const secondary = theme.palette.secondary.main; + const secondarylight = theme.palette.secondary.light; + const success = theme.palette.success.main; + const successlight = theme.palette.success.light; + + const stats = [ + { + title: 'Trip to singapore', + subtitle: 'working on', + time: 5, + color: primary, + lightcolor: primarylight, + icon: , + }, + { + title: 'Archived Data', + subtitle: 'working on', + time: 10, + color: secondary, + lightcolor: secondarylight, + icon: , + }, + { + title: 'Meeting with client', + subtitle: 'pending', + time: 15, + color: warning, + lightcolor: warninglight, + icon: , + }, + { + title: 'Screening Task Team', + subtitle: 'working on', + time: 20, + color: error, + lightcolor: errorlight, + icon: , + }, + { + title: 'Send envelope to John', + subtitle: 'done', + time: 20, + color: success, + lightcolor: successlight, + icon: , + }, + ]; + + return ( + <> + + {stats.map((stat, i) => ( + + + + {stat.icon} + + + + {stat.title} + + + {stat.subtitle} + + + + + + {stat.time} mins + + + ))} + + + ); +}; + +export default UpcomingActivity; +`} + + + ); +}; + +export default UpcomingActivityCode; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/CurrentValue.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/CurrentValue.tsx new file mode 100644 index 0000000..6bacc2e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/CurrentValue.tsx @@ -0,0 +1,330 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { Box, Button, CardContent, Grid2 as Grid, Typography, Stack } from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; +import { Props } from 'react-apexcharts'; + + +const CurrentValue = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.primary.light; + const secondary = theme.palette.secondary.main; + const textColor = theme.palette.mode === 'dark' ? 'rgba(255,255,255,0.8)' : '#2A3547'; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 200, + stacked: true, + sparkline: { + enabled: true, + }, + }, + colors: [primary, primary], + plotOptions: { + bar: { + horizontal: false, + barHeight: '60%', + columnWidth: '20%', + borderRadius: [6], + borderRadiusApplication: 'end', + borderRadiusWhenStacked: 'all', + }, + }, + stroke: { + show: false, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + show: false, + padding: { + top: 0, + right: 0, + bottom: 0, + left: 0, + }, + }, + yaxis: { + min: -5, + max: 5, + tickAmount: 4, + }, + xaxis: { + categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May'], + axisTicks: { + show: false, + }, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + }, + }; + const seriescolumnchart = [ + { + name: '', + data: [2.5, 3.7, 3.2, 2.6, 1.9, 2.5], + }, + { + name: '', + data: [-2.8, -1.1, -3.0, -1.5, -1.9, -2.8], + }, + ]; + + // chart 2 + const optionscolumn2chart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 200, + stacked: true, + sparkline: { + enabled: true, + }, + }, + colors: [secondary, secondary], + plotOptions: { + bar: { + horizontal: false, + barHeight: '60%', + columnWidth: '20%', + borderRadius: [6], + borderRadiusApplication: 'end', + borderRadiusWhenStacked: 'all', + }, + }, + stroke: { + show: false, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + show: false, + padding: { + top: 0, + right: 0, + bottom: 0, + left: 0, + }, + }, + yaxis: { + min: -5, + max: 5, + tickAmount: 4, + }, + xaxis: { + categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May'], + axisTicks: { + show: false, + }, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + }, + }; + const seriescolumn2chart = [ + { + name: '', + data: [2.5, 3.7, 3.2, 2.6, 1.9, 2.5], + }, + { + name: '', + data: [-2.8, -1.1, -3.0, -1.5, -1.9, -2.8], + }, + ]; + + // chart 3 + const optionscolumn3chart: Props = { + chart: { + type: 'donut', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + + toolbar: { + show: false, + }, + height: 220, + }, + labels: ['Income', 'Current', 'Expance'], + colors: [primary, primarylight, secondary], + plotOptions: { + pie: { + startAngle: 0, + endAngle: 360, + donut: { + size: '89%', + background: 'transparent', + + labels: { + show: true, + name: { + show: true, + offsetY: 7, + }, + value: { + show: false, + }, + total: { + show: true, + color: textColor, + fontSize: '20px', + fontWeight: '600', + label: '$98,260', + }, + }, + }, + }, + }, + dataLabels: { + enabled: false, + }, + stroke: { + show: false, + }, + legend: { + show: false, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + }, + }; + const seriescolumn3chart = [55, 55, 55]; + + return ( + ( + + + Current Value + + + + + + + + {/* 1 */} + + + + + + + + + Income + + + $25,260 + + +1.25% + + + + + + + {/* 2 */} + + + + + + + + + Expance + + + $12,260 + + +4.25% + + + + + + + {/* 3 */} + + + + + + + + + Current Year + + + $98,260 + + +2.5% + + + + + + + + + ) + ); +}; + +export default CurrentValue; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/Earned.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/Earned.tsx new file mode 100644 index 0000000..7b1614b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/Earned.tsx @@ -0,0 +1,82 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { CardContent, Typography, Stack } from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; +import { Props } from 'react-apexcharts'; + +const Earned = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'area', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 90, + sparkline: { + enabled: true, + }, + }, + colors: [primary], + + stroke: { + curve: 'straight', + width: 2, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + show: false, + }, + xaxis: { + axisBorder: { + show: true, + }, + axisTicks: { + show: false, + }, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + }, + }; + const seriescolumnchart = [ + { + name: '', + data: [0, 3, 1, 2, 8, 1, 5, 1], + }, + ]; + + return ( + + + 2,545 + + + Earned + + + +1.20% + + + + + + ); +}; + +export default Earned; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/Followers.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/Followers.tsx new file mode 100644 index 0000000..675bc60 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/Followers.tsx @@ -0,0 +1,83 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { CardContent, Typography, Stack } from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; +import { Props } from 'react-apexcharts'; + + +const Followers = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'area', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 90, + sparkline: { + enabled: true, + }, + }, + colors: [primary], + + stroke: { + curve: 'straight', + width: 2, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + show: false, + }, + xaxis: { + axisBorder: { + show: true, + }, + axisTicks: { + show: false, + }, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + }, + }; + const seriescolumnchart = [ + { + name: '', + data: [0, 150, 110, 240, 200, 200, 300, 200], + }, + ]; + + return ( + + + 2,545 + + + Followers + + + +1.20% + + + + + + ); +}; + +export default Followers; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/MostVisited.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/MostVisited.tsx new file mode 100644 index 0000000..a49f508 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/MostVisited.tsx @@ -0,0 +1,137 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { CardContent, Typography, MenuItem, Stack, Box } from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; +import CustomSelect from '../../forms/theme-elements/CustomSelect'; +import { Props } from 'react-apexcharts'; + +const MostVisited = () => { + // for select + const [month, setMonth] = React.useState('1'); + + const handleChange = (event: React.ChangeEvent) => { + setMonth(event.target.value); + }; + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 250, + stacked: true, + }, + colors: [primary, secondary], + plotOptions: { + bar: { + borderRadius: [6], + horizontal: false, + barHeight: '60%', + columnWidth: '40%', + borderRadiusApplication: 'end', + borderRadiusWhenStacked: 'all', + }, + }, + stroke: { + show: false, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + show: false, + }, + yaxis: { + tickAmount: 4, + }, + xaxis: { + categories: ['01', '02', '03', '04', '05', '06'], + axisTicks: { + show: false, + }, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + fillSeriesColor: false, + }, + }; + const seriescolumnchart = [ + { + name: 'San Francisco', + data: [44, 55, 41, 67, 22, 43], + }, + { + name: 'Diego', + data: [13, 23, 20, 8, 13, 27], + }, + ]; + + return ( + + + + Most Visited + + March 2023 + April 2023 + May 2023 + + + + + + + + + + San Francisco + + + + + + Diego + + + + + + ); +}; + +export default MostVisited; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/PageImpressions.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/PageImpressions.tsx new file mode 100644 index 0000000..08047f9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/PageImpressions.tsx @@ -0,0 +1,115 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { CardContent, Typography, Avatar, Grid2 as Grid, Stack } from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; +import { IconArrowDownRight } from '@tabler/icons-react'; +import { Props } from 'react-apexcharts'; + +const PageImpressions = () => { + // chart color + const theme = useTheme(); + const secondary = theme.palette.secondary.main; + const secondarylight = theme.palette.secondary.light; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 100, + sparkline: { + enabled: true, + }, + }, + colors: [secondarylight, secondarylight, secondary, secondarylight, secondarylight, secondarylight], + plotOptions: { + bar: { + borderRadius: 4, + columnWidth: '50%', + distributed: true, + endingShape: 'rounded', + }, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + yaxis: { + lines: { + show: false, + }, + }, + }, + xaxis: { + labels: { + show: false, + }, + axisBorder: { + show: false, + }, + axisTicks: { + show: false, + }, + }, + yaxis: { + labels: { + show: false, + }, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + }, + }; + const seriescolumnchart = [ + { + name: '', + data: [20, 15, 30, 25, 10], + }, + ]; + + return ( + ( + + Page Impressions + + + + + $456,120 + + (Change Yesterday) + + + + + + + +9% + + + + + + + + + ) + ); +}; + +export default PageImpressions; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/Views.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/Views.tsx new file mode 100644 index 0000000..6d48544 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/components/widgets/charts/Views.tsx @@ -0,0 +1,109 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import { CardContent, Typography, Stack } from '@mui/material'; +import BlankCard from '../../shared/BlankCard'; +import { Props } from 'react-apexcharts'; + +const Views = () => { + // chart color + const theme = useTheme(); + const secondary = theme.palette.secondary.main; + const secondarylight = theme.palette.secondary.light; + + // chart + const optionscolumnchart: Props = { + chart: { + type: 'bar', + fontFamily: "'Plus Jakarta Sans', sans-serif;", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + height: 80, + sparkline: { + enabled: true, + }, + }, + colors: [ + secondarylight, + secondarylight, + secondary, + secondarylight, + secondarylight, + secondarylight, + secondarylight, + secondarylight, + ], + plotOptions: { + bar: { + borderRadius: 4, + columnWidth: '50%', + distributed: true, + endingShape: 'rounded', + }, + }, + dataLabels: { + enabled: false, + }, + legend: { + show: false, + }, + grid: { + show: false, + padding: { + top: 0, + right: 0, + bottom: 0, + left: 0, + }, + }, + xaxis: { + categories: ['M', 'T', 'W', 'T', 'F', 'S', 'S'], + labels: { + show: false, + }, + axisBorder: { + show: false, + }, + axisTicks: { + show: false, + }, + }, + yaxis: { + labels: { + show: false, + }, + }, + tooltip: { + theme: theme.palette.mode === 'dark' ? 'dark' : 'light', + }, + }; + const seriescolumnchart = [ + { + name: '', + data: [20, 15, 30, 25, 10, 18, 20], + }, + ]; + + return ( + + + 15,480 + + + Views + + + -4.150% + + + + + + ); +}; + +export default Views; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/context/InvoiceContext/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/context/InvoiceContext/index.tsx new file mode 100644 index 0000000..1ba5e6c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/context/InvoiceContext/index.tsx @@ -0,0 +1,78 @@ +'use client' +import React, { createContext, useEffect, useState } from 'react'; +import { InvoiceList } from 'src/types/apps/invoice'; + +import axios from '../../utils/axios'; + +interface InvoiceContextType { + invoices: InvoiceList[]; + loading: boolean; + error: Error | null; + deleteEmail: () => {}, + addInvoice: (newInvoice: InvoiceList) => void; + updateInvoice: (updatedInvoice: InvoiceList) => void; +} + +export const InvoiceContext = createContext(undefined); + +export const InvoiceProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => { + const [invoices, setInvoices] = useState([]); + const [loading, setLoading] = useState(true); + const [error] = useState(null); + + useEffect(() => { + const fetchData = async () => { + try { + const response = await axios.get('/api/data/invoicedata'); + setInvoices(response.data); + setLoading(false); + } catch (error) { + // setError(error); + setLoading(false); + } + }; + + fetchData(); + }, []); + + // Function to delete an invoice + const deleteInvoice = async (id: number) => { + try { + + await axios.delete('/api/data/invoicedata/deleteinvoice', { data: { invoiceId: id } }); + setInvoices((prevInvoices) => prevInvoices.filter((invoice) => invoice.id !== id)); + } catch (error) { + console.error('Error deleting invoice:', error); + + } + }; + + const addInvoice = async (newInvoice: InvoiceList) => { + try { + const response = await axios.post('/api/data/invoicedata/addinvoice', newInvoice); + const addedInvoice = response.data; + setInvoices((prevInvoices) => [...prevInvoices, addedInvoice]); + } catch (error) { + console.error('Error adding invoice:', error); + } + }; + + // Function to update an invoice + const updateInvoice = async (updatedInvoice: InvoiceList) => { + try { + const response = await axios.put('/api/data/invoicedata/updateinvoice', updatedInvoice); + const updated = response.data; + setInvoices((prevInvoices) => + prevInvoices.map((invoice) => (invoice.id === updated.id ? updated : invoice)) + ); + } catch (error) { + console.error('Error updating invoice:', error); + } + }; + + return ( + + {children} + + ); +}; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/context/kanbancontext/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/context/kanbancontext/index.tsx new file mode 100644 index 0000000..9285156 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/context/kanbancontext/index.tsx @@ -0,0 +1,130 @@ + +import React, { createContext, useState, useEffect, ReactNode } from 'react'; +import axios from '../../utils/axios'; + +import { TodoCategory } from 'src/types/apps/kanban'; + +interface KanbanDataContextProps { + children: ReactNode; +} + +interface KanbanContextType { + todoCategories: TodoCategory[]; + addCategory: (categoryName: string) => Promise; + deleteCategory: (categoryId: string) => Promise; + clearAllTasks: (categoryId: string) => Promise; + deleteTodo: (taskId: number) => Promise; + setError: (errorMessage: string | null) => void; + moveTask: ( + taskId: number, + sourceCategoryId: string, + destinationCategoryId: string, + sourceIndex: number, + destinationIndex: number + ) => void; +} + +export const KanbanDataContext = createContext({} as KanbanContextType); + +export const KanbanDataContextProvider: React.FC = ({ children }) => { + const [todoCategories, setTodoCategories] = useState([]); + const [, setError] = useState(null); + + // Fetch todo data from the API + useEffect(() => { + const fetchData = async () => { + try { + const response = await axios.get('/api/TodoData'); + setTodoCategories(response.data); + setError(null); + } catch (error: any) { + handleError(error.message); + } + }; + fetchData(); + }, []); + + + + const moveTask = (_taskId: any, sourceCategoryId: any, destinationCategoryId: any, sourceIndex: number, destinationIndex: number) => { + + setTodoCategories((prevCategories) => { + // Find the source and destination categories + const sourceCategoryIndex = prevCategories.findIndex(cat => cat.id.toString() === sourceCategoryId); + const destinationCategoryIndex = prevCategories.findIndex(cat => cat.id.toString() === destinationCategoryId); + + if (sourceCategoryIndex === -1 || destinationCategoryIndex === -1) { + return prevCategories; // Return previous state if categories are not found + } + // Clone the source and destination categories + const updatedCategories = [...prevCategories]; + const sourceCategory = { ...updatedCategories[sourceCategoryIndex] }; + const destinationCategory = { ...updatedCategories[destinationCategoryIndex] }; + + // Remove the task from the source category + const taskToMove = sourceCategory.child.splice(sourceIndex, 1)[0]; + + // Insert the task into the destination category at the specified index + destinationCategory.child.splice(destinationIndex, 0, taskToMove); + + // Update the categories in the state + updatedCategories[sourceCategoryIndex] = sourceCategory; + updatedCategories[destinationCategoryIndex] = destinationCategory; + + return updatedCategories; + }); + }; + + const handleError = (errorMessage: string) => { + setError(errorMessage); + }; + + const deleteCategory = async (categoryId: string) => { + try { + const response = await axios.delete(`/api/TodoData?id=${categoryId}`); + setTodoCategories(response.data); + setError(null); + } catch (error: any) { + handleError(error.message); + } + }; + + const clearAllTasks = async (categoryId: string) => { + try { + const response = await axios.delete(`/api/TodoData/clearTasks?id=${categoryId}`); + setTodoCategories(response.data); + setError(null); + } catch (error: any) { + handleError(error.message); + } + }; + + const addCategory = async (categoryName: string) => { + try { + const response = await axios.post('/api/TodoData/addCategory', { categoryName }); + setTodoCategories((prevCategories) => [...prevCategories, response.data]); + setError(null); + } catch (error: any) { + handleError(error.message); + } + }; + + const deleteTodo = async (taskId: number) => { + try { + const response = await axios.delete(`/api/TodoData/deleteTask?id=${taskId}`); + setTodoCategories(response.data); + } catch (error: any) { + handleError(error.message); + } + }; + + return ( + + {children} + + ); +}; + + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/index.css b/Modernize/Modernize/react-version/packages/typescript/main/src/index.css new file mode 100644 index 0000000..b8d99af --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/index.css @@ -0,0 +1,69 @@ +:root { + font-family: Inter, system-ui, Avenir, Helvetica, Arial, sans-serif; + line-height: 1.5; + font-weight: 400; + + color-scheme: light dark; + color: rgba(255, 255, 255, 0.87); + background-color: #242424; + + font-synthesis: none; + text-rendering: optimizeLegibility; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; + -webkit-text-size-adjust: 100%; +} + +a { + font-weight: 500; + color: #646cff; + text-decoration: inherit; +} +a:hover { + color: #535bf2; +} + +body { + margin: 0; + display: flex; + place-items: center; + min-width: 320px; + min-height: 100vh; +} + +h1 { + font-size: 3.2em; + line-height: 1.1; +} + +button { + border-radius: 8px; + border: 1px solid transparent; + padding: 0.6em 1.2em; + font-size: 1em; + font-weight: 500; + font-family: inherit; + background-color: #1a1a1a; + cursor: pointer; + transition: border-color 0.25s; +} +button:hover { + border-color: #646cff; +} +button:focus, +button:focus-visible { + outline: 4px auto -webkit-focus-ring-color; +} + +@media (prefers-color-scheme: light) { + :root { + color: #213547; + background-color: #ffffff; + } + a:hover { + color: #747bff; + } + button { + background-color: #f9f9f9; + } +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/blank/BlankLayout.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/blank/BlankLayout.tsx new file mode 100644 index 0000000..1b5bd19 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/blank/BlankLayout.tsx @@ -0,0 +1,11 @@ +import { Outlet } from "react-router"; +import LoadingBar from '../../LoadingBar'; + +const BlankLayout = () => ( + <> + + + +); + +export default BlankLayout; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/FullLayout.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/FullLayout.tsx new file mode 100644 index 0000000..eaaf941 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/FullLayout.tsx @@ -0,0 +1,89 @@ +import { FC } from 'react'; +import { styled, Container, Box, useTheme } from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import { Outlet } from 'react-router'; +import { AppState } from 'src/store/Store'; +import Header from './vertical/header/Header'; +import Sidebar from './vertical/sidebar/Sidebar'; +import Customizer from './shared/customizer/Customizer'; +import Navigation from '../full/horizontal/navbar/Navigation'; +import HorizontalHeader from '../full/horizontal/header/Header'; +import ScrollToTop from '../../components/shared/ScrollToTop'; +import LoadingBar from '../../LoadingBar'; + +const MainWrapper = styled('div')(() => ({ + display: 'flex', + minHeight: '100vh', + width: '100%', +})); + +const PageWrapper = styled('div')(() => ({ + display: 'flex', + flexGrow: 1, + paddingBottom: '60px', + flexDirection: 'column', + zIndex: 1, + width: '100%', + backgroundColor: 'transparent', +})); + +const FullLayout: FC = () => { + const customizer = useSelector((state: AppState) => state.customizer); + + const theme = useTheme(); + + return ( + <> + + + + {/* ------------------------------------------- */} + {/* Sidebar */} + {/* ------------------------------------------- */} + {customizer.isHorizontal ? '' : } + {/* ------------------------------------------- */} + {/* Main Wrapper */} + {/* ------------------------------------------- */} + + {/* ------------------------------------------- */} + {/* Header */} + {/* ------------------------------------------- */} + {customizer.isHorizontal ? :
} + {/* PageContent */} + {customizer.isHorizontal ? : ''} + + {/* ------------------------------------------- */} + {/* PageContent */} + {/* ------------------------------------------- */} + + + + + + + + {/* ------------------------------------------- */} + {/* End Page */} + {/* ------------------------------------------- */} + + + + + + + ); +}; + +export default FullLayout; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/header/Header.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/header/Header.tsx new file mode 100644 index 0000000..3d6c553 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/header/Header.tsx @@ -0,0 +1,110 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import * as React from 'react'; +import { + IconButton, + Box, + AppBar, + useMediaQuery, + Toolbar, + styled, + Stack, + Theme, +} from '@mui/material'; + +import { useSelector, useDispatch } from 'src/store/Store'; +import { toggleMobileSidebar, setDarkMode } from 'src/store/customizer/CustomizerSlice'; +import { IconMenu2, IconMoon, IconSun } from '@tabler/icons-react'; +import Notifications from 'src/layouts/full/vertical/header/Notification'; +import Cart from 'src/layouts/full/vertical/header/Cart'; +import Profile from 'src/layouts/full/vertical/header/Profile'; +import Search from 'src/layouts/full/vertical/header/Search'; +import Language from 'src/layouts/full/vertical/header/Language'; +import Navigation from 'src/layouts/full/vertical/header/Navigation'; +import Logo from 'src/layouts/full/shared/logo/Logo'; +import { AppState } from 'src/store/Store'; + +const Header = () => { + const lgDown = useMediaQuery((theme: Theme) => theme.breakpoints.down('lg')); + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + + // drawer + const customizer = useSelector((state: AppState) => state.customizer); + const dispatch = useDispatch(); + + const AppBarStyled = styled(AppBar)(({ theme }) => ({ + background: theme.palette.background.paper, + justifyContent: 'center', + backdropFilter: 'blur(4px)', + + [theme.breakpoints.up('lg')]: { + minHeight: customizer.TopbarHeight, + }, + })); + const ToolbarStyled = styled(Toolbar)(({ theme }) => ({ + margin: '0 auto', + width: '100%', + color: `${theme.palette.text.secondary} !important`, + })); + + return ( + + + + + + {/* ------------------------------------------- */} + {/* Toggle Button Sidebar */} + {/* ------------------------------------------- */} + {lgDown ? ( + dispatch(toggleMobileSidebar())} + > + + + ) : ( + '' + )} + {/* ------------------------------------------- */} + {/* Search Dropdown */} + {/* ------------------------------------------- */} + + {lgUp ? ( + <> + + + ) : null} + + + + {/* ------------------------------------------- */} + {/* Ecommerce Dropdown */} + {/* ------------------------------------------- */} + + {/* ------------------------------------------- */} + {/* End Ecommerce Dropdown */} + {/* ------------------------------------------- */} + + + {customizer.activeMode === 'light' ? ( + dispatch(setDarkMode('dark'))} /> + ) : ( + dispatch(setDarkMode('light'))} /> + )} + + + + + + + + ); +}; + +export default Header; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/Menudata.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/Menudata.ts new file mode 100644 index 0000000..0c7d5d8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/Menudata.ts @@ -0,0 +1,875 @@ +import { + IconHome, + IconPoint, + IconApps, + IconClipboard, + IconFileDescription, + IconBorderAll, + IconZoomCode, + IconRotate, + IconUserPlus, + IconLogin, + IconAlertCircle, + IconSettings, + IconAppWindow, + IconListTree, + IconChartHistogram, +} from '@tabler/icons-react'; +import { uniqueId } from 'lodash'; + +const Menuitems = [ + { + id: uniqueId(), + title: 'Dashboard', + icon: IconHome, + href: '/dashboards/', + children: [ + { + id: uniqueId(), + title: 'Modern', + icon: IconPoint, + href: '/dashboards/modern', + chip: 'New', + chipColor: 'secondary', + }, + { + id: uniqueId(), + title: 'eCommerce', + icon: IconPoint, + href: '/dashboards/ecommerce', + }, + ], + }, + { + id: uniqueId(), + title: 'Frontend pages', + icon: IconAppWindow, + href: '/frontend-pages/', + children: [ + { + id: uniqueId(), + title: 'Homepage', + icon: IconPoint, + href: '/frontend-pages/homepage', + }, + { + id: uniqueId(), + title: 'About Us', + icon: IconPoint, + href: '/frontend-pages/about', + }, + { + id: uniqueId(), + title: 'Blog', + icon: IconPoint, + href: '/frontend-pages/blog', + }, + { + id: uniqueId(), + title: 'Blog Details', + icon: IconPoint, + href: '/frontend-pages/blog/Blog_1', + }, + { + id: uniqueId(), + title: 'Contact', + icon: IconPoint, + href: '/frontend-pages/contact', + }, + { + id: uniqueId(), + title: 'Portfolio', + icon: IconPoint, + href: '/frontend-pages/portfolio', + }, + { + id: uniqueId(), + title: 'Pricing', + icon: IconPoint, + href: '/frontend-pages/pricing', + }, + ], + }, + { + id: uniqueId(), + title: 'Apps', + icon: IconApps, + href: '/apps/', + children: [ + { + id: uniqueId(), + title: 'Contacts', + icon: IconPoint, + href: '/apps/contacts', + }, + { + id: uniqueId(), + title: 'Chats', + icon: IconPoint, + href: '/apps/chats', + }, + { + id: uniqueId(), + title: 'Notes', + icon: IconPoint, + href: '/apps/notes', + }, + { + id: uniqueId(), + title: 'Calendar', + icon: IconPoint, + href: '/apps/calendar', + }, + { + id: uniqueId(), + title: 'Email', + icon: IconPoint, + href: '/apps/email', + }, + { + id: uniqueId(), + title: 'Tickets', + icon: IconPoint, + href: '/apps/tickets', + }, + { + id: uniqueId(), + title: 'Kanban', + icon: IconPoint, + href: '/apps/kanban', + }, + { + id: uniqueId(), + title: 'Invoice', + icon: IconPoint, + href: '/apps/invoice/', + children: [ + { + id: uniqueId(), + title: 'List', + icon: IconPoint, + href: '/apps/invoice/list', + }, + { + id: uniqueId(), + title: 'Create', + icon: IconPoint, + href: '/apps/invoice/create', + }, + { + id: uniqueId(), + title: 'Detail', + icon: IconPoint, + href: '/apps/invoice/detail/PineappleInc.', + }, + { + id: uniqueId(), + title: 'Edit', + icon: IconPoint, + href: '/apps/invoice/edit/PineappleInc.', + }, + ], + }, + { + id: uniqueId(), + title: 'User Profile', + icon: IconPoint, + href: '/user-profile', + children: [ + { + id: uniqueId(), + title: 'Profile', + icon: IconPoint, + href: '/user-profile', + }, + { + id: uniqueId(), + title: 'Followers', + icon: IconPoint, + href: '/apps/followers', + }, + { + id: uniqueId(), + title: 'Friends', + icon: IconPoint, + href: '/apps/friends', + }, + { + id: uniqueId(), + title: 'Gallery', + icon: IconPoint, + href: '/apps/gallery', + }, + ], + }, + { + id: uniqueId(), + title: 'Ecommerce', + icon: IconPoint, + href: '/apps/ecommerce/', + children: [ + { + id: uniqueId(), + title: 'Shop', + icon: IconPoint, + href: '/apps/ecommerce/shop', + }, + { + id: uniqueId(), + title: 'Detail', + icon: IconPoint, + href: '/apps/ecommerce/detail/1', + }, + { + id: uniqueId(), + title: 'List', + icon: IconPoint, + href: '/apps/ecommerce/eco-product-list', + }, + { + id: uniqueId(), + title: 'Checkout', + icon: IconPoint, + href: '/apps/ecommerce/eco-checkout', + }, + { + id: uniqueId(), + title: 'Add Product', + icon: IconPoint, + href: '/apps/ecommerce/add-product', + }, + { + id: uniqueId(), + title: 'Edit Product', + icon: IconPoint, + href: '/apps/ecommerce/edit-product', + }, + ], + }, + { + id: uniqueId(), + title: 'Blog', + icon: IconPoint, + href: '/frontend-pages/blog/', + children: [ + { + id: uniqueId(), + title: 'Posts', + icon: IconPoint, + href: '/frontend-pages/blog/', + }, + { + id: uniqueId(), + title: 'Detail', + icon: IconPoint, + href: '/frontend-pages/blog/detail/streaming-video-way-before-it-was-cool-go-dark-tomorrow', + }, + ], + }, + ], + }, + + { + id: uniqueId(), + title: 'Pages', + icon: IconClipboard, + href: '/ui-components/', + children: [ + { + id: uniqueId(), + title: 'Pricing', + icon: IconPoint, + href: '/pages/pricing', + }, + { + id: uniqueId(), + title: 'Account Setting', + icon: IconPoint, + href: '/pages/account-settings', + }, + { + id: uniqueId(), + title: 'Landingpage', + icon: IconPoint, + href: '/landingpage', + }, + { + id: uniqueId(), + title: 'FAQ', + icon: IconPoint, + href: '/pages/faq', + }, + { + id: uniqueId(), + title: 'Widgets', + icon: IconPoint, + href: '/widgets/cards', + children: [ + { + id: uniqueId(), + title: 'Cards', + icon: IconPoint, + href: '/widgets/cards', + }, + { + id: uniqueId(), + title: 'Banners', + icon: IconPoint, + href: '/widgets/banners', + }, + { + id: uniqueId(), + title: 'Charts', + icon: IconPoint, + href: '/widgets/charts', + }, + ], + }, + { + id: uniqueId(), + title: 'Ui', + icon: IconPoint, + href: '/ui-components/alert', + children: [ + { + id: uniqueId(), + title: 'Alert', + icon: IconPoint, + href: '/ui-components/alert', + }, + { + id: uniqueId(), + title: 'Accordion', + icon: IconPoint, + href: '/ui-components/accordion', + }, + { + id: uniqueId(), + title: 'Avatar', + icon: IconPoint, + href: '/ui-components/avatar', + }, + { + id: uniqueId(), + title: 'Chip', + icon: IconPoint, + href: '/ui-components/chip', + }, + { + id: uniqueId(), + title: 'Dialog', + icon: IconPoint, + href: '/ui-components/dialog', + }, + { + id: uniqueId(), + title: 'List', + icon: IconPoint, + href: '/ui-components/list', + }, + { + id: uniqueId(), + title: 'Popover', + icon: IconPoint, + href: '/ui-components/popover', + }, + { + id: uniqueId(), + title: 'Rating', + icon: IconPoint, + href: '/ui-components/rating', + }, + { + id: uniqueId(), + title: 'Tabs', + icon: IconPoint, + href: '/ui-components/tabs', + }, + { + id: uniqueId(), + title: 'Tooltip', + icon: IconPoint, + href: '/ui-components/tooltip', + }, + { + id: uniqueId(), + title: 'Transfer List', + icon: IconPoint, + href: '/ui-components/transfer-list', + }, + { + id: uniqueId(), + title: 'Typography', + icon: IconPoint, + href: '/typography', + }, + ], + }, + { + id: uniqueId(), + title: 'Charts', + icon: IconPoint, + href: '/charts/', + children: [ + { + id: uniqueId(), + title: 'Line', + icon: IconPoint, + href: '/charts/line-chart', + }, + { + id: uniqueId(), + title: 'Gredient', + icon: IconPoint, + href: '/charts/gredient-chart', + }, + { + id: uniqueId(), + title: 'Area', + icon: IconPoint, + href: '/charts/area-chart', + }, + { + id: uniqueId(), + title: 'Candlestick', + icon: IconPoint, + href: '/charts/candlestick-chart', + }, + { + id: uniqueId(), + title: 'Column', + icon: IconPoint, + href: '/charts/column-chart', + }, + { + id: uniqueId(), + title: 'Doughtnut & Pie', + icon: IconPoint, + href: '/charts/doughnut-pie-chart', + }, + { + id: uniqueId(), + title: 'RadialBar & Radar', + icon: IconPoint, + href: '/charts/radialbar-chart', + }, + ], + }, + { + id: uniqueId(), + title: 'Auth', + icon: IconPoint, + href: '/400', + children: [ + { + id: uniqueId(), + title: 'Error', + icon: IconAlertCircle, + href: '/400', + }, + { + id: uniqueId(), + title: 'Maintenance', + icon: IconSettings, + href: '/auth/maintenance', + }, + { + id: uniqueId(), + title: 'Login', + icon: IconLogin, + href: '/auth/login', + children: [ + { + id: uniqueId(), + title: 'Side Login', + icon: IconPoint, + href: '/auth/login', + }, + { + id: uniqueId(), + title: 'Boxed Login', + icon: IconPoint, + href: '/auth/login2', + }, + ], + }, + { + id: uniqueId(), + title: 'Register', + icon: IconUserPlus, + href: '/auth/register', + children: [ + { + id: uniqueId(), + title: 'Side Register', + icon: IconPoint, + href: '/auth/register', + }, + { + id: uniqueId(), + title: 'Boxed Register', + icon: IconPoint, + href: '/auth/register2', + }, + ], + }, + { + id: uniqueId(), + title: 'Forgot Password', + icon: IconRotate, + href: '/auth/forgot-password', + children: [ + { + id: uniqueId(), + title: 'Side Forgot Password', + icon: IconPoint, + href: '/auth/forgot-password', + }, + { + id: uniqueId(), + title: 'Boxed Forgot Password', + icon: IconPoint, + href: '/auth/forgot-password2', + }, + ], + }, + { + id: uniqueId(), + title: 'Two Steps', + icon: IconZoomCode, + href: '/auth/two-steps', + children: [ + { + id: uniqueId(), + title: 'Side Two Steps', + icon: IconPoint, + href: '/auth/two-steps', + }, + { + id: uniqueId(), + title: 'Boxed Two Steps', + icon: IconPoint, + href: '/auth/two-steps2', + }, + ], + }, + ], + }, + ], + }, + { + id: uniqueId(), + title: 'Forms', + icon: IconFileDescription, + href: '/forms/form-elements/autocomplete', + children: [ + { + id: uniqueId(), + title: 'Form Elements', + icon: IconPoint, + href: '/forms/form-elements/autocomplete', + children: [ + { + id: uniqueId(), + title: 'Autocomplete', + icon: IconPoint, + href: '/forms/form-elements/autocomplete', + }, + { + id: uniqueId(), + title: 'Button', + icon: IconPoint, + href: '/forms/form-elements/button', + }, + { + id: uniqueId(), + title: 'Radio', + icon: IconPoint, + href: '/forms/form-elements/radio', + }, + { + id: uniqueId(), + title: 'Date Time', + icon: IconPoint, + href: '/forms/form-elements/date-time', + }, + { + id: uniqueId(), + title: 'Slider', + icon: IconPoint, + href: '/forms/form-elements/slider', + }, + { + id: uniqueId(), + title: 'Switch', + icon: IconPoint, + href: '/forms/form-elements/switch', + }, + ], + }, + { + id: uniqueId(), + title: 'Form Layout', + icon: IconPoint, + href: '/forms/form-layouts', + }, + { + id: uniqueId(), + title: 'Form Horizontal', + icon: IconPoint, + href: '/forms/form-horizontal', + }, + { + id: uniqueId(), + title: 'Form Vertical', + icon: IconPoint, + href: '/forms/form-vertical', + }, + { + id: uniqueId(), + title: 'Form Custom', + icon: IconPoint, + href: '/forms/form-custom', + }, + { + id: uniqueId(), + title: 'Form Wizard', + icon: IconPoint, + href: '/forms/form-wizard', + }, + { + id: uniqueId(), + title: 'Form Validation', + icon: IconPoint, + href: '/forms/form-validation', + }, + { + id: uniqueId(), + title: 'Tiptap Editor', + icon: IconPoint, + href: '/forms/form-tiptap', + }, + ], + }, + { + id: uniqueId(), + title: 'Tables', + icon: IconBorderAll, + href: '/tables/', + children: [ + { + id: uniqueId(), + title: 'Basic', + icon: IconPoint, + href: '/tables/basic', + }, + { + id: uniqueId(), + title: 'Collapsible', + icon: IconPoint, + href: '/tables/collapsible', + }, + { + id: uniqueId(), + title: 'Enhanced', + icon: IconPoint, + href: '/tables/enhanced', + }, + { + id: uniqueId(), + title: 'Fixed Header', + icon: IconPoint, + href: '/tables/fixed-header', + }, + { + id: uniqueId(), + title: 'Pagination', + icon: IconPoint, + href: '/tables/pagination', + }, + { + id: uniqueId(), + title: 'Search', + icon: IconPoint, + href: '/tables/search', + }, + { + id: uniqueId(), + title: 'React Table', + icon: IconPoint, + href: '/react-tables/basic', + children: [ + { + id: uniqueId(), + title: 'Basic', + icon: IconPoint, + href: '/react-tables/basic', + }, + { + id: uniqueId(), + title: 'Dense', + icon: IconPoint, + href: '/react-tables/dense', + }, + { + id: uniqueId(), + title: 'Filter', + icon: IconPoint, + href: '/react-tables/filter', + }, + { + id: uniqueId(), + title: 'Row Selection', + icon: IconPoint, + href: '/react-tables/row-selection', + }, + { + id: uniqueId(), + title: 'Pagination', + icon: IconPoint, + href: '/react-tables/pagination', + }, + { + id: uniqueId(), + title: 'Sorting', + icon: IconPoint, + href: '/react-tables/sorting', + }, + { + id: uniqueId(), + title: 'Column Visibility', + icon: IconPoint, + href: '/react-tables/column-visiblity', + }, + { + id: uniqueId(), + title: 'Editable', + icon: IconPoint, + href: '/react-tables/editable', + }, + { + id: uniqueId(), + title: 'Expanding', + icon: IconPoint, + href: '/react-tables/expanding', + }, + { + id: uniqueId(), + title: 'Sticky', + icon: IconPoint, + href: '/react-tables/sticky', + }, + { + id: uniqueId(), + title: 'Empty', + icon: IconPoint, + href: '/react-tables/empty', + }, + { + id: uniqueId(), + title: 'Drag & Drop', + icon: IconPoint, + href: '/react-tables/drag-drop', + }, + ], + }, + ], + }, + { + id: uniqueId(), + title: 'Mui Charts', + icon: IconChartHistogram, + href: '/muicharts/barcharts', + children: [ + { + id: uniqueId(), + title: 'BarCharts', + icon: IconPoint, + href: '/muicharts/barcharts', + }, + { + id: uniqueId(), + title: 'LineCharts', + icon: IconPoint, + href: '/muicharts/linecharts/line', + children: [ + { + id: uniqueId(), + title: 'Lines', + icon: IconPoint, + href: '/muicharts/linecharts/line', + }, + { + id: uniqueId(), + title: 'Area', + icon: IconPoint, + href: '/muicharts/linecharts/area', + }, + ], + }, + { + id: uniqueId(), + title: 'PieCharts', + icon: IconPoint, + href: '/muicharts/piecharts', + }, + { + id: uniqueId(), + title: 'ScatterCharts', + icon: IconPoint, + href: '/muicharts/scattercharts', + }, + { + id: uniqueId(), + title: 'SparklineCharts', + icon: IconPoint, + href: '/muicharts/sparklinecharts', + }, + { + id: uniqueId(), + title: 'GaugeCharts', + icon: IconPoint, + href: '/muicharts/gaugecharts', + }, + ], + }, + { + id: uniqueId(), + title: 'SimpleTreeView', + icon: IconListTree, + href: '/mui-trees/simpletree/simpletree-items', + children: [ + { + id: uniqueId(), + title: 'Items', + icon: IconPoint, + href: '/mui-trees/simpletree/simpletree-items', + }, + { + id: uniqueId(), + title: 'Selection', + icon: IconPoint, + href: '/mui-trees/simpletree/simpletree-selection', + }, + { + id: uniqueId(), + title: 'Expansion', + icon: IconPoint, + href: '/mui-trees/simpletree/simpletree-expansion', + }, + { + id: uniqueId(), + title: 'Customization', + icon: IconPoint, + href: '/mui-trees/simpletree/simpletree-customization', + }, + { + id: uniqueId(), + title: 'Focus', + icon: IconPoint, + href: '/mui-trees/simpletree/simpletree-focus', + }, + ], + }, +]; +export default Menuitems; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/NavCollapse/NavCollapse.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/NavCollapse/NavCollapse.tsx new file mode 100644 index 0000000..f15b993 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/NavCollapse/NavCollapse.tsx @@ -0,0 +1,147 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { useTheme } from '@mui/material/styles'; +import { useLocation } from 'react-router'; + +// mui imports +import { ListItemIcon, styled, ListItemText, Box, ListItemButton } from '@mui/material'; +import { useSelector } from 'src/store/Store'; + +// custom imports +import NavItem from '../NavItem/NavItem'; + +// plugins +import { IconChevronDown } from '@tabler/icons-react'; +import { AppState } from 'src/store/Store'; + +type NavGroupProps = { + [x: string]: any; + navlabel?: boolean; + subheader?: string; + title?: string; + icon?: any; + href?: any; +}; + +interface NavCollapseProps { + menu: NavGroupProps; + level: number; + pathWithoutLastPart: any; + pathDirect: any; + hideMenu: any; + onClick: any; +} + +// FC Component For Dropdown Menu +const NavCollapse = ({ menu, level, pathWithoutLastPart, pathDirect, hideMenu }: NavCollapseProps) => { + const Icon = menu.icon; + const theme = useTheme(); + const { pathname } = useLocation(); + const [open, setOpen] = React.useState(false); + const customizer = useSelector((state: AppState) => state.customizer); + const menuIcon = + level > 1 ? : ; + + React.useEffect(() => { + setOpen(false); + menu.children.forEach((item: any) => { + if (item.href === pathname) { + setOpen(true); + } + }); + }, [pathname, menu.children]); + + const ListItemStyled = styled(ListItemButton)(() => ({ + width: 'auto', + padding: '5px 10px', + position: 'relative', + flexGrow: 'unset', + gap: '10px', + borderRadius: `${customizer.borderRadius}px`, + whiteSpace: 'nowrap', + color: open || pathname.includes(menu.href) || level < 1 ? 'white' : theme.palette.text.secondary, + backgroundColor: open || pathname.includes(menu.href) ? theme.palette.primary.main : '', + + '&:hover': { + backgroundColor: + open || pathname.includes(menu.href) + ? theme.palette.primary.main + : theme.palette.primary.light, + }, + '&:hover > .SubNav': { display: 'block' }, + })); + + const ListSubMenu = styled((props: any) => )(() => ({ + display: 'none', + position: 'absolute', + top: level > 1 ? `0px` : '35px', + left: level > 1 ? `${level + 228}px` : '0px', + padding: '10px', + width: '250px', + color: theme.palette.text.primary, + boxShadow: theme.shadows[8], + backgroundColor: theme.palette.background.paper, + })); + + const listItemProps: { + component: string; + } = { + component: 'li', + }; + + // If Menu has Children + const submenus = menu.children?.map((item: any) => { + if (item.children) { + return ( + + ); + } else { + return ( + + ); + } + }); + + return ( + + + + {menuIcon} + + + {menu.title} + + + + {submenus} + + + + ); +}; + +export default NavCollapse; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/NavItem/NavItem.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/NavItem/NavItem.tsx new file mode 100644 index 0000000..f849674 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/NavItem/NavItem.tsx @@ -0,0 +1,99 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { NavLink } from 'react-router'; + +// mui imports +import { ListItemIcon, List, styled, ListItemText, useTheme, ListItemButton } from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import { AppState } from 'src/store/Store'; + +type NavGroup = { + [x: string]: any; + id?: string; + navlabel?: boolean; + subheader?: string; + title?: string; + icon?: any; + href?: string; + children?: NavGroup[]; + chip?: string; + chipColor?: any; + variant?: string | any; + external?: boolean; + level?: number; +}; + +interface ItemType { + item: NavGroup; + onClick: React.MouseEventHandler; + hideMenu: any; + level?: number | any; + pathDirect: string; +} + +const NavItem = ({ item, level, pathDirect, onClick }: ItemType) => { + const customizer = useSelector((state: AppState) => state.customizer); + const Icon = item.icon; + const theme = useTheme(); + const itemIcon = + level > 1 ? : ; + + const ListItemStyled2 = styled(ListItemButton)(() => ({ + padding: '5px 10px', + gap: '10px', + borderRadius: `${customizer.borderRadius}px`, + marginBottom: level > 1 ? '3px' : '0px', + color: + level > 1 && pathDirect === item.href ? `${theme.palette.primary.main}!important` : theme.palette.text.secondary, + + '&:hover': { + backgroundColor: theme.palette.primary.light, + }, + '&.Mui-selected': { + color: level > 1 ? theme.palette.primary.main : 'white!important', + backgroundColor: level > 1 ? 'transparent' : theme.palette.primary.main, + '&:hover': { + backgroundColor: level > 1 ? '' : theme.palette.primary.main, + color: 'white', + }, + }, + })); + + const listItemProps: { + component: any; + href?: string; + target?: any; + to?: any; + } = { + component: item?.external ? 'a' : NavLink, + to: item?.href, + href: item?.external ? item?.href : '', + target: item?.external ? '_blank' : '', + }; + + return ( + + + + {itemIcon} + + {item.title} + + + ); +}; + + +export default NavItem; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/NavListing/NavListing.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/NavListing/NavListing.tsx new file mode 100644 index 0000000..684c4fa --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/NavListing/NavListing.tsx @@ -0,0 +1,48 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Menudata from '../Menudata'; +import { useLocation } from 'react-router'; +import { Box, List, Theme, useMediaQuery } from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import NavItem from '../NavItem/NavItem'; +import NavCollapse from '../NavCollapse/NavCollapse'; +import { AppState } from 'src/store/Store'; + +const NavListing = () => { + const { pathname } = useLocation(); + const pathDirect = pathname; + const pathWithoutLastPart = pathname.slice(0, pathname.lastIndexOf('/')); + const customizer = useSelector((state: AppState) => state.customizer); + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + const hideMenu = lgUp ? customizer.isCollapse && !customizer.isSidebarHover : ''; + + return ( + + + {Menudata.map((item) => { + if (item.children) { + return ( + + ); + + // {/********If Sub No Menu**********/} + } else { + return ( + + ); + } + })} + + + ); +}; +export default NavListing; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/Navigation.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/Navigation.tsx new file mode 100644 index 0000000..a50d8f7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/horizontal/navbar/Navigation.tsx @@ -0,0 +1,59 @@ +import { useMediaQuery, Box, Drawer, Container, Theme } from '@mui/material'; +import NavListing from './NavListing/NavListing'; +import Logo from '../../shared/logo/Logo'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { toggleMobileSidebar } from 'src/store/customizer/CustomizerSlice'; +import SidebarItems from '../../vertical/sidebar/SidebarItems'; +import { AppState } from 'src/store/Store'; + +const Navigation = () => { + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + const customizer = useSelector((state: AppState) => state.customizer); + const dispatch = useDispatch(); + + if (lgUp) { + return ( + + {/* ------------------------------------------- */} + {/* Sidebar for desktop */} + {/* ------------------------------------------- */} + + + + + ); + } + + return ( + dispatch(toggleMobileSidebar())} + variant="temporary" + PaperProps={{ + sx: { + width: customizer.SidebarWidth, + border: '0 !important', + boxShadow: (theme) => theme.shadows[8], + }, + }} + > + {/* ------------------------------------------- */} + {/* Logo */} + {/* ------------------------------------------- */} + + + + {/* ------------------------------------------- */} + {/* Sidebar For Mobile */} + {/* ------------------------------------------- */} + + + ); +}; + +export default Navigation; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/breadcrumb/Breadcrumb.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/breadcrumb/Breadcrumb.tsx new file mode 100644 index 0000000..df5a446 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/breadcrumb/Breadcrumb.tsx @@ -0,0 +1,97 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Typography, Box, Breadcrumbs, Link, Theme } from '@mui/material'; +import { NavLink } from 'react-router'; + +import breadcrumbImg from 'src/assets/images/breadcrumb/ChatBc.png'; +import { IconCircle } from '@tabler/icons-react'; + +interface BreadCrumbType { + subtitle?: string; + items?: any[]; + title: string; + children?: any; +} + +const Breadcrumb = ({ subtitle, items, title, children }: BreadCrumbType) => ( + theme.shape.borderRadius / 4, + p: '30px 25px 20px', + marginBottom: '30px', + position: 'relative', + overflow: 'hidden', + }} + > + + {title} + + {subtitle} + + + } + sx={{ alignItems: 'center', mt: items ? '10px' : '' }} + aria-label="breadcrumb" + > + {items + ? items.map((item) => ( +
+ {item.to ? ( + + {item.title} + + ) : ( + {item.title} + )} +
+ )) + : ''} +
+
+ + + {children ? ( + {children} + ) : ( + <> + + {breadcrumbImg} + + + )} + + +
+); + +export default Breadcrumb; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/customizer/Customizer.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/customizer/Customizer.tsx new file mode 100644 index 0000000..36e0269 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/customizer/Customizer.tsx @@ -0,0 +1,315 @@ +import { FC, useState } from 'react'; +import { + Fab, + Drawer, + Grid2 as Grid, + Slider, + Divider, + styled, + IconButton, + Typography, + Tooltip, + Stack, +} from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import Box, { BoxProps } from '@mui/material/Box'; +import { IconX, IconSettings, IconCheck } from '@tabler/icons-react'; +import { + setTheme, + setDir, + setDarkMode, + toggleLayout, + toggleSidebar, + toggleHorizontal, + setBorderRadius, + setCardShadow, +} from 'src/store/customizer/CustomizerSlice'; +import { AppState } from 'src/store/Store'; +import Scrollbar from 'src/components/custom-scroll/Scrollbar'; +import WbSunnyTwoToneIcon from '@mui/icons-material/WbSunnyTwoTone'; +import DarkModeTwoToneIcon from '@mui/icons-material/DarkModeTwoTone'; +import SwipeLeftAltTwoToneIcon from '@mui/icons-material/SwipeLeftAltTwoTone'; +import SwipeRightAltTwoToneIcon from '@mui/icons-material/SwipeRightAltTwoTone'; +import AspectRatioTwoToneIcon from '@mui/icons-material/AspectRatioTwoTone'; +import CallToActionTwoToneIcon from '@mui/icons-material/CallToActionTwoTone'; +import ViewSidebarTwoToneIcon from '@mui/icons-material/ViewSidebarTwoTone'; +import WebAssetTwoToneIcon from '@mui/icons-material/WebAssetTwoTone'; +import { ViewComfyTwoTone, PaddingTwoTone, BorderOuter } from '@mui/icons-material'; + +const SidebarWidth = '320px'; +interface colors { + id: number; + bgColor: string; + disp?: string; +} +const Customizer: FC = () => { + const [showDrawer, setShowDrawer] = useState(false); + const customizer = useSelector((state: AppState) => state.customizer); + + const dispatch = useDispatch(); + + const StyledBox = styled(Box)(({ theme }) => ({ + boxShadow: theme.shadows[8], + padding: '20px', + cursor: 'pointer', + justifyContent: 'center', + display: 'flex', + transition: '0.1s ease-in', + border: '1px solid rgba(145, 158, 171, 0.12)', + '&:hover': { + transform: 'scale(1.05)', + }, + })); + + const thColors: colors[] = [ + { + id: 1, + bgColor: '#5D87FF', + disp: 'BLUE_THEME', + }, + { + id: 2, + bgColor: '#0074BA', + disp: 'AQUA_THEME', + }, + { + id: 3, + bgColor: '#763EBD', + disp: 'PURPLE_THEME', + }, + { + id: 4, + bgColor: '#0A7EA4', + disp: 'GREEN_THEME', + }, + { + id: 5, + bgColor: '#01C0C8', + disp: 'CYAN_THEME', + }, + { + id: 6, + bgColor: '#FA896B', + disp: 'ORANGE_THEME', + }, + ]; + + return ( + (
+ {/* ------------------------------------------- */} + {/* --Floating Button to open customizer ------ */} + {/* ------------------------------------------- */} + + setShowDrawer(true)} + > + + + + setShowDrawer(false)} + PaperProps={{ + sx: { + width: SidebarWidth, + }, + }} + > + {/* ------------------------------------------- */} + {/* ------------ Customizer Sidebar ------------- */} + {/* ------------------------------------------- */} + + + Settings + + setShowDrawer(false)}> + + + + + + {/* ------------------------------------------- */} + {/* ------------ Dark light theme setting ------------- */} + {/* ------------------------------------------- */} + + Theme Option + + + dispatch(setDarkMode('light'))} display="flex" gap={1}> + + Light + + dispatch(setDarkMode('dark'))} display="flex" gap={1}> + + Dark + + + + + {/* ------------------------------------------- */} + {/* ------------ RTL theme setting -------------*/} + {/* ------------------------------------------- */} + + Theme Direction + + + dispatch(setDir('ltr'))} display="flex" gap={1}> + {' '} + LTR + + dispatch(setDir('rtl'))} display="flex" gap={1}> + {' '} + RTL + + + + + {/* ------------------------------------------- */} + {/* ------------ Theme Color setting ------------- */} + {/* ------------------------------------------- */} + + Theme Colors + + + {thColors.map((thcolor) => ( + + dispatch(setTheme(thcolor.disp))}> + + + {customizer.activeTheme === thcolor.disp ? : ''} + + + + + ))} + + + {/* ------------------------------------------- */} + {/* ------------ Layout Horizontal / Vertical ------------- */} + {/* ------------------------------------------- */} + + Layout Type + + + dispatch(toggleHorizontal(false))} display="flex" gap={1}> + + Vertical + + dispatch(toggleHorizontal(true))} display="flex" gap={1}> + + Horizontal + + + + {/* ------------------------------------------- */} + {/* ------------ Layout Boxed / Full ------------- */} + {/* ------------------------------------------- */} + + Container Option + + + dispatch(toggleLayout('boxed'))} display="flex" gap={1}> + + Boxed + + dispatch(toggleLayout('full'))} display="flex" gap={1}> + + Full + + + + {/* ------------------------------------------- */} + {/* ------------ Sidebar Color setting ------------- */} + {/* ------------------------------------------- */} + + {/* ------------------------------------------- */} + {/* ------------ Theme Color setting ------------- */} + {/* ------------------------------------------- */} + {customizer.isHorizontal ? ( + '' + ) : ( + <> + + Sidebar Type + + + dispatch(toggleSidebar())} display="flex" gap={1}> + + Full + + dispatch(toggleSidebar())} display="flex" gap={1}> + + mini + + + + )} + + + Card With + + + dispatch(setCardShadow(false))} display="flex" gap={1}> + + Border + + dispatch(setCardShadow(true))} display="flex" gap={1}> + + Shadow + + + + {/* ------------------------------------------- */} + {/* ------------ Theme Color setting ------------- */} + {/* ------------------------------------------- */} + + Theme Border Radius + + + dispatch(setBorderRadius(event.target.value))} + valueLabelDisplay="auto" + /> + + + +
) + ); +}; + +export default Customizer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/customizer/RTL.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/customizer/RTL.tsx new file mode 100644 index 0000000..084c793 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/customizer/RTL.tsx @@ -0,0 +1,39 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useEffect } from 'react'; + +import createCache from '@emotion/cache'; +import { CacheProvider } from '@emotion/react'; +import rtlPlugin from 'stylis-plugin-rtl'; + +interface RTLType { + children: React.ReactNode; + direction: string; +} + +const styleCache = () => + createCache({ + key: 'rtl', + prepend: true, + + // We have to temporary ignore this due to incorrect definitions + // in the stylis-plugin-rtl module + // @see https://github.com/styled-components/stylis-plugin-rtl/issues/23 + stylisPlugins: [rtlPlugin], + }); + +const RTL = (props: RTLType) => { + const { children, direction } = props; + + useEffect(() => { + document.dir = direction; + }, [direction]); + + if (direction === 'rtl') { + return {children}; + } + + return <>{children}; +}; + +export default RTL; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/customizer/typings.d.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/customizer/typings.d.ts new file mode 100644 index 0000000..20d884a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/customizer/typings.d.ts @@ -0,0 +1,4 @@ +declare module "stylis-plugin-rtl" { + const noTypesYet: any; + export default noTypesYet; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/loadable/Loadable.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/loadable/Loadable.tsx new file mode 100644 index 0000000..b5a251c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/loadable/Loadable.tsx @@ -0,0 +1,17 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { Suspense } from 'react'; + +// project imports +import Spinner from 'src/views/spinner/Spinner'; + +// ===========================|| LOADABLE - LAZY LOADING ||=========================== // + +const Loadable = (Component: any) => (props: any) => + ( + }> + + + ); + +export default Loadable; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/logo/Logo.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/logo/Logo.tsx new file mode 100644 index 0000000..7527ffe --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/logo/Logo.tsx @@ -0,0 +1,63 @@ +import { FC } from 'react'; +import { useSelector } from 'src/store/Store'; +import { Link } from 'react-router'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import { ReactComponent as LogoDark } from 'src/assets/images/logos/dark-logo.svg'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import { ReactComponent as LogoDarkRTL } from 'src/assets/images/logos/dark-rtl-logo.svg'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import { ReactComponent as LogoLight } from 'src/assets/images/logos/light-logo.svg'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import { ReactComponent as LogoLightRTL } from 'src/assets/images/logos/light-logo-rtl.svg'; +import { styled } from '@mui/material'; +import { AppState } from 'src/store/Store'; + +const Logo: FC = () => { + const customizer = useSelector((state: AppState) => state.customizer); + const LinkStyled = styled(Link)(() => ({ + height: customizer.TopbarHeight, + width: customizer.isCollapse ? '40px' : '180px', + overflow: 'hidden', + display: 'block', + })); + + if (customizer.activeDir === 'ltr') { + return ( + + {customizer.activeMode === 'dark' ? ( + + ) : ( + + )} + + ); + } + + return ( + + {customizer.activeMode === 'dark' ? ( + + ) : ( + + )} + + ); +}; + +export default Logo; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/welcome/Welcome.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/welcome/Welcome.tsx new file mode 100644 index 0000000..de6cc60 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/shared/welcome/Welcome.tsx @@ -0,0 +1,50 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import * as React from 'react'; +import { Snackbar, Alert, AlertTitle } from '@mui/material'; + +const Welcome = () => { + const [open, setOpen] = React.useState(false); + + const handleClick = () => { + setOpen(true); + }; + + const handleClose = (reason: any) => { + if (reason === 'clickaway') { + return; + } + setOpen(false); + }; + React.useEffect(() => { + // Update the document title using the browser API + const timer = setTimeout(() => { + handleClick(); + }, 1500); + + return () => clearTimeout(timer); + }, []); + + return ( + + + + Welcome To Modernize + Easy to customize the Template!!! + + + + ); +}; + +export default Welcome; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/AppLinks.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/AppLinks.tsx new file mode 100644 index 0000000..5c79553 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/AppLinks.tsx @@ -0,0 +1,70 @@ +import { Avatar, Box, Typography, Grid2 as Grid, Stack } from '@mui/material'; +import * as dropdownData from './data'; +import { Link } from 'react-router'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +const AppLinks = () => { + return ( + ( + {dropdownData.appsLink.map((links, index) => ( + + + + + + + + + {links.title} + + + {links.subtext} + + + + + + ))} + ) + ); +}; + +export default AppLinks; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Cart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Cart.tsx new file mode 100644 index 0000000..6fc1a57 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Cart.tsx @@ -0,0 +1,114 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { sum } from 'lodash'; +import { IconShoppingCart, IconX } from '@tabler/icons-react'; +import { Box, Typography, Badge, Drawer, IconButton, Button, Stack } from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import { Link } from 'react-router'; +import CartItems from './CartItem'; +import { AppState } from 'src/store/Store'; + +const Cart = () => { + // Get Products + const Cartproduct = useSelector((state: AppState) => state.ecommerceReducer.cart); + const bcount = Cartproduct.length > 0 ? Cartproduct.length : '0'; + + const checkout = useSelector((state: AppState) => state.ecommerceReducer.cart); + const total = sum(checkout.map((product: any) => product.price * product.qty)); + + const [showDrawer, setShowDrawer] = useState(false); + const handleDrawerClose = () => { + setShowDrawer(false); + }; + + const cartContent = ( + + {/* ------------------------------------------- */} + {/* Cart Content */} + {/* ------------------------------------------- */} + + + + + ); + + return ( + + setShowDrawer(true)} + sx={{ + color: 'text.secondary', + ...(showDrawer && { + color: 'primary.main', + }), + }} + > + + + + + {/* ------------------------------------------- */} + {/* Cart Sidebar */} + {/* ------------------------------------------- */} + setShowDrawer(false)} + PaperProps={{ sx: { maxWidth: '500px' } }} + > + + + Shopping Cart + + + theme.palette.grey.A200, + }} + onClick={handleDrawerClose} + > + + + + + + {/* component */} + {cartContent} + {/* ------------------------------------------- */} + {/* Checkout */} + {/* ------------------------------------------- */} + + {Cartproduct.length > 0 ? ( + <> + + + Total + + + ${total} + + + + + ) : ( + '' + )} + + + + ); +}; + +export default Cart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/CartItem.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/CartItem.tsx new file mode 100644 index 0000000..1ac29ce --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/CartItem.tsx @@ -0,0 +1,101 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, Typography, Avatar, Stack, ButtonGroup, Button } from '@mui/material'; +import { Link } from 'react-router'; +import { IconMinus, IconPlus } from '@tabler/icons-react'; +import { useSelector, useDispatch } from 'src/store/Store'; +import emptyCart from 'src/assets/images/products/empty-shopping-cart.svg'; +import { increment, decrement } from 'src/store/apps/eCommerce/ECommerceSlice'; +import { AppState } from 'src/store/Store'; + +const CartItems = () => { + const dispatch = useDispatch(); + + // Get Products + const Cartproduct = useSelector((state: AppState) => state.ecommerceReducer.cart); + + const Increase = (productId: string) => { + dispatch(increment(productId)); + }; + + const Decrease = (productId: string) => { + dispatch(decrement(productId)); + }; + + return ( + + {Cartproduct.length > 0 ? ( + <> + {Cartproduct.map((product: any, index: number) => ( + + + + + + {product.title} + {' '} + + {' '} + {product.category} + + + + ${product.price * product.qty} + + + + + + + + + + + ))} + + ) : ( + + cart + + Cart is Empty + + + + )} + + ); +}; + +export default CartItems; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Header.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Header.tsx new file mode 100644 index 0000000..f4a9a09 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Header.tsx @@ -0,0 +1,94 @@ +import { IconButton, Box, AppBar, useMediaQuery, Toolbar, styled, Stack } from '@mui/material'; + +import { useSelector, useDispatch } from 'src/store/Store'; +import { + toggleSidebar, + toggleMobileSidebar, + setDarkMode, +} from 'src/store/customizer/CustomizerSlice'; +import { IconMenu2, IconMoon, IconSun } from '@tabler/icons-react'; +import Notifications from './Notification'; +import Profile from './Profile'; +import Cart from './Cart'; +import Search from './Search'; +import Language from './Language'; +import { AppState } from 'src/store/Store'; +import Navigation from './Navigation'; +import MobileRightSidebar from './MobileRightSidebar'; + +const Header = () => { + const lgUp = useMediaQuery((theme: any) => theme.breakpoints.up('lg')); + const lgDown = useMediaQuery((theme: any) => theme.breakpoints.down('lg')); + + // drawer + const customizer = useSelector((state: AppState) => state.customizer); + const dispatch = useDispatch(); + + const AppBarStyled = styled(AppBar)(({ theme }) => ({ + boxShadow: 'none', + background: theme.palette.background.paper, + justifyContent: 'center', + backdropFilter: 'blur(4px)', + [theme.breakpoints.up('lg')]: { + minHeight: customizer.TopbarHeight, + }, + })); + const ToolbarStyled = styled(Toolbar)(({ theme }) => ({ + width: '100%', + color: theme.palette.text.secondary, + })); + + return ( + + + {/* ------------------------------------------- */} + {/* Toggle Button Sidebar */} + {/* ------------------------------------------- */} + dispatch(toggleSidebar()) : () => dispatch(toggleMobileSidebar())} + > + + + + {/* ------------------------------------------- */} + {/* Search Dropdown */} + {/* ------------------------------------------- */} + + {lgUp ? ( + <> + + + ) : null} + + + + + {/* ------------------------------------------- */} + {/* Ecommerce Dropdown */} + {/* ------------------------------------------- */} + + {/* ------------------------------------------- */} + {/* End Ecommerce Dropdown */} + {/* ------------------------------------------- */} + + {customizer.activeMode === 'light' ? ( + dispatch(setDarkMode('dark'))} /> + ) : ( + dispatch(setDarkMode('light'))} /> + )} + + + {/* ------------------------------------------- */} + {/* Toggle Right Sidebar for mobile */} + {/* ------------------------------------------- */} + {lgDown ? : null} + + + + + ); +}; + +export default Header; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Language.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Language.tsx new file mode 100644 index 0000000..1950f8d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Language.tsx @@ -0,0 +1,98 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Avatar, IconButton, Menu, MenuItem, Typography, Stack } from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { setLanguage } from 'src/store/customizer/CustomizerSlice'; +import FlagEn from 'src/assets/images/flag/icon-flag-en.svg'; +import FlagFr from 'src/assets/images/flag/icon-flag-fr.svg'; +import FlagCn from 'src/assets/images/flag/icon-flag-cn.svg'; +import FlagSa from 'src/assets/images/flag/icon-flag-sa.svg'; +import { useTranslation } from 'react-i18next'; +import { useEffect } from 'react'; +import { AppState } from 'src/store/Store'; + +const Languages = [ + { + flagname: 'English (UK)', + icon: FlagEn, + value: 'en', + }, + { + flagname: '中国人 (Chinese)', + icon: FlagCn, + value: 'ch', + }, + { + flagname: 'français (French)', + icon: FlagFr, + value: 'fr', + }, + + { + flagname: 'عربي (Arabic)', + icon: FlagSa, + value: 'ar', + }, +]; + +const Language = () => { + const [anchorEl, setAnchorEl] = React.useState(null); + const dispatch = useDispatch(); + const open = Boolean(anchorEl); + const customizer = useSelector((state: AppState) => state.customizer); + const currentLang = + Languages.find((_lang) => _lang.value === customizer.isLanguage) || Languages[1]; + const { i18n } = useTranslation(); + const handleClick = (event: any) => { + setAnchorEl(event.currentTarget); + }; + const handleClose = () => { + setAnchorEl(null); + }; + useEffect(() => { + i18n.changeLanguage(customizer.isLanguage); + // eslint-disable-next-line react-hooks/exhaustive-deps + }, []); + + return ( + <> + + + + + {Languages.map((option, index) => ( + dispatch(setLanguage(option.value))} + > + + + {option.flagname} + + + ))} + + + ); +}; + +export default Language; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Message.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Message.tsx new file mode 100644 index 0000000..daa43bc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Message.tsx @@ -0,0 +1,140 @@ +import { useState } from 'react'; +import { + IconButton, + Box, + Badge, + Menu, + MenuItem, + Avatar, + Typography, + Divider, + Button, + Stack +} from '@mui/material'; +import * as dropdownData from './data'; + +import { IconChecks, IconClock, IconMessageDots } from '@tabler/icons-react'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +const Message = () => { + const [anchorEl2, setAnchorEl2] = useState(null); + + const handleClick2 = (event: any) => { + setAnchorEl2(event.currentTarget); + }; + + const handleClose2 = () => { + setAnchorEl2(null); + }; + + return ( + + + + + + + {/* ------------------------------------------- */} + {/* Message Dropdown */} + {/* ------------------------------------------- */} + + + + Messages + + You have 3 unread messages + + + + + + {dropdownData.messages.map((message) => ( + + + + + + + {message.title} + + + {message.subtitle} + + + + {message.time} + + + + + + + ))} + + + + + + ); +}; + +export default Message; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/MobileRightSidebar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/MobileRightSidebar.tsx new file mode 100644 index 0000000..8849d86 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/MobileRightSidebar.tsx @@ -0,0 +1,144 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { + IconApps, + IconCalendarEvent, + IconChevronDown, + IconChevronUp, + IconGridDots, + IconMail, + IconMessages, +} from '@tabler/icons-react'; +import { + Box, + Typography, + Drawer, + IconButton, + List, + ListItemButton, + ListItemIcon, + ListItemText, + Collapse, +} from '@mui/material'; + +import { Link } from 'react-router'; +import AppLinks from './AppLinks'; +import QuickLinks from './QuickLinks'; + +const MobileRightSidebar = () => { + const [showDrawer, setShowDrawer] = useState(false); + + const [open, setOpen] = React.useState(true); + + const handleClick = () => { + setOpen(!open); + }; + + const cartContent = ( + + {/* ------------------------------------------- */} + {/* Apps Content */} + {/* ------------------------------------------- */} + + + + + + + + + Chats + + + + + + + + + + Calendar + + + + + + + + + + Email + + + + + + + + + + Apps + + + {open ? ( + + ) : ( + + )} + + + + + + + + + + + + + + ); + + return ( + + setShowDrawer(true)} + sx={{ + ...(showDrawer && { + color: 'primary.main', + }), + }} + > + + + {/* ------------------------------------------- */} + {/* Cart Sidebar */} + {/* ------------------------------------------- */} + setShowDrawer(false)} + PaperProps={{ sx: { width: '300px' } }} + > + + + Navigation + + + + {/* component */} + {cartContent} + + + ); +}; + +export default MobileRightSidebar; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Navigation.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Navigation.tsx new file mode 100644 index 0000000..33be935 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Navigation.tsx @@ -0,0 +1,123 @@ +import { useState } from 'react'; +import { Box, Menu, Typography, Button, Divider, Grid2 as Grid } from '@mui/material'; +import { Link } from 'react-router'; +import { IconChevronDown, IconHelp } from '@tabler/icons-react'; +import AppLinks from './AppLinks'; +import QuickLinks from './QuickLinks'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +const AppDD = () => { + const [anchorEl2, setAnchorEl2] = useState(null); + + const handleClick2 = (event: any) => { + setAnchorEl2(event.currentTarget); + }; + + const handleClose2 = () => { + setAnchorEl2(null); + }; + + return (<> + + + {/* ------------------------------------------- */} + {/* Message Dropdown */} + {/* ------------------------------------------- */} + + + + + + + + + + + Frequently Asked Questions + + + + + + + + + + + + + + + + + + + ); +}; + +export default AppDD; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Notification.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Notification.tsx new file mode 100644 index 0000000..782da2e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Notification.tsx @@ -0,0 +1,122 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { + IconButton, + Box, + Badge, + Menu, + MenuItem, + Avatar, + Typography, + Button, + Chip, + Stack +} from '@mui/material'; +import * as dropdownData from './data'; +import Scrollbar from 'src/components/custom-scroll/Scrollbar'; + +import { IconBellRinging } from '@tabler/icons-react'; +import { Link } from 'react-router'; + +const Notifications = () => { + const [anchorEl2, setAnchorEl2] = useState(null); + + const handleClick2 = (event: any) => { + setAnchorEl2(event.currentTarget); + }; + + const handleClose2 = () => { + setAnchorEl2(null); + }; + + return ( + + + + + + + {/* ------------------------------------------- */} + {/* Message Dropdown */} + {/* ------------------------------------------- */} + + + Notifications + + + + {dropdownData.notifications.map((notification, index) => ( + + + + + + + {notification.title} + + + {notification.subtitle} + + + + + + ))} + + + + + + + ); +}; + +export default Notifications; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Profile.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Profile.tsx new file mode 100644 index 0000000..70c6171 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Profile.tsx @@ -0,0 +1,172 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { Link } from 'react-router'; +import { + Box, + Menu, + Avatar, + Typography, + Divider, + Button, + IconButton, + Stack +} from '@mui/material'; +import * as dropdownData from './data'; + +import { IconMail } from '@tabler/icons-react'; + +import ProfileImg from 'src/assets/images/profile/user-1.jpg'; +import unlimitedImg from 'src/assets/images/backgrounds/unlimited-bg.png'; + +const Profile = () => { + const [anchorEl2, setAnchorEl2] = useState(null); + const handleClick2 = (event: any) => { + setAnchorEl2(event.currentTarget); + }; + const handleClose2 = () => { + setAnchorEl2(null); + }; + + return ( + + + + + {/* ------------------------------------------- */} + {/* Message Dropdown */} + {/* ------------------------------------------- */} + + User Profile + + + + + Mathew Anderson + + + Designer + + + + info@modernize.com + + + + + {dropdownData.profile.map((profile) => ( + + + + + + + + + + {profile.title} + + + {profile.subtitle} + + + + + + + ))} + + + + + + Unlimited
+ Access +
+ +
+ unlimited +
+
+ +
+
+
+ ); +}; + +export default Profile; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/QuickLinks.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/QuickLinks.tsx new file mode 100644 index 0000000..1330a00 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/QuickLinks.tsx @@ -0,0 +1,27 @@ +import { Typography, Stack } from '@mui/material'; +import * as dropdownData from './data'; +import { Link } from 'react-router'; + +const QuickLinks = () => { + return ( + <> + Quick Links + + {dropdownData.pageLinks.map((pagelink, index) => ( + + + {pagelink.title} + + + ))} + + + ); +}; + +export default QuickLinks; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Search.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Search.tsx new file mode 100644 index 0000000..17b46c0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/Search.tsx @@ -0,0 +1,135 @@ +import { useState } from 'react'; +import { + IconButton, + Dialog, + DialogContent, + Stack, + Divider, + Box, + List, + ListItemText, + Typography, + TextField, + ListItemButton, +} from '@mui/material'; +import { IconSearch, IconX } from '@tabler/icons-react'; +import Menuitems from '../sidebar/MenuItems'; +import { Link } from 'react-router'; + +interface menuType { + title: string; + id: string; + subheader: string; + children: menuType[]; + href: string; +} + +const Search = () => { + // drawer top + const [showDrawer2, setShowDrawer2] = useState(false); + const [search, setSerach] = useState(''); + + const handleDrawerClose2 = () => { + setShowDrawer2(false); + }; + + const filterRoutes = (rotr: any, cSearch: string) => { + if (rotr.length > 1) + return rotr.filter((t: any) => + t.title ? t.href.toLocaleLowerCase().includes(cSearch.toLocaleLowerCase()) : '', + ); + + return rotr; + }; + const searchData = filterRoutes(Menuitems, search); + + return ( + <> + setShowDrawer2(true)} + size="large" + > + + + setShowDrawer2(false)} + fullWidth + maxWidth={'sm'} + aria-labelledby="alert-dialog-title" + aria-describedby="alert-dialog-description" + PaperProps={{ sx: { position: 'fixed', top: 30, m: 0 } }} + > + + + setSerach(e.target.value)} + inputProps={{ 'aria-label': 'Search here' }} + /> + + + + + + + + + Quick Page Links + + + + {searchData.map((menu: menuType) => { + return ( + + {menu.title && !menu.children ? ( + + + + ) : ( + '' + )} + {menu.children ? ( + <> + {menu.children.map((child: menuType) => { + return ( + + + + ); + })} + + ) : ( + '' + )} + + ); + })} + + + + + + ); +}; + +export default Search; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/data.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/data.ts new file mode 100644 index 0000000..9ad74e2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/header/data.ts @@ -0,0 +1,242 @@ +import img1 from 'src/assets/images/profile/user-1.jpg'; +import img2 from 'src/assets/images/profile/user-2.jpg'; +import img3 from 'src/assets/images/profile/user-3.jpg'; +import img4 from 'src/assets/images/profile/user-4.jpg'; + +import icon1 from 'src/assets/images/svgs/icon-account.svg' +import icon2 from 'src/assets/images/svgs/icon-inbox.svg' +import icon3 from 'src/assets/images/svgs/icon-tasks.svg' + +import ddIcon1 from 'src/assets/images/svgs/icon-dd-chat.svg' +import ddIcon2 from 'src/assets/images/svgs/icon-dd-cart.svg' +import ddIcon3 from 'src/assets/images/svgs/icon-dd-invoice.svg' +import ddIcon4 from 'src/assets/images/svgs/icon-dd-date.svg' +import ddIcon5 from 'src/assets/images/svgs/icon-dd-mobile.svg' +import ddIcon6 from 'src/assets/images/svgs/icon-dd-lifebuoy.svg' +import ddIcon7 from 'src/assets/images/svgs/icon-dd-message-box.svg' +import ddIcon8 from 'src/assets/images/svgs/icon-dd-application.svg' + +// Notifications dropdown + +interface notificationType { + avatar: string; + title: string; + subtitle: string; +} + +const notifications: notificationType[] = [ + { + avatar: img1, + title: 'Roman Joined the Team!', + subtitle: 'Congratulate him', + }, + { + avatar: img2, + title: 'New message received', + subtitle: 'Salma sent you new message', + }, + { + avatar: img3, + title: 'New Payment received', + subtitle: 'Check your earnings', + }, + { + avatar: img4, + title: 'Jolly completed tasks', + subtitle: 'Assign her new tasks', + }, + { + avatar: img1, + title: 'Roman Joined the Team!', + subtitle: 'Congratulate him', + }, + { + avatar: img2, + title: 'New message received', + subtitle: 'Salma sent you new message', + }, + { + avatar: img3, + title: 'New Payment received', + subtitle: 'Check your earnings', + }, + { + avatar: img4, + title: 'Jolly completed tasks', + subtitle: 'Assign her new tasks', + }, +]; + +// +// Messages dropdown +// +interface messageType { + avatar: string; + title: string; + subtitle: string; + time: string; + status: string; +} +const messages: messageType[] = [ + { + avatar: img1, + title: 'Roman Joined the Team!', + subtitle: 'Congratulate him', + time: '1 hours ago', + status: 'success', + }, + { + avatar: img2, + title: 'New message received', + subtitle: 'Salma sent you new message', + time: '1 day ago', + status: 'warning', + }, + { + avatar: img3, + title: 'New Payment received', + subtitle: 'Check your earnings', + time: '2 days ago', + status: 'success', + }, + { + avatar: img4, + title: 'Jolly completed tasks', + subtitle: 'Assign her new tasks', + time: '1 week ago', + status: 'danger', + }, +]; + +// +// Profile dropdown +// +interface ProfileType { + href: string; + title: string; + subtitle: string; + icon: any; +} +const profile: ProfileType[] = [ + { + href: '/user-profile', + title: 'My Profile', + subtitle: 'Account Settings', + icon: icon1, + }, + { + href: '/apps/email', + title: 'My Inbox', + subtitle: 'Messages & Emails', + icon: icon2, + }, + { + href: '/apps/notes', + title: 'My Tasks', + subtitle: 'To-do and Daily Tasks', + icon: icon3, + }, +]; + +// apps dropdown + +interface appsLinkType { + href: string; + title : string; + subtext: string; + avatar: string; +} + +const appsLink:appsLinkType[] = [ + { + href: '/apps/chats', + title: 'Chat Application', + subtext: 'New messages arrived', + avatar: ddIcon1 + }, + { + href: '/apps/ecommerce/shop', + title: 'eCommerce App', + subtext: 'New stock available', + avatar: ddIcon2 + }, + { + href: '/apps/notes', + title: 'Notes App', + subtext: 'To-do and Daily tasks', + avatar: ddIcon3 + }, + { + href: '/apps/calendar', + title: 'Calendar App', + subtext: 'Get dates', + avatar: ddIcon4 + }, + { + href: '/apps/contacts', + title: 'Contact Application', + subtext: '2 Unsaved Contacts', + avatar: ddIcon5 + }, + { + href: '/apps/tickets', + title: 'Tickets App', + subtext: 'Submit tickets', + avatar: ddIcon6 + }, + { + href: '/apps/email', + title: 'Email App', + subtext: 'Get new emails', + avatar: ddIcon7 + }, + { + href: '/apps/blog/posts', + title: 'Blog App', + subtext: 'added new blog', + avatar: ddIcon8 + }, +] + + +interface LinkType { + href: string; + title: string; +} + +const pageLinks:LinkType[] = [ + { + href: '/pricing', + title: 'Pricing Page' + }, + { + href: '/auth/login', + title: 'Authentication Design' + }, + { + href: '/auth/register', + title: 'Register Now' + }, + { + href: '/404', + title: '404 Error Page' + }, + { + href: '/auth/login', + title: 'Login Page' + }, + { + href: '/user-profile', + title: 'User Application' + }, + { + href: '/apps/blog/posts', + title: 'Blog Design' + }, + { + href: '/apps/ecommerce/eco-checkout', + title: 'Shopping Cart' + }, +] + +export { notifications, messages, profile, pageLinks, appsLink }; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/MenuItems.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/MenuItems.ts new file mode 100644 index 0000000..560c989 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/MenuItems.ts @@ -0,0 +1,1015 @@ +import { uniqueId } from 'lodash'; + +interface MenuitemsType { + [x: string]: any; + id?: string; + navlabel?: boolean; + subheader?: string; + title?: string; + icon?: any; + href?: string; + children?: MenuitemsType[]; + chip?: string; + chipColor?: string; + variant?: string; + external?: boolean; +} +import { + IconAward, + IconBoxMultiple, + IconPoint, + IconAlertCircle, + IconNotes, + IconCalendar, + IconMail, + IconTicket, + IconEdit, + IconCurrencyDollar, + IconApps, + IconFileDescription, + IconFileDots, + IconFiles, + IconBan, + IconStar, + IconMoodSmile, + IconBorderAll, + IconBorderHorizontal, + IconBorderInner, + IconBorderVertical, + IconBorderTop, + IconUserCircle, + IconPackage, + IconMessage2, + IconBasket, + IconChartLine, + IconChartArcs, + IconChartCandle, + IconChartArea, + IconChartDots, + IconChartDonut3, + IconChartRadar, + IconLogin, + IconUserPlus, + IconRotate, + IconBox, + IconShoppingCart, + IconAperture, + IconLayout, + IconSettings, + IconHelp, + IconZoomCode, + IconBoxAlignBottom, + IconBoxAlignLeft, + IconBorderStyle2, + IconAppWindow, + IconNotebook, + IconFileCheck, + IconChartHistogram, + IconChartPie2, + IconChartScatter, + IconChartPpf, + IconChartArcs3, + IconListTree, +} from '@tabler/icons-react'; + +const Menuitems: MenuitemsType[] = [ + { + navlabel: true, + subheader: 'Home', + }, + + { + id: uniqueId(), + title: 'Modern', + icon: IconAperture, + href: '/dashboards/modern', + chip: 'New', + chipColor: 'secondary', + }, + { + id: uniqueId(), + title: 'eCommerce', + icon: IconShoppingCart, + href: '/dashboards/ecommerce', + }, + { + id: uniqueId(), + title: 'Frontend pages', + icon: IconAppWindow, + href: '/frontend-pages/', + children: [ + { + id: uniqueId(), + title: 'Homepage', + icon: IconPoint, + href: '/frontend-pages/homepage', + }, + { + id: uniqueId(), + title: 'About Us', + icon: IconPoint, + href: '/frontend-pages/about', + }, + { + id: uniqueId(), + title: 'Blog', + icon: IconPoint, + href: '/frontend-pages/blog', + }, + { + id: uniqueId(), + title: 'Blog Details', + icon: IconPoint, + href: '/frontend-pages/blog/detail/streaming-video-way-before-it-was-cool-go-dark-tomorrow', + }, + { + id: uniqueId(), + title: 'Contact', + icon: IconPoint, + href: '/frontend-pages/contact', + }, + { + id: uniqueId(), + title: 'Portfolio', + icon: IconPoint, + href: '/frontend-pages/portfolio', + }, + { + id: uniqueId(), + title: 'Pricing', + icon: IconPoint, + href: '/frontend-pages/pricing', + }, + ], + }, + { + navlabel: true, + subheader: 'Apps', + }, + { + id: uniqueId(), + title: 'Contacts', + icon: IconPackage, + chip: '2', + chipColor: 'secondary', + href: '/apps/contacts', + }, + + { + id: uniqueId(), + title: 'Blog', + icon: IconChartDonut3, + href: '/frontend-pages/blog/', + children: [ + { + id: uniqueId(), + title: 'Posts', + icon: IconPoint, + href: '/frontend-pages/blog/', + }, + { + id: uniqueId(), + title: 'Detail', + icon: IconPoint, + href: '/frontend-pages/blog/detail/streaming-video-way-before-it-was-cool-go-dark-tomorrow', + }, + ], + }, + { + id: uniqueId(), + title: 'Ecommerce', + icon: IconBasket, + href: '/apps/ecommerce/', + children: [ + { + id: uniqueId(), + title: 'Shop', + icon: IconPoint, + href: '/apps/ecommerce/shop', + }, + { + id: uniqueId(), + title: 'Detail', + icon: IconPoint, + href: '/apps/ecommerce/detail/1', + }, + { + id: uniqueId(), + title: 'List', + icon: IconPoint, + href: '/apps/ecommerce/eco-product-list', + }, + { + id: uniqueId(), + title: 'Checkout', + icon: IconPoint, + href: '/apps/ecommerce/eco-checkout', + }, + { + id: uniqueId(), + title: 'Add Product', + icon: IconPoint, + href: '/apps/ecommerce/add-product', + }, + { + id: uniqueId(), + title: 'Edit Product', + icon: IconPoint, + href: '/apps/ecommerce/edit-product', + }, + ], + }, + { + id: uniqueId(), + title: 'Chats', + icon: IconMessage2, + href: '/apps/chats', + }, + { + id: uniqueId(), + title: 'Users', + icon: IconUserCircle, + href: '/user-profile', + children: [ + { + id: uniqueId(), + title: 'Profile', + icon: IconPoint, + href: '/user-profile', + }, + { + id: uniqueId(), + title: 'Followers', + icon: IconPoint, + href: '/apps/followers', + }, + { + id: uniqueId(), + title: 'Friends', + icon: IconPoint, + href: '/apps/friends', + }, + { + id: uniqueId(), + title: 'Gallery', + icon: IconPoint, + href: '/apps/gallery', + }, + ], + }, + { + id: uniqueId(), + title: 'Notes', + icon: IconNotes, + href: '/apps/notes', + }, + { + id: uniqueId(), + title: 'Calendar', + icon: IconCalendar, + href: '/apps/calendar', + }, + { + id: uniqueId(), + title: 'Email', + icon: IconMail, + href: '/apps/email', + }, + { + id: uniqueId(), + title: 'Tickets', + icon: IconTicket, + href: '/apps/tickets', + }, + { + id: uniqueId(), + title: 'Kanban', + icon: IconNotebook, + href: '/apps/kanban', + }, + + { + id: uniqueId(), + title: 'Invoice', + icon: IconFileCheck, + href: '/apps/invoice/list', + children: [ + { + id: uniqueId(), + title: 'List', + icon: IconPoint, + href: '/apps/invoice/list', + }, + { + id: uniqueId(), + title: 'Details', + icon: IconPoint, + href: '/apps/invoice/detail/PineappleInc', + }, + { + id: uniqueId(), + title: 'Create', + icon: IconPoint, + href: '/apps/invoice/create', + }, + { + id: uniqueId(), + title: 'Edit', + icon: IconPoint, + href: '/apps/invoice/edit/PineappleInc', + }, + ], + }, + + { + navlabel: true, + subheader: 'Pages', + }, + { + id: uniqueId(), + title: 'Pricing', + icon: IconCurrencyDollar, + href: '/pages/pricing', + }, + { + id: uniqueId(), + title: 'Account Setting', + icon: IconUserCircle, + href: '/pages/account-settings', + }, + { + id: uniqueId(), + title: 'FAQ', + icon: IconHelp, + href: '/pages/faq', + }, + { + id: uniqueId(), + title: 'Landingpage', + icon: IconAppWindow, + href: '/landingpage', + }, + { + id: uniqueId(), + title: 'Widgets', + icon: IconLayout, + href: '/widgets/cards', + children: [ + { + id: uniqueId(), + title: 'Cards', + icon: IconPoint, + href: '/widgets/cards', + }, + { + id: uniqueId(), + title: 'Banners', + icon: IconPoint, + href: '/widgets/banners', + }, + { + id: uniqueId(), + title: 'Charts', + icon: IconPoint, + href: '/widgets/charts', + }, + ], + }, + { + navlabel: true, + subheader: 'Forms', + }, + { + id: uniqueId(), + title: 'Form Elements', + icon: IconApps, + href: '/forms/form-elements/autocomplete', + children: [ + { + id: uniqueId(), + title: 'Autocomplete', + icon: IconPoint, + href: '/forms/form-elements/autocomplete', + }, + { + id: uniqueId(), + title: 'Button', + icon: IconPoint, + href: '/forms/form-elements/button', + }, + { + id: uniqueId(), + title: 'Checkbox', + icon: IconPoint, + href: '/forms/form-elements/checkbox', + }, + { + id: uniqueId(), + title: 'Radio', + icon: IconPoint, + href: '/forms/form-elements/radio', + }, + { + id: uniqueId(), + title: 'Date Time', + icon: IconPoint, + href: '/forms/form-elements/date-time', + }, + { + id: uniqueId(), + title: 'Slider', + icon: IconPoint, + href: '/forms/form-elements/slider', + }, + { + id: uniqueId(), + title: 'Switch', + icon: IconPoint, + href: '/forms/form-elements/switch', + }, + ], + }, + { + id: uniqueId(), + title: 'Form Layout', + icon: IconFileDescription, + href: '/forms/form-layouts', + }, + { + id: uniqueId(), + title: 'Form Horizontal', + icon: IconBoxAlignBottom, + href: '/forms/form-horizontal', + }, + { + id: uniqueId(), + title: 'Form Vertical', + icon: IconBoxAlignLeft, + href: '/forms/form-vertical', + }, + { + id: uniqueId(), + title: 'Form Custom', + icon: IconFileDots, + href: '/forms/form-custom', + }, + { + id: uniqueId(), + title: 'Form Wizard', + icon: IconFiles, + href: '/forms/form-wizard', + }, + { + id: uniqueId(), + title: 'Form Validation', + icon: IconFiles, + href: '/forms/form-validation', + }, + { + id: uniqueId(), + title: 'Tiptap Editor', + icon: IconEdit, + href: '/forms/form-tiptap', + }, + { + navlabel: true, + subheader: 'Tables', + }, + { + id: uniqueId(), + title: 'Basic', + icon: IconBorderAll, + href: '/tables/basic', + }, + { + id: uniqueId(), + title: 'Collapsible', + icon: IconBorderHorizontal, + href: '/tables/collapsible', + }, + { + id: uniqueId(), + title: 'Enhanced', + icon: IconBorderInner, + href: '/tables/enhanced', + }, + { + id: uniqueId(), + title: 'Fixed Header', + icon: IconBorderVertical, + href: '/tables/fixed-header', + }, + { + id: uniqueId(), + title: 'Pagination', + icon: IconBorderTop, + href: '/tables/pagination', + }, + { + id: uniqueId(), + title: 'Search', + icon: IconBorderStyle2, + href: '/tables/search', + }, + { + id: uniqueId(), + title: 'React Table', + icon: IconBorderStyle2, + href: '/react-tables/basic', + children: [ + { + id: uniqueId(), + title: 'Basic', + icon: IconPoint, + href: '/react-tables/basic', + }, + { + id: uniqueId(), + title: 'Dense', + icon: IconPoint, + href: '/react-tables/dense', + }, + { + id: uniqueId(), + title: 'Filter', + icon: IconPoint, + href: '/react-tables/filter', + }, + { + id: uniqueId(), + title: 'Row Selection', + icon: IconPoint, + href: '/react-tables/row-selection', + }, + { + id: uniqueId(), + title: 'Pagination', + icon: IconPoint, + href: '/react-tables/pagination', + }, + { + id: uniqueId(), + title: 'Sorting', + icon: IconPoint, + href: '/react-tables/sorting', + }, + { + id: uniqueId(), + title: 'Column Visibility', + icon: IconPoint, + href: '/react-tables/column-visiblity', + }, + { + id: uniqueId(), + title: 'Editable', + icon: IconPoint, + href: '/react-tables/editable', + }, + { + id: uniqueId(), + title: 'Expanding', + icon: IconPoint, + href: '/react-tables/expanding', + }, + { + id: uniqueId(), + title: 'Sticky', + icon: IconPoint, + href: '/react-tables/sticky', + }, + { + id: uniqueId(), + title: 'Empty', + icon: IconPoint, + href: '/react-tables/empty', + }, + { + id: uniqueId(), + title: 'Drag & Drop', + icon: IconPoint, + href: '/react-tables/drag-drop', + }, + ], + }, + { + navlabel: true, + subheader: 'Mui Charts', + }, + + { + id: uniqueId(), + title: 'BarCharts', + icon: IconChartHistogram, + href: '/muicharts/barcharts', + }, + { + id: uniqueId(), + title: 'LineCharts', + icon: IconChartLine, + href: '/muicharts/linecharts/line', + children: [ + { + id: uniqueId(), + title: 'Lines', + icon: IconPoint, + href: '/muicharts/linecharts/line', + }, + { + id: uniqueId(), + title: 'Area', + icon: IconPoint, + href: '/muicharts/linecharts/area', + }, + ], + }, + { + id: uniqueId(), + title: 'PieCharts', + icon: IconChartPie2, + href: '/muicharts/piecharts', + }, + { + id: uniqueId(), + title: 'ScatterCharts', + icon: IconChartScatter, + href: '/muicharts/scattercharts', + }, + { + id: uniqueId(), + title: 'SparklineCharts', + icon: IconChartPpf, + href: '/muicharts/sparklinecharts', + }, + { + id: uniqueId(), + title: 'GaugeCharts', + icon: IconChartArcs3, + href: '/muicharts/gaugecharts', + }, + + { + navlabel: true, + subheader: 'Mui Trees', + }, + { + id: uniqueId(), + title: 'SimpleTreeView', + icon: IconListTree, + href: '/mui-trees/simpletree/simpletree-items', + children: [ + { + id: uniqueId(), + title: 'Items', + icon: IconPoint, + href: '/mui-trees/simpletree/simpletree-items', + }, + { + id: uniqueId(), + title: 'Selection', + icon: IconPoint, + href: '/mui-trees/simpletree/simpletree-selection', + }, + { + id: uniqueId(), + title: 'Expansion', + icon: IconPoint, + href: '/mui-trees/simpletree/simpletree-expansion', + }, + { + id: uniqueId(), + title: 'Customization', + icon: IconPoint, + href: '/mui-trees/simpletree/simpletree-customization', + }, + { + id: uniqueId(), + title: 'Focus', + icon: IconPoint, + href: '/mui-trees/simpletree/simpletree-focus', + }, + ], + }, + { + navlabel: true, + subheader: 'UI', + }, + { + id: uniqueId(), + title: 'Ui Components', + icon: IconBox, + href: '/ui-components/alert', + children: [ + { + id: uniqueId(), + title: 'Alert', + icon: IconPoint, + href: '/ui-components/alert', + }, + { + id: uniqueId(), + title: 'Accordion', + icon: IconPoint, + href: '/ui-components/accordion', + }, + { + id: uniqueId(), + title: 'Avatar', + icon: IconPoint, + href: '/ui-components/avatar', + }, + { + id: uniqueId(), + title: 'Chip', + icon: IconPoint, + href: '/ui-components/chip', + }, + { + id: uniqueId(), + title: 'Dialog', + icon: IconPoint, + href: '/ui-components/dialog', + }, + { + id: uniqueId(), + title: 'List', + icon: IconPoint, + href: '/ui-components/list', + }, + { + id: uniqueId(), + title: 'Popover', + icon: IconPoint, + href: '/ui-components/popover', + }, + { + id: uniqueId(), + title: 'Rating', + icon: IconPoint, + href: '/ui-components/rating', + }, + { + id: uniqueId(), + title: 'Tabs', + icon: IconPoint, + href: '/ui-components/tabs', + }, + { + id: uniqueId(), + title: 'Tooltip', + icon: IconPoint, + href: '/ui-components/tooltip', + }, + { + id: uniqueId(), + title: 'Transfer List', + icon: IconPoint, + href: '/ui-components/transfer-list', + }, + { + id: uniqueId(), + title: 'Typography', + icon: IconPoint, + href: '/ui-components/typography', + }, + ], + }, + + { + navlabel: true, + subheader: 'Charts', + }, + { + id: uniqueId(), + title: 'Line', + icon: IconChartLine, + href: '/charts/line-chart', + }, + { + id: uniqueId(), + title: 'Gredient', + icon: IconChartArcs, + href: '/charts/gredient-chart', + }, + { + id: uniqueId(), + title: 'Area', + icon: IconChartArea, + href: '/charts/area-chart', + }, + { + id: uniqueId(), + title: 'Candlestick', + icon: IconChartCandle, + href: '/charts/candlestick-chart', + }, + { + id: uniqueId(), + title: 'Column', + icon: IconChartDots, + href: '/charts/column-chart', + }, + { + id: uniqueId(), + title: 'Doughtnut & Pie', + icon: IconChartDonut3, + href: '/charts/doughnut-pie-chart', + }, + { + id: uniqueId(), + title: 'RadialBar & Radar', + icon: IconChartRadar, + href: '/charts/radialbar-chart', + }, + { + navlabel: true, + subheader: 'Auth', + }, + + { + id: uniqueId(), + title: 'Login', + icon: IconLogin, + href: '/auth/login', + children: [ + { + id: uniqueId(), + title: 'Side Login', + icon: IconPoint, + href: '/auth/login', + }, + { + id: uniqueId(), + title: 'Boxed Login', + icon: IconPoint, + href: '/auth/login2', + }, + ], + }, + { + id: uniqueId(), + title: 'Register', + icon: IconUserPlus, + href: '/auth/register', + children: [ + { + id: uniqueId(), + title: 'Side Register', + icon: IconPoint, + href: '/auth/register', + }, + { + id: uniqueId(), + title: 'Boxed Register', + icon: IconPoint, + href: '/auth/register2', + }, + ], + }, + { + id: uniqueId(), + title: 'Forgot Password', + icon: IconRotate, + href: '/auth/forgot-password', + children: [ + { + id: uniqueId(), + title: 'Side Forgot Password', + icon: IconPoint, + href: '/auth/forgot-password', + }, + { + id: uniqueId(), + title: 'Boxed Forgot Password', + icon: IconPoint, + href: '/auth/forgot-password2', + }, + ], + }, + + { + id: uniqueId(), + title: 'Two Steps', + icon: IconZoomCode, + href: '/auth/two-steps', + children: [ + { + id: uniqueId(), + title: 'Side Two Steps', + icon: IconPoint, + href: '/auth/two-steps', + }, + { + id: uniqueId(), + title: 'Boxed Two Steps', + icon: IconPoint, + href: '/auth/two-steps2', + }, + ], + }, + { + id: uniqueId(), + title: 'Error', + icon: IconAlertCircle, + href: '/400', + }, + { + id: uniqueId(), + title: 'Maintenance', + icon: IconSettings, + href: '/auth/maintenance', + }, + + { + navlabel: true, + subheader: 'Other', + }, + { + id: uniqueId(), + title: 'Menu Level', + icon: IconBoxMultiple, + href: '/menulevel/', + children: [ + { + id: uniqueId(), + title: 'Level 1', + icon: IconPoint, + href: '/l1', + }, + { + id: uniqueId(), + title: 'Level 1.1', + icon: IconPoint, + href: '/l1.1', + children: [ + { + id: uniqueId(), + title: 'Level 2', + icon: IconPoint, + href: '/l2', + }, + { + id: uniqueId(), + title: 'Level 2.1', + icon: IconPoint, + href: '/l2.1', + children: [ + { + id: uniqueId(), + title: 'Level 3', + icon: IconPoint, + href: '/l3', + }, + { + id: uniqueId(), + title: 'Level 3.1', + icon: IconPoint, + href: '/l3.1', + }, + ], + }, + ], + }, + ], + }, + { + id: uniqueId(), + title: 'Disabled', + icon: IconBan, + href: '/', + disabled: true, + }, + { + id: uniqueId(), + title: 'SubCaption', + subtitle: 'This is the sutitle', + icon: IconStar, + href: '/', + }, + + { + id: uniqueId(), + title: 'Chip', + icon: IconAward, + href: '/', + chip: '9', + chipColor: 'primary', + }, + { + id: uniqueId(), + title: 'Outlined', + icon: IconMoodSmile, + href: '/', + chip: 'outline', + variant: 'outlined', + chipColor: 'primary', + }, + { + id: uniqueId(), + title: 'External Link', + external: true, + icon: IconStar, + href: 'https://google.com', + }, +]; + +export default Menuitems; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/NavCollapse/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/NavCollapse/index.tsx new file mode 100644 index 0000000..b504e19 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/NavCollapse/index.tsx @@ -0,0 +1,152 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +import { useState } from 'react'; +import { useSelector } from 'src/store/Store'; +import { useLocation } from 'react-router'; + +// mui imports +import { + ListItemIcon, + ListItemButton, + Collapse, + styled, + ListItemText, + useTheme, +} from '@mui/material'; + +// custom imports +import NavItem from '../NavItem'; + +// plugins +import { IconChevronDown, IconChevronUp } from '@tabler/icons-react'; +import { useTranslation } from 'react-i18next'; +import { AppState } from 'src/store/Store'; + +type NavGroupProps = { + [x: string]: any; + navlabel?: boolean; + subheader?: string; + title?: string; + icon?: any; + href?: any; +}; + +interface NavCollapseProps { + menu: NavGroupProps; + level: number; + pathWithoutLastPart: any; + pathDirect: any; + hideMenu: any; + onClick: (event: React.MouseEvent) => void; +} + +// FC Component For Dropdown Menu +const NavCollapse = ({ + menu, + level, + pathWithoutLastPart, + pathDirect, + hideMenu, + onClick +}: NavCollapseProps) => { + const customizer = useSelector((state: AppState) => state.customizer); + const Icon = menu?.icon; + const theme = useTheme(); + const { pathname } = useLocation(); + const { t } = useTranslation(); + const [open, setOpen] = useState(true); + const menuIcon = + level > 1 ? : ; + + const handleClick = () => { + setOpen(!open); + }; + + // menu collapse for sub-levels + React.useEffect(() => { + setOpen(false); + menu?.children?.forEach((item: any) => { + if (item?.href === pathname) { + setOpen(true); + } + }); + }, [pathname, menu.children]); + + const ListItemStyled = styled(ListItemButton)(() => ({ + marginBottom: '2px', + padding: '8px 10px', + paddingLeft: hideMenu ? '10px' : level > 2 ? `${level * 15}px` : '10px', + backgroundColor: open && level < 2 ? theme.palette.primary.main : '', + whiteSpace: 'nowrap', + '&:hover': { + backgroundColor: pathname.includes(menu.href) || open + ? theme.palette.primary.main + : theme.palette.primary.light, + color: pathname.includes(menu.href) || open ? 'white' : theme.palette.primary.main, + }, + color: + open && level < 2 + ? 'white' + : level > 1 && open + ? theme.palette.primary.main + : theme.palette.text.secondary, + borderRadius: `${customizer.borderRadius}px`, + })); + + // If Menu has Children + const submenus = menu.children?.map((item: any) => { + if (item.children) { + return ( + + ); + } else { + return ( + + ); + } + }); + + return ( + <> + + + {menuIcon} + + {hideMenu ? '' : <>{t(`${menu.title}`)}} + {!open ? : } + + + {submenus} + + + ); +}; + +export default NavCollapse; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/NavGroup/NavGroup.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/NavGroup/NavGroup.tsx new file mode 100644 index 0000000..5bfc924 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/NavGroup/NavGroup.tsx @@ -0,0 +1,36 @@ +import { ListSubheader, styled, Theme } from '@mui/material'; +import { IconDots } from '@tabler/icons-react'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +type NavGroup = { + navlabel?: boolean; + subheader?: string; +}; + +interface ItemType { + item: NavGroup; + hideMenu: string | boolean; +} + +const NavGroup = ({ item, hideMenu }: ItemType) => { + const ListSubheaderStyle = styled((props: Theme | any) => ( + + ))(({ theme }) => ({ + ...theme.typography.overline, + fontWeight: '700', + marginTop: theme.spacing(3), + marginBottom: theme.spacing(0), + color: 'text.Primary', + lineHeight: '26px', + padding: '3px 12px', + marginLeft: hideMenu ? '' : '-10px', + })); + + return ( + {hideMenu ? : item?.subheader} + ); +}; + +export default NavGroup; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/NavItem/index.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/NavItem/index.tsx new file mode 100644 index 0000000..398ccbb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/NavItem/index.tsx @@ -0,0 +1,134 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { NavLink } from 'react-router'; + +// mui imports +import { + ListItemIcon, + List, + styled, + ListItemText, + Chip, + useTheme, + Typography, + ListItemButton, +} from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import { useTranslation } from 'react-i18next'; +import { AppState } from 'src/store/Store'; + +type NavGroup = { + [x: string]: any; + id?: string; + navlabel?: boolean; + subheader?: string; + title?: string; + icon?: any; + href?: string; + children?: NavGroup[]; + chip?: string; + chipColor?: any; + variant?: string | any; + external?: boolean; + level?: number; + onClick?: React.MouseEvent; +}; + +interface ItemType { + item: NavGroup; + hideMenu?: any; + onClick: (event: React.MouseEvent) => void; + level?: number | any; + pathDirect: string; +} + +const NavItem = ({ item, level, pathDirect, hideMenu, onClick }: ItemType) => { + const customizer = useSelector((state: AppState) => state.customizer); + const Icon = item?.icon; + const theme = useTheme(); + const { t } = useTranslation(); + const itemIcon = + level > 1 ? : ; + + const ListItemStyled = styled(ListItemButton)(() => ({ + whiteSpace: 'nowrap', + marginBottom: '2px', + padding: '8px 10px', + borderRadius: `${customizer.borderRadius}px`, + backgroundColor: level > 1 ? 'transparent !important' : 'inherit', + color: + level > 1 && pathDirect === item?.href + ? `${theme.palette.primary.main}!important` + : theme.palette.text.secondary, + paddingLeft: hideMenu ? '10px' : level > 2 ? `${level * 15}px` : '10px', + '&:hover': { + backgroundColor: theme.palette.primary.light, + color: theme.palette.primary.main, + }, + '&.Mui-selected': { + color: 'white', + backgroundColor: theme.palette.primary.main, + '&:hover': { + backgroundColor: theme.palette.primary.main, + color: 'white', + }, + }, + })); + + const listItemProps: { + component: any; + href?: string; + target?: any; + to?: any; + } = { + component: item?.external ? 'a' : NavLink, + to: item?.href, + href: item?.external ? item?.href : '', + target: item?.external ? '_blank' : '', + }; + + return ( + + + 1 && pathDirect === item?.href + ? `${theme.palette.primary.main}!important` + : 'inherit', + }} + > + {itemIcon} + + + {hideMenu ? '' : <>{t(`${item?.title}`)}} +
+ {item?.subtitle ? ( + {hideMenu ? '' : item?.subtitle} + ) : ( + '' + )} +
+ + {!item?.chip || hideMenu ? null : ( + + )} +
+
+ ); +}; + +export default NavItem; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/Sidebar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/Sidebar.tsx new file mode 100644 index 0000000..21898bd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/Sidebar.tsx @@ -0,0 +1,121 @@ +import { useMediaQuery, Box, Drawer, useTheme } from '@mui/material'; +import SidebarItems from './SidebarItems'; +import Logo from '../../shared/logo/Logo'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { hoverSidebar, toggleMobileSidebar } from 'src/store/customizer/CustomizerSlice'; +import Scrollbar from 'src/components/custom-scroll/Scrollbar'; +import { Profile } from './SidebarProfile/Profile'; +import { AppState } from 'src/store/Store'; + +const Sidebar = () => { + const lgUp = useMediaQuery((theme: any) => theme.breakpoints.up('lg')); + const customizer = useSelector((state: AppState) => state.customizer); + const dispatch = useDispatch(); + const theme = useTheme(); + const toggleWidth = + customizer.isCollapse && !customizer.isSidebarHover + ? customizer.MiniSidebarWidth + : customizer.SidebarWidth; + + const onHoverEnter = () => { + if (customizer.isCollapse) { + dispatch(hoverSidebar(true)); + } + }; + + const onHoverLeave = () => { + dispatch(hoverSidebar(false)); + }; + + if (lgUp) { + return ( + + {/* ------------------------------------------- */} + {/* Sidebar for desktop */} + {/* ------------------------------------------- */} + + {/* ------------------------------------------- */} + {/* Sidebar Box */} + {/* ------------------------------------------- */} + + {/* ------------------------------------------- */} + {/* Logo */} + {/* ------------------------------------------- */} + + + + + {/* ------------------------------------------- */} + {/* Sidebar Items */} + {/* ------------------------------------------- */} + + + + + + + ); + } + + return ( + dispatch(toggleMobileSidebar())} + variant="temporary" + PaperProps={{ + sx: { + width: customizer.SidebarWidth, + + // backgroundColor: + // customizer.activeMode === 'dark' + // ? customizer.darkBackground900 + // : customizer.activeSidebarBg, + // color: customizer.activeSidebarBg === '#ffffff' ? '' : 'white', + border: '0 !important', + boxShadow: (theme) => theme.shadows[8], + }, + }} + > + {/* ------------------------------------------- */} + {/* Logo */} + {/* ------------------------------------------- */} + + + + {/* ------------------------------------------- */} + {/* Sidebar For Mobile */} + {/* ------------------------------------------- */} + + + ); +}; + +export default Sidebar; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/SidebarItems.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/SidebarItems.tsx new file mode 100644 index 0000000..f55d95a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/SidebarItems.tsx @@ -0,0 +1,58 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Menuitems from './MenuItems'; +import { useLocation } from 'react-router'; +import { Box, List, useMediaQuery } from '@mui/material'; +import { useSelector, useDispatch } from 'src/store/Store'; +import { toggleMobileSidebar } from 'src/store/customizer/CustomizerSlice'; +import NavItem from './NavItem'; +import NavCollapse from './NavCollapse'; +import NavGroup from './NavGroup/NavGroup'; +import { AppState } from 'src/store/Store'; + +const SidebarItems = () => { + const { pathname } = useLocation(); + const pathDirect = pathname; + const pathWithoutLastPart = pathname.slice(0, pathname.lastIndexOf('/')); + const customizer = useSelector((state: AppState) => state.customizer); + const lgUp = useMediaQuery((theme: any) => theme.breakpoints.up('lg')); + const hideMenu: any = lgUp ? customizer.isCollapse && !customizer.isSidebarHover : ''; + const dispatch = useDispatch(); + + return ( + + + {Menuitems.map((item) => { + // {/********SubHeader**********/} + if (item.subheader) { + return ; + + // {/********If Sub Menu**********/} + /* eslint no-else-return: "off" */ + } else if (item.children) { + return ( + dispatch(toggleMobileSidebar())} + /> + ); + + // {/********If Sub No Menu**********/} + } else { + return ( + dispatch(toggleMobileSidebar())} /> + ); + } + })} + + + ); +}; +export default SidebarItems; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/SidebarProfile/Profile.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/SidebarProfile/Profile.tsx new file mode 100644 index 0000000..d75485d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/SidebarProfile/Profile.tsx @@ -0,0 +1,47 @@ +import { Box, Avatar, Typography, IconButton, Tooltip, useMediaQuery } from '@mui/material'; +import { useSelector } from 'src/store/Store'; +import img1 from 'src/assets/images/profile/user-1.jpg'; +import { IconPower } from '@tabler/icons-react'; +import { AppState } from 'src/store/Store'; +import { Link } from 'react-router'; + +export const Profile = () => { + const customizer = useSelector((state: AppState) => state.customizer); + const lgUp = useMediaQuery((theme: any) => theme.breakpoints.up('lg')); + const hideMenu = lgUp ? customizer.isCollapse && !customizer.isSidebarHover : ''; + + return ( + + {!hideMenu ? ( + <> + + + + Mathew + Designer + + + + + + + + + + ) : ( + '' + )} + + ); +}; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/module-name.d.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/module-name.d.ts new file mode 100644 index 0000000..4cefc92 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/layouts/full/vertical/sidebar/module-name.d.ts @@ -0,0 +1 @@ +declare module 'stylis-plugin-rtl'; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/main.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/main.tsx new file mode 100644 index 0000000..870ab89 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/main.tsx @@ -0,0 +1,18 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { Suspense } from 'react'; +import { Provider } from 'react-redux'; +import ReactDOM from 'react-dom/client'; +import App from './App'; +import { store } from './store/Store'; +import Spinner from './views/spinner/Spinner'; +import './utils/i18n'; +import './_mockApis'; + +ReactDOM.createRoot(document.getElementById('root')!).render( + + }> + + + , +) diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/routes/Router.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/routes/Router.tsx new file mode 100644 index 0000000..a0958d9 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/routes/Router.tsx @@ -0,0 +1,308 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { lazy } from 'react'; +import { createBrowserRouter, Navigate } from 'react-router'; +import Loadable from '../layouts/full/shared/loadable/Loadable'; + +/* ***Layouts**** */ +const FullLayout = Loadable(lazy(() => import('../layouts/full/FullLayout'))); +const BlankLayout = Loadable(lazy(() => import('../layouts/blank/BlankLayout'))); + +/* ****Pages***** */ +const ModernDash = Loadable(lazy(() => import('../views/dashboard/Modern'))); +const EcommerceDash = Loadable(lazy(() => import('../views/dashboard/Ecommerce'))); + +/* ****Apps***** */ +// const Blog = Loadable(lazy(() => import('../views/apps/blog/Blog'))); +// const BlogDetail = Loadable(lazy(() => import('../views/apps/blog/BlogPost'))); +const Contacts = Loadable(lazy(() => import('../views/apps/contacts/Contacts'))); +const Chats = Loadable(lazy(() => import('../views/apps/chat/Chat'))); +const Notes = Loadable(lazy(() => import('../views/apps/notes/Notes'))); +const Tickets = Loadable(lazy(() => import('../views/apps/tickets/Tickets'))); +const Ecommerce = Loadable(lazy(() => import('../views/apps/eCommerce/Ecommerce'))); +const EcommerceDetail = Loadable(lazy(() => import('../views/apps/eCommerce/EcommerceDetail'))); +const EcommerceAddProduct = Loadable( + lazy(() => import('../views/apps/eCommerce/EcommerceAddProduct')), +); +const EcommerceEditProduct = Loadable( + lazy(() => import('../views/apps/eCommerce/EcommerceEditProduct')), +); +const EcomProductList = Loadable(lazy(() => import('../views/apps/eCommerce/EcomProductList'))); +const EcomProductCheckout = Loadable( + lazy(() => import('../views/apps/eCommerce/EcommerceCheckout')), +); +const Calendar = Loadable(lazy(() => import('../views/apps/calendar/BigCalendar'))); +const UserProfile = Loadable(lazy(() => import('../views/apps/user-profile/UserProfile'))); +const Followers = Loadable(lazy(() => import('../views/apps/user-profile/Followers'))); +const Friends = Loadable(lazy(() => import('../views/apps/user-profile/Friends'))); +const Gallery = Loadable(lazy(() => import('../views/apps/user-profile/Gallery'))); +const Email = Loadable(lazy(() => import('../views/apps/email/Email'))); +const InvoiceList = Loadable(lazy(() => import('../views/apps/invoice/List'))); +const InvoiceCreate = Loadable(lazy(() => import('../views/apps/invoice/Create'))); +const InvoiceDetail = Loadable(lazy(() => import('../views/apps/invoice/Detail'))); +const InvoiceEdit = Loadable(lazy(() => import('../views/apps/invoice/Edit'))); +const Kanban = Loadable(lazy(() => import('../views/apps/kanban/Kanban'))); + +// ui components +const MuiAlert = Loadable(lazy(() => import('../views/ui-components/MuiAlert'))); +const MuiAccordion = Loadable(lazy(() => import('../views/ui-components/MuiAccordion'))); +const MuiAvatar = Loadable(lazy(() => import('../views/ui-components/MuiAvatar'))); +const MuiChip = Loadable(lazy(() => import('../views/ui-components/MuiChip'))); +const MuiDialog = Loadable(lazy(() => import('../views/ui-components/MuiDialog'))); +const MuiList = Loadable(lazy(() => import('../views/ui-components/MuiList'))); +const MuiPopover = Loadable(lazy(() => import('../views/ui-components/MuiPopover'))); +const MuiRating = Loadable(lazy(() => import('../views/ui-components/MuiRating'))); +const MuiTabs = Loadable(lazy(() => import('../views/ui-components/MuiTabs'))); +const MuiTooltip = Loadable(lazy(() => import('../views/ui-components/MuiTooltip'))); +const MuiTransferList = Loadable(lazy(() => import('../views/ui-components/MuiTransferList'))); +const MuiTypography = Loadable(lazy(() => import('../views/ui-components/MuiTypography'))); + +// form elements +const MuiAutoComplete = Loadable( + lazy(() => import('../views/forms/form-elements/MuiAutoComplete')), +); +const MuiButton = Loadable(lazy(() => import('../views/forms/form-elements/MuiButton'))); +const MuiCheckbox = Loadable(lazy(() => import('../views/forms/form-elements/MuiCheckbox'))); +const MuiRadio = Loadable(lazy(() => import('../views/forms/form-elements/MuiRadio'))); +const MuiSlider = Loadable(lazy(() => import('../views/forms/form-elements/MuiSlider'))); +const MuiDateTime = Loadable(lazy(() => import('../views/forms/form-elements/MuiDateTime'))); +const MuiSwitch = Loadable(lazy(() => import('../views/forms/form-elements/MuiSwitch'))); + +// forms +const FormLayouts = Loadable(lazy(() => import('../views/forms/FormLayouts'))); +const FormCustom = Loadable(lazy(() => import('../views/forms/FormCustom'))); +const FormHorizontal = Loadable(lazy(() => import('../views/forms/FormHorizontal'))); +const FormVertical = Loadable(lazy(() => import('../views/forms/FormVertical'))); +const FormWizard = Loadable(lazy(() => import('../views/forms/FormWizard'))); +const FormValidation = Loadable(lazy(() => import('../views/forms/FormValidation'))); +const TiptapEditor = Loadable(lazy(() => import('../views/forms/from-tiptap/TiptapEditor'))); + +// pages +const RollbaseCASL = Loadable(lazy(() => import('../views/pages/rollbaseCASL/RollbaseCASL'))); +const Faq = Loadable(lazy(() => import('../views/pages/faq/Faq'))); +const Pricing = Loadable(lazy(() => import('../views/pages/pricing/Pricing'))); +const AccountSetting = Loadable( + lazy(() => import('../views/pages/account-setting/AccountSetting')), +); + +// charts +const AreaChart = Loadable(lazy(() => import('../views/charts/AreaChart'))); +const CandlestickChart = Loadable(lazy(() => import('../views/charts/CandlestickChart'))); +const ColumnChart = Loadable(lazy(() => import('../views/charts/ColumnChart'))); +const DoughnutChart = Loadable(lazy(() => import('../views/charts/DoughnutChart'))); +const GredientChart = Loadable(lazy(() => import('../views/charts/GredientChart'))); +const RadialbarChart = Loadable(lazy(() => import('../views/charts/RadialbarChart'))); +const LineChart = Loadable(lazy(() => import('../views/charts/LineChart'))); + +// tables +const BasicTable = Loadable(lazy(() => import('../views/tables/BasicTable'))); +const EnhanceTable = Loadable(lazy(() => import('../views/tables/EnhanceTable'))); +const PaginationTable = Loadable(lazy(() => import('../views/tables/PaginationTable'))); +const FixedHeaderTable = Loadable(lazy(() => import('../views/tables/FixedHeaderTable'))); +const CollapsibleTable = Loadable(lazy(() => import('../views/tables/CollapsibleTable'))); +const SearchTable = Loadable(lazy(() => import('../views/tables/SearchTable'))); + +//react tables +const ReactBasicTable = Loadable(lazy(() => import('../views/react-tables/basic/page'))); +const ReactColumnVisibilityTable = Loadable( + lazy(() => import('../views/react-tables/columnvisibility/page')), +); +const ReactDenseTable = Loadable(lazy(() => import('../views/react-tables/dense/page'))); +const ReactDragDropTable = Loadable(lazy(() => import('../views/react-tables/drag-drop/page'))); +const ReactEditableTable = Loadable(lazy(() => import('../views/react-tables/editable/page'))); +const ReactEmptyTable = Loadable(lazy(() => import('../views/react-tables/empty/page'))); +const ReactExpandingTable = Loadable(lazy(() => import('../views/react-tables/expanding/page'))); +const ReactFilterTable = Loadable(lazy(() => import('../views/react-tables/filtering/page'))); +const ReactPaginationTable = Loadable(lazy(() => import('../views/react-tables/pagination/page'))); +const ReactRowSelectionTable = Loadable( + lazy(() => import('../views/react-tables/row-selection/page')), +); +const ReactSortingTable = Loadable(lazy(() => import('../views/react-tables/sorting/page'))); +const ReactStickyTable = Loadable(lazy(() => import('../views/react-tables/sticky/page'))); + +//mui charts +const BarCharts = Loadable(lazy(() => import('../views/muicharts/barcharts/page'))); +const GaugeCharts = Loadable(lazy(() => import('../views/muicharts/gaugecharts/page'))); +const AreaCharts = Loadable(lazy(() => import('../views/muicharts/linecharts/area/page'))); +const LineCharts = Loadable(lazy(() => import('../views/muicharts/linecharts/line/page'))); +const PieCharts = Loadable(lazy(() => import('../views/muicharts/piecharts/page'))); +const ScatterCharts = Loadable(lazy(() => import('../views/muicharts/scattercharts/page'))); +const SparklineCharts = Loadable(lazy(() => import('../views/muicharts/sparklinecharts/page'))); + +//mui charts +const SimpletreeCustomization = Loadable(lazy(() => import('../views/mui-trees/simpletree/simpletree-customization/page'))); +const SimpletreeExpansion = Loadable(lazy(() => import('../views/mui-trees/simpletree/simpletree-expansion/page'))); +const SimpletreeFocus = Loadable(lazy(() => import('../views/mui-trees/simpletree/simpletree-focus/page'))); +const SimpletreeItems = Loadable(lazy(() => import('../views/mui-trees/simpletree/simpletree-items/page'))); +const SimpletreeSelection = Loadable(lazy(() => import('../views/mui-trees/simpletree/simpletree-selection/page'))); + +// widget +const WidgetCards = Loadable(lazy(() => import('../views/widgets/cards/WidgetCards'))); +const WidgetBanners = Loadable(lazy(() => import('../views/widgets/banners/WidgetBanners'))); +const WidgetCharts = Loadable(lazy(() => import('../views/widgets/charts/WidgetCharts'))); + +// authentication +const Login = Loadable(lazy(() => import('../views/authentication/auth1/Login'))); +const Login2 = Loadable(lazy(() => import('../views/authentication/auth2/Login2'))); +const Register = Loadable(lazy(() => import('../views/authentication/auth1/Register'))); +const Register2 = Loadable(lazy(() => import('../views/authentication/auth2/Register2'))); +const ForgotPassword = Loadable(lazy(() => import('../views/authentication/auth1/ForgotPassword'))); +const ForgotPassword2 = Loadable( + lazy(() => import('../views/authentication/auth2/ForgotPassword2')), +); +const TwoSteps = Loadable(lazy(() => import('../views/authentication/auth1/TwoSteps'))); +const TwoSteps2 = Loadable(lazy(() => import('../views/authentication/auth2/TwoSteps2'))); +const Error = Loadable(lazy(() => import('../views/authentication/Error'))); +const Maintenance = Loadable(lazy(() => import('../views/authentication/Maintenance'))); + +// landingpage +const Landingpage = Loadable(lazy(() => import('../views/pages/landingpage/Landingpage'))); + +// front end pages +const Homepage = Loadable(lazy(() => import('../views/pages/frontend-pages/Homepage'))); +const About = Loadable(lazy(() => import('../views/pages/frontend-pages/About'))); +const Contact = Loadable(lazy(() => import('../views/pages/frontend-pages/Contact'))); +const Portfolio = Loadable(lazy(() => import('../views/pages/frontend-pages/Portfolio'))); +const PagePricing = Loadable(lazy(() => import('../views/pages/frontend-pages/Pricing'))); +const BlogPage = Loadable(lazy(() => import('../views/pages/frontend-pages/Blog'))); +const BlogPost = Loadable(lazy(() => import('../views/pages/frontend-pages/BlogPost'))); + + + +const Router = [ + { + path: '/', + element: , + children: [ + { path: '/', element: }, + { path: '/dashboards/modern', exact: true, element: }, + { path: '/dashboards/ecommerce', exact: true, element: }, + { path: '/apps/contacts', element: }, + // { path: '/apps/blog/posts', element: }, + // { path: '/frontend-pages/blog/detail/:id', element: }, + { path: '/apps/chats', element: }, + { path: '/apps/email', element: }, + { path: '/apps/notes', element: }, + { path: '/apps/tickets', element: }, + { path: '/apps/ecommerce/shop', element: }, + { path: '/apps/ecommerce/eco-product-list', element: }, + { path: '/apps/ecommerce/eco-checkout', element: }, + { path: '/apps/ecommerce/add-product', element: }, + { path: '/apps/ecommerce/edit-product', element: }, + { path: '/apps/ecommerce/detail/:id', element: }, + { path: '/apps/followers', element: }, + { path: '/apps/friends', element: }, + { path: '/apps/gallery', element: }, + { path: '/apps/kanban', element: }, + { path: '/apps/invoice/list', element: }, + { path: '/apps/invoice/create', element: }, + { path: '/apps/invoice/detail/:id', element: }, + { path: '/apps/invoice/edit/:id', element: }, + { path: '/user-profile', element: }, + { path: '/apps/calendar', element: }, + { path: '/ui-components/alert', element: }, + { path: '/ui-components/accordion', element: }, + { path: '/ui-components/avatar', element: }, + { path: '/ui-components/chip', element: }, + { path: '/ui-components/dialog', element: }, + { path: '/ui-components/list', element: }, + { path: '/ui-components/popover', element: }, + { path: '/ui-components/rating', element: }, + { path: '/ui-components/tabs', element: }, + { path: '/ui-components/tooltip', element: }, + { path: '/ui-components/transfer-list', element: }, + { path: '/ui-components/typography', element: }, + { path: '/pages/casl', element: }, + { path: '/pages/pricing', element: }, + { path: '/pages/faq', element: }, + { path: '/pages/account-settings', element: }, + { path: '/tables/basic', element: }, + { path: '/tables/enhanced', element: }, + { path: '/tables/pagination', element: }, + { path: '/tables/fixed-header', element: }, + { path: '/tables/collapsible', element: }, + { path: '/tables/search', element: }, + { path: '/forms/form-elements/autocomplete', element: }, + { path: '/forms/form-elements/button', element: }, + { path: '/forms/form-elements/checkbox', element: }, + { path: '/forms/form-elements/radio', element: }, + { path: '/forms/form-elements/slider', element: }, + { path: '/forms/form-elements/date-time', element: }, + { path: '/forms/form-elements/switch', element: }, + { path: '/forms/form-elements/switch', element: }, + { path: '/forms/form-layouts', element: }, + { path: '/forms/form-custom', element: }, + { path: '/forms/form-wizard', element: }, + { path: '/forms/form-validation', element: }, + { path: '/forms/form-horizontal', element: }, + { path: '/forms/form-vertical', element: }, + { path: '/forms/form-tiptap', element: }, + { path: '/charts/area-chart', element: }, + { path: '/charts/line-chart', element: }, + { path: '/charts/gredient-chart', element: }, + { path: '/charts/candlestick-chart', element: }, + { path: '/charts/column-chart', element: }, + { path: '/charts/doughnut-pie-chart', element: }, + { path: '/charts/radialbar-chart', element: }, + { path: '/widgets/cards', element: }, + { path: '/widgets/banners', element: }, + { path: '/widgets/charts', element: }, + { path: '/react-tables/basic', element: }, + { path: '/react-tables/column-visiblity', element: }, + { path: '/react-tables/drag-drop', element: }, + { path: '/react-tables/dense', element: }, + { path: '/react-tables/editable', element: }, + { path: '/react-tables/empty', element: }, + { path: '/react-tables/expanding', element: }, + { path: '/react-tables/filter', element: }, + { path: '/react-tables/pagination', element: }, + { path: '/react-tables/row-selection', element: }, + { path: '/react-tables/sorting', element: }, + { path: '/react-tables/sticky', element: }, + + { path: '/muicharts/barcharts', element: }, + { path: '/muicharts/gaugecharts', element: }, + { path: '/muicharts/linecharts/area', element: }, + { path: '/muicharts/linecharts/line', element: }, + { path: '/muicharts/piecharts', element: }, + { path: '/muicharts/scattercharts', element: }, + { path: '/muicharts/sparklinecharts', element: }, + + { path: '/mui-trees/simpletree/simpletree-customization', element: }, + { path: '/mui-trees/simpletree/simpletree-expansion', element: }, + { path: '/mui-trees/simpletree/simpletree-focus', element: }, + { path: '/mui-trees/simpletree/simpletree-items', element: }, + { path: '/mui-trees/simpletree/simpletree-selection', element: }, + + { path: '*', element: }, + ], + }, + { + path: '/', + element: , + children: [ + { path: '/auth/404', element: }, + { path: '/auth/login', element: }, + { path: '/auth/login2', element: }, + { path: '/auth/register', element: }, + { path: '/auth/register2', element: }, + { path: '/auth/forgot-password', element: }, + { path: '/auth/forgot-password2', element: }, + { path: '/auth/two-steps', element: }, + { path: '/auth/two-steps2', element: }, + { path: '/auth/maintenance', element: }, + { path: '/landingpage', element: }, + { path: '/frontend-pages/homepage', element: }, + { path: '/frontend-pages/about', element: }, + { path: '/frontend-pages/contact', element: }, + { path: '/frontend-pages/portfolio', element: }, + { path: '/frontend-pages/pricing', element: }, + { path: '/frontend-pages/blog', element: }, + { path: '/frontend-pages/blog/detail/:id', element: }, + { path: '*', element: }, + ], + }, +]; +const router = createBrowserRouter(Router); + +export default router; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/store/Store.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/store/Store.tsx new file mode 100644 index 0000000..2a8f8e2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/store/Store.tsx @@ -0,0 +1,50 @@ +import { configureStore } from '@reduxjs/toolkit'; +import CustomizerReducer from './customizer/CustomizerSlice'; +import EcommerceReducer from './apps/eCommerce/ECommerceSlice'; +import ChatsReducer from './apps/chat/ChatSlice'; +import NotesReducer from './apps/notes/NotesSlice'; +import EmailReducer from './apps/email/EmailSlice'; +import TicketReducer from './apps/tickets/TicketSlice'; +import ContactsReducer from './apps/contacts/ContactSlice'; +import UserProfileReducer from './apps/userProfile/UserProfileSlice'; +import BlogReducer from './apps/blog/BlogSlice'; +import { combineReducers } from 'redux'; +import { + useDispatch as useAppDispatch, + useSelector as useAppSelector, + TypedUseSelectorHook, +} from 'react-redux'; + +export const store = configureStore({ + reducer: { + customizer: CustomizerReducer, + ecommerceReducer: EcommerceReducer, + chatReducer: ChatsReducer, + emailReducer: EmailReducer, + notesReducer: NotesReducer, + contactsReducer: ContactsReducer, + ticketReducer: TicketReducer, + userpostsReducer: UserProfileReducer, + blogReducer: BlogReducer, + }, +}); + +const rootReducer = combineReducers({ + customizer: CustomizerReducer, + ecommerceReducer: EcommerceReducer, + chatReducer: ChatsReducer, + emailReducer: EmailReducer, + notesReducer: NotesReducer, + contactsReducer: ContactsReducer, + ticketReducer: TicketReducer, + userpostsReducer: UserProfileReducer, + blogReducer: BlogReducer, +}); + +export type AppState = ReturnType; +export type AppDispatch = typeof store.dispatch; +export const { dispatch } = store; +export const useDispatch = () => useAppDispatch(); +export const useSelector: TypedUseSelectorHook = useAppSelector; + +export default store; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/blog/BlogSlice.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/blog/BlogSlice.tsx new file mode 100644 index 0000000..4495fc6 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/blog/BlogSlice.tsx @@ -0,0 +1,60 @@ +import axios from 'src/utils/axios'; +import { createSlice } from '@reduxjs/toolkit'; +import { AppDispatch } from 'src/store/Store'; + +interface StateType { + blogposts: any[]; + recentPosts: any[]; + blogSearch: string; + sortBy: string; + selectedPost: any; +} + +const initialState = { + blogposts: [], + recentPosts: [], + blogSearch: '', + sortBy: 'newest', + selectedPost: null, +}; + +export const BlogSlice = createSlice({ + name: 'Blog', + initialState, + reducers: { + getPosts: (state: StateType, action) => { + state.blogposts = action.payload; + }, + getPost: (state: StateType, action) => { + state.selectedPost = action.payload; + }, + }, +}); + +export const { getPosts, getPost } = BlogSlice.actions; + +export const fetchBlogPosts = () => async (dispatch: AppDispatch) => { + try { + const response = await axios.get('/api/data/blog/BlogPosts'); + dispatch(getPosts(response.data)); + } catch (err) { + throw new Error(); + } +}; +export const addComment = (postId: number, comment: any) => async (dispatch: AppDispatch) => { + try { + const response = await axios.post('/api/data/blog/post/add', { postId, comment }); + dispatch(getPosts(response.data.posts)); + } catch (err: any) { + throw new Error(err); + } +}; +export const fetchBlogPost = (title: string) => async (dispatch: AppDispatch) => { + try { + const response = await axios.post('/api/data/blog/post', { title }); + dispatch(getPost(response.data.post)); + } catch (err: any) { + throw new Error(err); + } +}; +export default BlogSlice.reducer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/chat/ChatSlice.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/chat/ChatSlice.tsx new file mode 100644 index 0000000..000ee58 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/chat/ChatSlice.tsx @@ -0,0 +1,70 @@ +import axios from '../../../utils/axios'; +import { createSlice } from '@reduxjs/toolkit'; +import { AppDispatch } from 'src/store/Store'; +import { uniqueId } from 'lodash'; +import { sub } from 'date-fns'; + +const API_URL = '/api/data/chat/ChatData'; + +interface StateType { + chats: any[]; + chatContent: number; + chatSearch: string; +} + +const initialState = { + chats: [], + chatContent: 1, + chatSearch: '', +}; + +export const ChatSlice = createSlice({ + name: 'chat', + initialState, + reducers: { + getChats: (state, action) => { + state.chats = action.payload; + }, + SearchChat: (state, action) => { + state.chatSearch = action.payload; + }, + SelectChat: (state: StateType, action) => { + state.chatContent = action.payload; + }, + sendMsg: (state: StateType, action) => { + const conversation = action.payload; + const { id, msg } = conversation; + + const newMessage = { + id: id, + msg: msg, + type: 'text', + attachments: [], + createdAt: sub(new Date(), { seconds: 1 }), + senderId: uniqueId(), + }; + + state.chats = state.chats.map((chat) => + chat.id === action.payload.id + ? { + ...chat, + ...chat.messages.push(newMessage), + } + : chat, + ); + }, + }, +}); + +export const { SearchChat, getChats, sendMsg, SelectChat } = ChatSlice.actions; + +export const fetchChats = () => async (dispatch: AppDispatch) => { + try { + const response = await axios.get(`${API_URL}`); + dispatch(getChats(response.data)); + } catch (err: any) { + throw new Error(err); + } +}; + +export default ChatSlice.reducer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/contacts/ContactSlice.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/contacts/ContactSlice.tsx new file mode 100644 index 0000000..6ae57ca --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/contacts/ContactSlice.tsx @@ -0,0 +1,127 @@ +import axios from '../../../utils/axios'; +import { createSlice } from '@reduxjs/toolkit'; +import { AppDispatch } from 'src/store/Store'; +import type { PayloadAction } from '@reduxjs/toolkit'; + +const API_URL = '/api/data/contacts/ContactsData'; + +interface StateType { + contacts: any[]; + contactContent: number; + contactSearch: string; + editContact: boolean; + currentFilter: string; +} + +const initialState = { + contacts: [], + contactContent: 1, + contactSearch: '', + editContact: false, + currentFilter: 'show_all', +}; + +export const ContactSlice = createSlice({ + name: 'contacts', + initialState, + reducers: { + getContacts: (state: StateType, action) => { + state.contacts = action.payload; + }, + SearchContact: (state: StateType, action) => { + state.contactSearch = action.payload; + }, + SelectContact: (state: StateType, action) => { + state.contactContent = action.payload; + }, + DeleteContact: (state: StateType, action) => { + state.contacts = state.contacts.map((contact) => + contact.id === action.payload ? { ...contact, deleted: !contact.deleted } : contact, + ); + }, + toggleStarredContact: (state: StateType, action) => { + state.contacts = state.contacts.map((contact) => + contact.id === action.payload ? { ...contact, starred: !contact.starred } : contact, + ); + }, + isEdit: (state: StateType) => { + state.editContact = !state.editContact; + }, + setVisibilityFilter: (state: StateType, action) => { + state.currentFilter = action.payload; + }, + + UpdateContact: { + reducer: (state: StateType, action: PayloadAction) => { + state.contacts = state.contacts.map((contact) => + contact.id === action.payload.id + ? { ...contact, [action.payload.field]: action.payload.value } + : contact, + ); + }, + prepare: (id, field, value) => { + return { + payload: { id, field, value }, + }; + }, + }, + addContact: { + reducer: (state: StateType, action: PayloadAction) => { + state.contacts.push(action.payload); + }, + prepare: ( + id, + firstname, + lastname, + image, + department, + company, + phone, + email, + address, + notes, + ) => { + return { + payload: { + id, + firstname, + lastname, + image, + department, + company, + phone, + email, + address, + notes, + frequentlycontacted: false, + starred: false, + deleted: false, + }, + }; + }, + }, + }, +}); + +export const { + getContacts, + SearchContact, + isEdit, + SelectContact, + DeleteContact, + toggleStarredContact, + UpdateContact, + addContact, + setVisibilityFilter, +} = ContactSlice.actions; + +export const fetchContacts = () => async (dispatch: AppDispatch) => { + try { + const response = await axios.get(`${API_URL}`); + dispatch(getContacts(response.data)); + } catch (err: any) { + throw new Error(err); + } +}; + +export default ContactSlice.reducer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/eCommerce/ECommerceSlice.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/eCommerce/ECommerceSlice.tsx new file mode 100644 index 0000000..afe3616 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/eCommerce/ECommerceSlice.tsx @@ -0,0 +1,164 @@ +import axios from '../../../utils/axios'; +import { filter, map } from 'lodash'; +import { createSlice } from '@reduxjs/toolkit'; +import { AppDispatch } from 'src/store/Store'; + +const API_URL = '/api/data/eCommerce/ProductsData'; + +interface StateType { + products: any[]; + productSearch: string; + sortBy: string; + cart: any[]; + total: number; + filters: { + category: string; + color: string; + gender: string; + price: string; + rating: string; + }; + error: string; +} + +const initialState = { + products: [], + productSearch: '', + sortBy: 'newest', + cart: [], + total: 0, + filters: { + category: 'All', + color: 'All', + gender: 'All', + price: 'All', + rating: '', + }, + error: '', +}; + +export const EcommerceSlice = createSlice({ + name: 'ecommerce', + initialState, + reducers: { + // HAS ERROR + + hasError(state: StateType, action) { + state.error = action.payload; + }, + + // GET PRODUCTS + getProducts: (state, action) => { + state.products = action.payload; + }, + SearchProduct: (state, action) => { + state.productSearch = action.payload; + }, + + // SORT PRODUCTS + sortByProducts(state, action) { + state.sortBy = action.payload; + }, + + // SORT PRODUCTS + sortByGender(state, action) { + state.filters.gender = action.payload.gender; + }, + + // SORT By Color + sortByColor(state, action) { + state.filters.color = action.payload.color; + }, + + // SORT By Color + sortByPrice(state, action) { + state.filters.price = action.payload.price; + }, + + // FILTER PRODUCTS + filterProducts(state, action) { + state.filters.category = action.payload.category; + }, + + // FILTER Reset + filterReset(state) { + state.filters.category = 'All'; + state.filters.color = 'All'; + state.filters.gender = 'All'; + state.filters.price = 'All'; + state.sortBy = 'newest'; + }, + + // ADD TO CART + addToCart(state: StateType, action) { + const product = action.payload; + state.cart = [...state.cart, product]; + }, + + // qty increment + increment(state: StateType, action) { + const productId = action.payload; + const updateCart = map(state.cart, (product) => { + if (product.id === productId) { + return { + ...product, + qty: product.qty + 1, + }; + } + + return product; + }); + + state.cart = updateCart; + }, + + // qty decrement + decrement(state: StateType, action) { + const productId = action.payload; + const updateCart = map(state.cart, (product) => { + if (product.id === productId) { + return { + ...product, + qty: product.qty - 1, + }; + } + + return product; + }); + + state.cart = updateCart; + }, + + // delete Cart + deleteCart(state: StateType, action) { + const updateCart = filter(state.cart, (item) => item.id !== action.payload); + state.cart = updateCart; + }, + }, +}); +export const { + hasError, + getProducts, + SearchProduct, + sortByProducts, + filterProducts, + sortByGender, + increment, + deleteCart, + decrement, + addToCart, + sortByPrice, + filterReset, + sortByColor, +} = EcommerceSlice.actions; + +export const fetchProducts = () => async (dispatch: AppDispatch) => { + try { + const response = await axios.get(`${API_URL}`); + dispatch(getProducts(response.data)); + } catch (error) { + dispatch(hasError(error)); + } +}; + +export default EcommerceSlice.reducer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/email/EmailSlice.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/email/EmailSlice.tsx new file mode 100644 index 0000000..77aa0e1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/email/EmailSlice.tsx @@ -0,0 +1,80 @@ +import axios from '../../../utils/axios'; +import { createSlice } from '@reduxjs/toolkit'; +import { AppDispatch } from 'src/store/Store'; + +const API_URL = '/api/data/email/EmailData'; + +interface StateType { + emails: any[]; + emailContent: number; + emailSearch: string; + currentFilter: string; +} + +const initialState = { + emails: [], + emailContent: 1, + emailSearch: '', + currentFilter: 'inbox', +}; + +export const EmailSlice = createSlice({ + name: 'email', + initialState, + reducers: { + getEmails: (state: StateType, action) => { + state.emails = action.payload; + }, + SearchEmail: (state: StateType, action) => { + state.emailSearch = action.payload; + }, + SelectEmail: (state: StateType, action) => { + state.emailContent = action.payload; + }, + starEmail: (state: StateType, action) => { + state.emails = state.emails.map((email) => + email.id === action.payload ? { ...email, starred: !email.starred } : email, + ); + }, + importantEmail: (state: StateType, action) => { + state.emails = state.emails.map((email) => + email.id === action.payload ? { ...email, important: !email.important } : email, + ); + }, + checkEmail: (state: StateType, action) => { + state.emails = state.emails.map((email) => + email.id === action.payload ? { ...email, checked: !email.checked } : email, + ); + }, + deleteEmail: (state: StateType, action) => { + state.emails = state.emails.map((email) => + email.id === action.payload ? { ...email, trash: !email.trash } : email, + ); + }, + setVisibilityFilter: (state, action) => { + state.currentFilter = action.payload; + }, + }, +}); + +export const { + SearchEmail, + SelectEmail, + getEmails, + starEmail, + importantEmail, + setVisibilityFilter, + deleteEmail, + checkEmail, +} = EmailSlice.actions; + +export const fetchEmails = () => async (dispatch: AppDispatch) => { + try { + const response = await axios.get(`${API_URL}`); + dispatch(getEmails(response.data)); + } catch (err: any) { + throw new Error(err); + } +}; + +export default EmailSlice.reducer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/notes/NotesSlice.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/notes/NotesSlice.tsx new file mode 100644 index 0000000..fdf3f70 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/notes/NotesSlice.tsx @@ -0,0 +1,77 @@ +import axios from '../../../utils/axios'; +import { createSlice } from '@reduxjs/toolkit'; +import { AppDispatch } from 'src/store/Store'; +import type { PayloadAction } from '@reduxjs/toolkit'; + +const API_URL = '/api/data/notes/NotesData'; + +interface StateType { + notes: any[]; + notesContent: number; + noteSearch: string; +} + +const initialState = { + notes: [], + notesContent: 1, + noteSearch: '', +}; + +export const NotesSlice = createSlice({ + name: 'notes', + initialState, + reducers: { + getNotes: (state, action) => { + state.notes = action.payload; + }, + SearchNotes: (state, action) => { + state.noteSearch = action.payload; + }, + SelectNote: (state, action) => { + state.notesContent = action.payload; + }, + + DeleteNote(state: StateType, action) { + const index = state.notes.findIndex((note) => note.id === action.payload); + state.notes.splice(index, 1); + }, + + UpdateNote: { + reducer: (state: StateType, action: PayloadAction) => { + state.notes = state.notes.map((note) => + note.id === action.payload.id + ? { ...note, [action.payload.field]: action.payload.value } + : note, + ); + }, + prepare: (id, field, value) => { + return { + payload: { id, field, value }, + }; + }, + }, + + addNote: { + reducer: (state: StateType, action: PayloadAction) => { + state.notes.push(action.payload); + }, + prepare: (id, title, color) => { + return { payload: { id, title, color, datef: new Date().toDateString(), deleted: false } }; + }, + }, + }, +}); + +export const { SearchNotes, getNotes, SelectNote, DeleteNote, UpdateNote, addNote } = + NotesSlice.actions; + +export const fetchNotes = () => async (dispatch: AppDispatch) => { + try { + const response = await axios.get(`${API_URL}`); + dispatch(getNotes(response.data)); + } catch (err: any) { + throw new Error(err); + } +}; + +export default NotesSlice.reducer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/tickets/TicketSlice.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/tickets/TicketSlice.tsx new file mode 100644 index 0000000..3a5c466 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/tickets/TicketSlice.tsx @@ -0,0 +1,50 @@ +import axios from '../../../utils/axios'; +import { createSlice } from '@reduxjs/toolkit'; +import { AppDispatch } from 'src/store/Store'; + +const API_URL = '/api/data/ticket/TicketData'; + +interface StateType { + tickets: any[]; + currentFilter: string; + ticketSearch: string; +} + +const initialState = { + tickets: [], + currentFilter: 'total_tickets', + ticketSearch: '', +}; + +export const TicketSlice = createSlice({ + name: 'ticket', + initialState, + reducers: { + getTickets: (state, action) => { + state.tickets = action.payload; + }, + setVisibilityFilter: (state, action) => { + state.currentFilter = action.payload; + }, + SearchTicket: (state, action) => { + state.ticketSearch = action.payload; + }, + DeleteTicket: (state: StateType, action) => { + const index = state.tickets.findIndex((ticket) => ticket.Id === action.payload); + state.tickets.splice(index, 1); + }, + }, +}); + +export const { getTickets, setVisibilityFilter, SearchTicket, DeleteTicket } = TicketSlice.actions; + +export const fetchTickets = () => async (dispatch: AppDispatch) => { + try { + const response = await axios.get(`${API_URL}`); + dispatch(getTickets(response.data)); + } catch (err: any) { + throw new Error(err); + } +}; + +export default TicketSlice.reducer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/userProfile/UserProfileSlice.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/userProfile/UserProfileSlice.tsx new file mode 100644 index 0000000..7b9386d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/store/apps/userProfile/UserProfileSlice.tsx @@ -0,0 +1,111 @@ +import axios from 'src/utils/axios'; +import { createSlice } from '@reduxjs/toolkit'; +import { map } from 'lodash'; +import { AppDispatch } from 'src/store/Store'; + +const API_URL = '/api/data/postData'; + +interface StateType { + posts: any[]; + followers: any[]; + gallery: any[]; +} + +const initialState = { + posts: [], + followers: [], + gallery: [], +}; + +export const UserProfileSlice = createSlice({ + name: 'UserPost', + initialState, + reducers: { + getPosts: (state, action) => { + state.posts = action.payload; + }, + getFollowers: (state, action) => { + state.followers = action.payload; + }, + getPhotos: (state, action) => { + state.gallery = action.payload; + }, + onToggleFollow(state: StateType, action) { + const followerId = action.payload; + + const handleToggle = map(state.followers, (follower) => { + if (follower.id === followerId) { + return { + ...follower, + isFollowed: !follower.isFollowed, + }; + } + + return follower; + }); + + state.followers = handleToggle; + }, + }, +}); + +export const { getPosts, getFollowers, onToggleFollow, getPhotos } = UserProfileSlice.actions; + +export const fetchPosts = () => async (dispatch: AppDispatch) => { + try { + const response = await axios.get(`${API_URL}`); + dispatch(getPosts(response.data)); + } catch (err: any) { + throw new Error(err); + } +}; +export const likePosts = (postId: number) => async (dispatch: AppDispatch) => { + try { + const response = await axios.post('/api/data/posts/like', { postId }); + dispatch(getPosts(response.data.posts)); + } catch (err: any) { + throw new Error(err); + } +}; +export const addComment = (postId: number, comment: any[]) => async (dispatch: AppDispatch) => { + try { + const response = await axios.post('/api/data/posts/comments/add', { postId, comment }); + dispatch(getPosts(response.data.posts)); + } catch (err: any) { + throw new Error(err); + } +}; + +export const addReply = + (postId: number, commentId: any[], reply: any[]) => async (dispatch: AppDispatch) => { + try { + const response = await axios.post('/api/data/posts/replies/add', { + postId, + commentId, + reply, + }); + dispatch(getPosts(response.data.posts)); + } catch (err: any) { + throw new Error(err); + } + }; + +export const fetchFollwores = () => async (dispatch: AppDispatch) => { + try { + const response = await axios.get(`/api/data/users`); + dispatch(getFollowers(response.data)); + } catch (err: any) { + throw new Error(err); + } +}; + +export const fetchPhotos = () => async (dispatch: AppDispatch) => { + try { + const response = await axios.get(`/api/data/gallery`); + dispatch(getPhotos(response.data)); + } catch (err: any) { + throw new Error(err); + } +}; + +export default UserProfileSlice.reducer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/store/customizer/CustomizerSlice.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/store/customizer/CustomizerSlice.tsx new file mode 100644 index 0000000..248c635 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/store/customizer/CustomizerSlice.tsx @@ -0,0 +1,92 @@ +import { createSlice } from '@reduxjs/toolkit'; + +interface StateType { + activeDir?: string | any; + activeMode?: string; // This can be light or dark + activeTheme?: string; // BLUE_THEME, GREEN_THEME, BLACK_THEME, PURPLE_THEME, ORANGE_THEME + SidebarWidth?: number; + MiniSidebarWidth?: number; + TopbarHeight?: number; + isCollapse?: boolean; + isLayout?: string; + isSidebarHover?: boolean; + isMobileSidebar?: boolean; + isHorizontal?: boolean; + isLanguage?: string; + isCardShadow?: boolean; + borderRadius?: number | any; +} + +const initialState: StateType = { + activeDir: 'ltr', + activeMode: 'light', // This can be light or dark + activeTheme: 'BLUE_THEME', // BLUE_THEME, GREEN_THEME, BLACK_THEME, PURPLE_THEME, ORANGE_THEME + SidebarWidth: 270, + MiniSidebarWidth: 87, + TopbarHeight: 70, + isLayout: 'boxed', // This can be full or boxed + isCollapse: false, // to make sidebar Mini by default + isSidebarHover: false, + isMobileSidebar: false, + isHorizontal: false, + isLanguage: 'en', + isCardShadow: true, + borderRadius: 7, +}; + +export const CustomizerSlice = createSlice({ + name: 'customizer', + initialState, + reducers: { + setTheme: (state: StateType, action) => { + state.activeTheme = action.payload; + }, + setDarkMode: (state: StateType, action) => { + state.activeMode = action.payload; + }, + + setDir: (state: StateType, action) => { + state.activeDir = action.payload; + }, + setLanguage: (state: StateType, action) => { + state.isLanguage = action.payload; + }, + setCardShadow: (state: StateType, action) => { + state.isCardShadow = action.payload; + }, + toggleSidebar: (state) => { + state.isCollapse = !state.isCollapse; + }, + hoverSidebar: (state: StateType, action) => { + state.isSidebarHover = action.payload; + }, + toggleMobileSidebar: (state) => { + state.isMobileSidebar = !state.isMobileSidebar; + }, + toggleLayout: (state: StateType, action) => { + state.isLayout = action.payload; + }, + toggleHorizontal: (state: StateType, action) => { + state.isHorizontal = action.payload; + }, + setBorderRadius: (state: StateType, action) => { + state.borderRadius = action.payload; + }, + }, +}); + +export const { + setTheme, + setDarkMode, + setDir, + toggleSidebar, + hoverSidebar, + toggleMobileSidebar, + toggleLayout, + setBorderRadius, + toggleHorizontal, + setLanguage, + setCardShadow, +} = CustomizerSlice.actions; + +export default CustomizerSlice.reducer; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Components.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Components.tsx new file mode 100644 index 0000000..82dbedf --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Components.tsx @@ -0,0 +1,486 @@ +// project imports +import './DefaultColors'; +import { Theme } from '@mui/material/styles'; + +const components: any = (theme: Theme) => { + return { + MuiCssBaseline: { + styleOverrides: { + '*': { + boxSizing: 'border-box', + }, + html: { + height: '100%', + width: '100%', + }, + a: { + textDecoration: 'none', + }, + body: { + height: '100%', + margin: 0, + padding: 0, + }, + '.ql-container.ql-snow, .ql-toolbar.ql-snow': { + border: '0 !important', borderRadius: '7px' + }, + '.ql-editor, .ql-snow *': { + fontFamiy: 'inherit !important' + }, + '#root': { + height: '100%', + }, + "*[dir='rtl'] .buyNowImg": { + transform: 'scaleX(-1)', + }, + '.border-none': { + border: '0px', + td: { + border: '0px', + }, + }, + 'pre': { + background: `${theme.palette.grey[100]} !important`, + }, + '.btn-xs': { + minWidth: '30px !important', + width: '30px', + height: '30px', + borderRadius: '6px !important', + padding: '0px !important', + }, + '.hover-text-primary:hover .text-hover': { + color: theme.palette.primary.main, + }, + '.hoverCard:hover': { + scale: '1.01', + transition: ' 0.1s ease-in', + }, + '.signup-bg': { + position: 'absolute', + top: 0, + right: 0, + height: '100%', + }, + '.MuiBox-root': { + borderRadius: theme.shape.borderRadius, + }, + '.MuiCardHeader-action': { + alignSelf: 'center !important', + }, + '.emoji-picker-react .emoji-scroll-wrapper': { + overflowX: 'hidden', + }, + '.scrollbar-container': { + borderRight: '0 !important', + }, + '.theme-timeline .MuiTimelineOppositeContent-root': { + minWidth: '90px', + }, + '.MuiAlert-root .MuiAlert-icon': { + color: 'inherit!important', + }, + '.MuiTimelineConnector-root': { + width: '1px !important', + }, + ' .simplebar-scrollbar:before': { + background: `${theme.palette.grey[300]} !important`, + }, + '@keyframes gradient': { + '0%': { + backgroundPosition: '0% 50%', + }, + '50%': { + backgroundPosition: ' 100% 50%', + }, + '100% ': { + backgroundPosition: ' 0% 50%', + }, + }, + '@keyframes slide': { + '0%': { + transform: 'translate3d(0, 0, 0)', + }, + '100% ': { + transform: 'translate3d(-2086px, 0, 0)', + }, + }, + '.rounded-bars .apexcharts-bar-series.apexcharts-plot-series .apexcharts-series path': { + clipPath: 'inset(0 0 5% 0 round 20px)', + }, + }, + }, + MuiButtonGroup: { + styleOverrides: { + root: { + boxShadow: 'none', + }, + }, + }, + MuiAccordion: { + styleOverrides: { + root: { + ':before': { + backgroundColor: theme.palette.grey[100], + }, + }, + }, + }, + MuiPaper: { + styleOverrides: { + root: { + // border: `1px solid ${theme.palette.divider}`, + backgroundImage: 'none', + }, + }, + }, + MuiStepConnector: { + styleOverrides: { + line: { + borderColor: theme.palette.divider, + }, + }, + }, + MuiFab: { + styleOverrides: { + root: { + boxShadow: 'none', + }, + sizeSmall: { + width: 30, + height: 30, + minHeight: 30, + }, + }, + }, + MuiIconButton: { + styleOverrides: { + root: { + '&:hover': { + backgroundColor: theme.palette.primary.light, + color: theme.palette.primary.main, + }, + }, + colorPrimary: { + '&:hover': { + backgroundColor: theme.palette.primary.main, + color: 'white', + }, + }, + colorSecondary: { + '&:hover': { + backgroundColor: theme.palette.secondary.main, + color: 'white', + }, + }, + colorSuccess: { + '&:hover': { + backgroundColor: theme.palette.success.main, + color: 'white', + }, + }, + colorError: { + '&:hover': { + backgroundColor: theme.palette.error.main, + color: 'white', + }, + }, + colorWarning: { + '&:hover': { + backgroundColor: theme.palette.warning.main, + color: 'white', + }, + }, + colorInfo: { + '&:hover': { + backgroundColor: theme.palette.info.main, + color: 'white', + }, + }, + }, + }, + MuiButton: { + styleOverrides: { + root: { + textTransform: 'none', + boxShadow: 'none', + }, + text: { + padding: '5px 15px', + '&:hover': { + backgroundColor: theme.palette.primary.light, + color: theme.palette.primary.main, + }, + }, + textPrimary: { + backgroundColor: theme.palette.primary.light, + '&:hover': { + backgroundColor: theme.palette.primary.main, + color: 'white', + }, + }, + textSecondary: { + backgroundColor: theme.palette.secondary.light, + '&:hover': { + backgroundColor: theme.palette.secondary.main, + color: 'white', + }, + }, + textSuccess: { + backgroundColor: theme.palette.success.light, + '&:hover': { + backgroundColor: theme.palette.success.main, + color: 'white', + }, + }, + textError: { + backgroundColor: theme.palette.error.light, + '&:hover': { + backgroundColor: theme.palette.error.main, + color: 'white', + }, + }, + textInfo: { + backgroundColor: theme.palette.info.light, + '&:hover': { + backgroundColor: theme.palette.info.main, + color: 'white', + }, + }, + textWarning: { + backgroundColor: theme.palette.warning.light, + '&:hover': { + backgroundColor: theme.palette.warning.main, + color: 'white', + }, + }, + outlinedPrimary: { + '&:hover': { + backgroundColor: theme.palette.primary.main, + color: 'white', + }, + }, + outlinedSecondary: { + '&:hover': { + backgroundColor: theme.palette.secondary.main, + color: 'white', + }, + }, + outlinedError: { + '&:hover': { + backgroundColor: theme.palette.error.main, + color: 'white', + }, + }, + outlinedSuccess: { + '&:hover': { + backgroundColor: theme.palette.success.main, + color: 'white', + }, + }, + outlinedInfo: { + '&:hover': { + backgroundColor: theme.palette.info.main, + color: 'white', + }, + }, + outlinedWarning: { + '&:hover': { + backgroundColor: theme.palette.warning.main, + color: 'white', + }, + }, + }, + }, + MuiCardHeader: { + styleOverrides: { + root: { + padding: '16px 24px', + }, + title: { + fontSize: '1.125rem', + }, + }, + }, + MuiCard: { + styleOverrides: { + root: { + width: '100%', + padding: '15px', + backgroundImage: 'none', + }, + }, + }, + MuiCardContent: { + styleOverrides: { + root: { + padding: '24px', + }, + }, + }, + MuiTableCell: { + styleOverrides: { + root: { + borderBottom: `1px solid ${theme.palette.divider}`, + }, + }, + }, + MuiTableRow: { + styleOverrides: { + root: { + '&:last-child td': { + borderBottom: 0, + }, + }, + }, + }, + MuiGridItem: { + styleOverrides: { + root: { + paddingTop: '30px', + paddingLeft: '30px !important', + }, + }, + }, + MuiLinearProgress: { + styleOverrides: { + root: { + backgroundColor: theme.palette.grey[200], + borderRadius: '6px', + }, + }, + }, + MuiTimelineConnector: { + styleOverrides: { + root: { + backgroundColor: theme.palette.divider, + }, + }, + }, + MuiDivider: { + styleOverrides: { + root: { + borderColor: theme.palette.divider, + }, + }, + }, + + MuiChip: { + styleOverrides: { + root: { + fontWeight: 600, + fontSize: '0.75rem', + }, + }, + }, + MuiAlert: { + styleOverrides: { + filledSuccess: { + color: 'white', + }, + filledInfo: { + color: 'white', + }, + filledError: { + color: 'white', + }, + filledWarning: { + color: 'white', + }, + standardSuccess: { + backgroundColor: theme.palette.success.light, + color: theme.palette.success.main, + }, + standardError: { + backgroundColor: theme.palette.error.light, + color: theme.palette.error.main, + }, + standardWarning: { + backgroundColor: theme.palette.warning.light, + color: theme.palette.warning.main, + }, + standardInfo: { + backgroundColor: theme.palette.info.light, + color: theme.palette.info.main, + }, + outlinedSuccess: { + borderColor: theme.palette.success.main, + color: theme.palette.success.main, + }, + outlinedWarning: { + borderColor: theme.palette.warning.main, + color: theme.palette.warning.main, + }, + outlinedError: { + borderColor: theme.palette.error.main, + color: theme.palette.error.main, + }, + outlinedInfo: { + borderColor: theme.palette.info.main, + color: theme.palette.info.main, + }, + successIcon: { + color: theme.palette.info.main, + }, + }, + }, + MuiOutlinedInput: { + styleOverrides: { + root: { + '& .MuiOutlinedInput-notchedOutline': { + borderColor: + theme.palette.mode === 'dark' ? theme.palette.grey[200] : theme.palette.grey[300], + }, + '&:hover .MuiOutlinedInput-notchedOutline': { + borderColor: theme.palette.grey[300], + }, + }, + input: { + padding: '12px 14px', + }, + inputSizeSmall: { + padding: '8px 14px', + }, + }, + }, + MuiAutocomplete: { + styleOverrides: { + root: { + '& .MuiOutlinedInput-root': { + padding: '4px 9px' + } + } + } + }, + MuiTooltip: { + styleOverrides: { + tooltip: { + color: theme.palette.background.paper, + background: theme.palette.text.primary, + }, + }, + }, + MuiDrawer: { + styleOverrides: { + paper: { + borderColor: `${theme.palette.divider}`, + }, + }, + }, + MuiDialogTitle: { + styleOverrides: { + root: { + fontSize: '1.25rem', + }, + }, + }, + MuiPopover: { + styleOverrides: { + paper: { + boxShadow: theme.shadows[9], + }, + }, + }, + }; +}; +export default components; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/theme/DarkThemeColors.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/DarkThemeColors.tsx new file mode 100644 index 0000000..bc7cbc1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/DarkThemeColors.tsx @@ -0,0 +1,111 @@ +const DarkThemeColors = [ + { + name: 'BLUE_THEME', + palette: { + primary: { + main: '#5D87FF', + light: '#253662', + dark: '#4570EA', + contrastText: '#ffffff', + }, + secondary: { + main: '#49BEFF', + light: '#1C455D', + dark: '#23afdb', + contrastText: '#ffffff', + }, + background: { + default: '#2A3447', + dark: '#2A3547', + paper: '#2A3447', + }, + }, + }, + { + name: 'AQUA_THEME', + palette: { + primary: { + main: '#0074BA', + light: '#103247', + dark: '#006DAF', + contrastText: '#ffffff', + }, + secondary: { + main: '#47D7BC', + light: '#0C4339', + dark: '#39C7AD', + contrastText: '#ffffff', + }, + }, + }, + { + name: 'PURPLE_THEME', + palette: { + primary: { + main: '#763EBD', + light: '#26153C', + dark: '#6E35B7', + contrastText: '#ffffff', + }, + secondary: { + main: '#95CFD5', + light: '#09454B', + dark: '#8BC8CE', + contrastText: '#ffffff', + }, + }, + }, + { + name: 'GREEN_THEME', + palette: { + primary: { + main: '#0A7EA4', + light: '#05313F', + dark: '#06769A', + contrastText: '#ffffff', + }, + secondary: { + main: '#CCDA4E', + light: '#282917', + dark: '#C3D046', + contrastText: '#ffffff', + }, + }, + }, + { + name: 'CYAN_THEME', + palette: { + primary: { + main: '#01C0C8', + light: '#003638', + dark: '#00B9C0', + contrastText: '#ffffff', + }, + secondary: { + main: '#FB9678', + light: '#40241C', + dark: '#F48B6C', + contrastText: '#ffffff', + }, + }, + }, + { + name: 'ORANGE_THEME', + palette: { + primary: { + main: '#FA896B', + light: '#402E32', + dark: '#F48162', + contrastText: '#ffffff', + }, + secondary: { + main: '#0074BA', + light: '#082E45', + dark: '#006FB1', + contrastText: '#ffffff', + }, + }, + }, +]; + +export { DarkThemeColors }; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/theme/DefaultColors.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/DefaultColors.tsx new file mode 100644 index 0000000..3cc6650 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/DefaultColors.tsx @@ -0,0 +1,135 @@ +const baselightTheme = { + direction: 'ltr', + palette: { + primary: { + main: '#5D87FF', + light: '#ECF2FF', + dark: '#4570EA', + }, + secondary: { + main: '#49BEFF', + light: '#E8F7FF', + dark: '#23afdb', + }, + success: { + main: '#13DEB9', + light: '#E6FFFA', + dark: '#02b3a9', + contrastText: '#ffffff', + }, + info: { + main: '#539BFF', + light: '#EBF3FE', + dark: '#1682d4', + contrastText: '#ffffff', + }, + error: { + main: '#FA896B', + light: '#FDEDE8', + dark: '#f3704d', + contrastText: '#ffffff', + }, + warning: { + main: '#FFAE1F', + light: '#FEF5E5', + dark: '#ae8e59', + contrastText: '#ffffff', + }, + purple: { + A50: '#EBF3FE', + A100: '#6610f2', + A200: '#557fb9', + }, + grey: { + 100: '#F2F6FA', + 200: '#EAEFF4', + 300: '#DFE5EF', + 400: '#7C8FAC', + 500: '#5A6A85', + 600: '#2A3547', + }, + text: { + primary: '#2A3547', + secondary: '#2A3547', + }, + action: { + disabledBackground: 'rgba(73,82,88,0.12)', + hoverOpacity: 0.02, + hover: '#f6f9fc', + }, + divider: '#e5eaef', + background: { + default: '#ffffff', + }, + }, +}; + +const baseDarkTheme = { + direction: 'ltr', + palette: { + primary: { + main: '#5D87FF', + light: '#ECF2FF', + dark: '#4570EA', + }, + secondary: { + main: '#777e89', + light: '#1C455D', + dark: '#173f98', + }, + success: { + main: '#13DEB9', + light: '#1B3C48', + dark: '#02b3a9', + contrastText: '#ffffff', + }, + info: { + main: '#539BFF', + light: '#223662', + dark: '#1682d4', + contrastText: '#ffffff', + }, + error: { + main: '#FA896B', + light: '#4B313D', + dark: '#f3704d', + contrastText: '#ffffff', + }, + warning: { + main: '#FFAE1F', + light: '#4D3A2A', + dark: '#ae8e59', + contrastText: '#ffffff', + }, + purple: { + A50: '#EBF3FE', + A100: '#6610f2', + A200: '#557fb9', + }, + grey: { + 100: '#333F55', + 200: '#465670', + 300: '#7C8FAC', + 400: '#DFE5EF', + 500: '#EAEFF4', + 600: '#F2F6FA', + }, + text: { + primary: '#EAEFF4', + secondary: '#7C8FAC', + }, + action: { + disabledBackground: 'rgba(73,82,88,0.12)', + hoverOpacity: 0.02, + hover: '#333F55', + }, + divider: '#333F55', + background: { + default: '#171c23', + dark: '#171c23', + paper: '#171c23', + }, + }, +}; + +export { baseDarkTheme, baselightTheme }; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/theme/LightThemeColors.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/LightThemeColors.tsx new file mode 100644 index 0000000..043a107 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/LightThemeColors.tsx @@ -0,0 +1,106 @@ +const LightThemeColors = [ + { + name: 'BLUE_THEME', + palette: { + primary: { + main: '#5D87FF', + light: '#ECF2FF', + dark: '#4570EA', + contrastText: '#ffffff', + }, + secondary: { + main: '#49BEFF', + light: '#E8F7FF', + dark: '#23afdb', + contrastText: '#ffffff', + }, + }, + }, + { + name: 'AQUA_THEME', + palette: { + primary: { + main: '#0074BA', + light: '#EFF9FF', + dark: '#006DAF', + contrastText: '#ffffff', + }, + secondary: { + main: '#47D7BC', + light: '#EDFBF7', + dark: '#39C7AD', + contrastText: '#ffffff', + }, + }, + }, + { + name: 'PURPLE_THEME', + palette: { + primary: { + main: '#763EBD', + light: '#F2ECF9', + dark: '#6E35B7', + contrastText: '#ffffff', + }, + secondary: { + main: '#95CFD5', + light: '#EDF8FA', + dark: '#8BC8CE', + contrastText: '#ffffff', + }, + }, + }, + { + name: 'GREEN_THEME', + palette: { + primary: { + main: '#0A7EA4', + light: '#F4F9FB', + dark: '#06769A', + contrastText: '#ffffff', + }, + secondary: { + main: '#CCDA4E', + light: '#FAFBEF', + dark: '#C3D046', + contrastText: '#ffffff', + }, + }, + }, + { + name: 'CYAN_THEME', + palette: { + primary: { + main: '#01C0C8', + light: '#EBF9FA', + dark: '#00B9C0', + contrastText: '#ffffff', + }, + secondary: { + main: '#FB9678', + light: '#FFF5F2', + dark: '#F48B6C', + contrastText: '#ffffff', + }, + }, + }, + { + name: 'ORANGE_THEME', + palette: { + primary: { + main: '#FA896B', + light: '#FBF2EF', + dark: '#F48162', + contrastText: '#ffffff', + }, + secondary: { + main: '#0074BA', + light: '#EFF9FF', + dark: '#006FB1', + contrastText: '#ffffff', + }, + }, + }, +]; + +export { LightThemeColors }; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Shadows.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Shadows.tsx new file mode 100644 index 0000000..757b792 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Shadows.tsx @@ -0,0 +1,57 @@ +const shadows = [ + 'none', + '0px 2px 3px rgba(0,0,0,0.10)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 2px 2px -2px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 3px 4px -2px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 3px 4px -2px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 4px 6px -2px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 4px 6px -2px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 4px 8px -2px rgba(0,0,0,0.25)', + '0 9px 17.5px rgb(0,0,0,0.05)', + 'rgb(145 158 171 / 30%) 0px 0px 2px 0px, rgb(145 158 171 / 12%) 0px 12px 24px -4px', + '0px 6px 12px rgba(127, 145, 156, 0.12)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 6px 16px -4px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 7px 16px -4px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 8px 18px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 9px 18px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 10px 20px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 11px 20px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 12px 22px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 13px 22px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 14px 24px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 16px 28px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 18px 30px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 20px 32px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 22px 34px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 24px 36px -8px rgba(0,0,0,0.25)', +]; + +const darkshadows = [ + 'none', + '0px 2px 3px rgba(0,0,0,0.10)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 2px 2px -2px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 3px 4px -2px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 3px 4px -2px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 4px 6px -2px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 4px 6px -2px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 4px 8px -2px rgba(0,0,0,0.25)', + '0 9px 17.5px rgb(0,0,0,0.05)', + 'rgb(145 158 171 / 30%) 0px 0px 2px 0px, rgb(145 158 171 / 2%) 0px 12px 24px -4px', + '0px 6px 12px rgba(127, 145, 156, 0.12)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 6px 16px -4px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 7px 16px -4px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 8px 18px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 9px 18px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 10px 20px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 11px 20px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 12px 22px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 13px 22px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 14px 24px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 16px 28px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 18px 30px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 20px 32px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 22px 34px -8px rgba(0,0,0,0.25)', + '0 0 1px 0 rgba(0,0,0,0.31), 0 24px 36px -8px rgba(0,0,0,0.25)', +]; + +export { shadows, darkshadows }; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Theme.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Theme.tsx new file mode 100644 index 0000000..d96bd80 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Theme.tsx @@ -0,0 +1,55 @@ +import _ from 'lodash'; +import { createTheme } from '@mui/material/styles'; +import { useSelector } from 'src/store/Store'; +import { useEffect } from 'react'; +import { AppState } from '../store/Store'; +import components from './Components'; +import typography from './Typography'; +import { shadows, darkshadows } from './Shadows'; +import { DarkThemeColors } from './DarkThemeColors'; +import { LightThemeColors } from './LightThemeColors'; +import { baseDarkTheme, baselightTheme } from './DefaultColors'; +import * as locales from '@mui/material/locale'; + +export const BuildTheme = (config: any = {}) => { + const themeOptions = LightThemeColors.find((theme) => theme.name === config.theme); + const darkthemeOptions = DarkThemeColors.find((theme) => theme.name === config.theme); + const customizer = useSelector((state: AppState) => state.customizer); + const defaultTheme = customizer.activeMode === 'dark' ? baseDarkTheme : baselightTheme; + const defaultShadow = customizer.activeMode === 'dark' ? darkshadows : shadows; + const themeSelect = customizer.activeMode === 'dark' ? darkthemeOptions : themeOptions; + const baseMode = { + palette: { + mode: customizer.activeMode, + }, + shape: { + borderRadius: customizer.borderRadius, + }, + shadows: defaultShadow, + typography: typography, + }; + const theme = createTheme( + _.merge({}, baseMode, defaultTheme, locales, themeSelect, { + direction: config.direction, + }), + ); + theme.components = components(theme); + + return theme; +}; + +const ThemeSettings = () => { + const activDir = useSelector((state: AppState) => state.customizer.activeDir); + const activeTheme = useSelector((state: AppState) => state.customizer.activeTheme); + const theme = BuildTheme({ + direction: activDir, + theme: activeTheme, + }); + useEffect(() => { + document.dir = activDir; + }, [activDir]); + + return theme; +}; + +export { ThemeSettings }; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/theme/ThemeColors.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/ThemeColors.tsx new file mode 100644 index 0000000..7efe077 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/ThemeColors.tsx @@ -0,0 +1,84 @@ +const ThemeColors = [ + { + name: 'BLUE_THEME', + palette: { + primary: { + main: '#0074BA', + light: '#EFF9FF', + dark: '#006DAF', + }, + secondary: { + main: '#47D7BC', + light: '#EDFBF7', + dark: '#39C7AD', + }, + }, + }, + { + name: 'GREEN_THEME', + palette: { + primary: { + main: '#0A7EA4', + light: '#F4F9FB', + dark: '#06769A', + }, + secondary: { + main: '#CCDA4E', + light: '#FAFBEF', + dark: '#C3D046', + }, + background: { + default: '#f8fffc', + dark: '#ffffff', + paper: '#ffffff', + }, + }, + }, + { + name: 'PURPLE_THEME', + palette: { + primary: { + main: '#763EBD', + light: '#F2ECF9', + dark: '#6E35B7', + }, + secondary: { + main: '#95CFD5', + light: '#EDF8FA', + dark: '#8BC8CE', + }, + }, + }, + { + name: 'ORANGE_THEME', + palette: { + primary: { + main: '#FA896B', + light: '#FBF2EF', + dark: '#F48162', + }, + secondary: { + main: '#0074BA', + light: '#EFF9FF', + dark: '#006FB1', + }, + }, + }, + { + name: 'CYAN_THEME', + palette: { + primary: { + main: '#01C0C8', + light: '#EBF9FA', + dark: '#00B9C0', + }, + secondary: { + main: '#FB9678', + light: '#FFF5F2', + dark: '#F48B6C', + }, + }, + }, +]; + +export default ThemeColors; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Typography.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Typography.tsx new file mode 100644 index 0000000..09268dc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/theme/Typography.tsx @@ -0,0 +1,58 @@ +const typography: any = { + fontFamily: "'Plus Jakarta Sans', sans-serif;", + h1: { + fontWeight: 600, + fontSize: '2.25rem', + lineHeight: '2.75rem', + }, + h2: { + fontWeight: 600, + fontSize: '1.875rem', + lineHeight: '2.25rem', + }, + h3: { + fontWeight: 600, + fontSize: '1.5rem', + lineHeight: '1.75rem', + }, + h4: { + fontWeight: 600, + fontSize: '1.3125rem', + lineHeight: '1.6rem', + }, + h5: { + fontWeight: 600, + fontSize: '1.125rem', + lineHeight: '1.6rem', + }, + h6: { + fontWeight: 600, + fontSize: '1rem', + lineHeight: '1.2rem', + }, + button: { + textTransform: 'capitalize', + fontWeight: 400, + }, + body1: { + fontSize: '0.875rem', + fontWeight: 400, + lineHeight: '1.334rem', + }, + body2: { + fontSize: '0.75rem', + letterSpacing: '0rem', + fontWeight: 400, + lineHeight: '1rem', + }, + subtitle1: { + fontSize: '0.875rem', + fontWeight: 400, + }, + subtitle2: { + fontSize: '0.875rem', + fontWeight: 400, + }, +}; + +export default typography; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/blog.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/blog.ts new file mode 100644 index 0000000..ce68c5e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/blog.ts @@ -0,0 +1,28 @@ +export type Profile = { + id?: string | number; + avatar?: string; + name?: string; + time?: string; +}; + +export interface BlogType { + id?: string; + profile?: Profile; + time?: Date; + comment?: string; + replies?: any[]; +} + +export interface BlogPostType { + id?: number; + title?: any; + content?: string; + coverImg?: string; + createdAt?: Date; + view?: number; + share?: number; + category?: string; + featured?: boolean; + author?: Profile; + comments?: any[]; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/chat.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/chat.ts new file mode 100644 index 0000000..9bf1219 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/chat.ts @@ -0,0 +1,25 @@ +type attachType = { + icon?: string; + file?: string; + fileSize?: string; +}; + +type MessageType = { + createdAt?: any; + msg: string; + senderId: number | string; + type: string; + attachment: attachType[]; + id: string; +}; + +export interface ChatsType { + id: number | string; + name: string; + status: string; + thumb: string; + recent: boolean; + excerpt: string; + chatHistory?: any[]; + messages: MessageType[]; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/contact.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/contact.ts new file mode 100644 index 0000000..5a9f44a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/contact.ts @@ -0,0 +1,15 @@ +export interface ContactType { + id: number | string; + firstname: string; + lastname: string; + image: string; + department: string; + company: string; + phone: string; + email: string; + address: string; + notes: string; + frequentlycontacted: boolean; + starred: boolean; + deleted: boolean; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/eCommerce.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/eCommerce.ts new file mode 100644 index 0000000..4f3b03f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/eCommerce.ts @@ -0,0 +1,36 @@ +import { GeneralIcon } from './icon'; + +export interface ProductType { + title: string; + price: number; + discount: number; + related: boolean; + salesPrice: number; + category: string[]; + gender: string; + rating: number; + stock: boolean; + qty: number; + colors: string[]; + photo: string; + id: number | string; + created: Date; + description: string; +} + +export interface ProductFiterType { + id: number; + filterbyTitle?: string; + name?: string; + sort?: string; + icon?: GeneralIcon | any; + devider?: boolean; +} + +export interface ProductCardProps { + id?: string | number; + color?: string; + like: string; + star: number; + value?: string; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/email.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/email.ts new file mode 100644 index 0000000..189a5c2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/email.ts @@ -0,0 +1,28 @@ +type AttachType = { + id: string; + image: string; + title: string; + fileSize: string; +}; + +export interface EmailType { + id: number; + from: string; + thumbnail: string; + subject: string; + time: any; + To: string; + emailExcerpt: string; + emailContent: string; + unread: boolean; + attachment: boolean; + starred: boolean; + important: boolean; + inbox: boolean; + sent: boolean; + draft: boolean; + spam: boolean; + trash: boolean; + label: string; + attchments?: AttachType[]; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/icon.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/icon.ts new file mode 100644 index 0000000..e02c512 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/icon.ts @@ -0,0 +1,14 @@ +import React, { FunctionComponent } from 'react'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import { TablerIcon } from '@tabler/icons-react'; +import { OverridableComponent } from '@mui/material/OverridableComponent'; +import { SvgIconTypeMap } from '@mui/material'; + +export type GeneralIcon = + | (OverridableComponent> & { + muiName: string; + }) + | React.ComponentClass + | FunctionComponent + | TablerIcon; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/invoice.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/invoice.ts new file mode 100644 index 0000000..a973bb7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/invoice.ts @@ -0,0 +1,30 @@ +export interface order { + itemName: string ; + unitPrice: number ; + units: number; + unitTotalPrice: number; + } + + export interface InvoiceList { + + id: number; + billFrom: string ; + billFromEmail: string; + billFromAddress: string; + billFromPhone: number; + billFromFax: number ; + billTo: string; + billToEmail: string; + billToAddress: string; + billToPhone: number ; + billToFax: number; + orders: order[] ; + orderDate: Date ; + totalCost: number; + vat: number; + grandTotal: number; + status: string ; + completed: boolean ; + isSelected: boolean ; + + } \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/kanban.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/kanban.ts new file mode 100644 index 0000000..8869fe8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/kanban.ts @@ -0,0 +1,15 @@ +export interface TodoTask { + id: number | any; + task: string; + taskImage: string | null | any; + taskText: string; + date: string; + taskProperty: string; + category?: string | any; +} + +export interface TodoCategory { + id: string | any; + name: string; + child: TodoTask[]; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/notes.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/notes.ts new file mode 100644 index 0000000..f494e40 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/notes.ts @@ -0,0 +1,7 @@ +export interface NotesType { + id: number; + color?: string; + title?: string; + datef?: any | string; + deleted: boolean; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/ticket.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/ticket.ts new file mode 100644 index 0000000..8ae6773 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/ticket.ts @@ -0,0 +1,11 @@ +export interface TicketType { + Id: number; + ticketTitle: string; + ticketDescription: string; + Status: string; + Label: string; + thumb: string; + AgentName: string; + Date: Date; + deleted: boolean; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/userProfile.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/userProfile.ts new file mode 100644 index 0000000..670f8fb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/userProfile.ts @@ -0,0 +1,52 @@ +export type ProfileType = { + id: number | string; + avatar: string; + name: string; + time: string; +}; + +export type Likes = { + like: boolean; + value: number; +}; + +export type PostImageType = { + img: string; + featured?: boolean; + title?: string; +}; + +export type CommentDataType = { + name?: string; + comment?: string; + likes?: Likes; + video?: string; + replies?: Reply[]; +}; + +export type Reply = { + id?: string | number; + profile?: ProfileType; + data: CommentDataType; +}; + +export type Comment = { + id: string | number; + profile: ProfileType; + data?: CommentDataType; +}; + +export type PostDataType = { + id?: string | number; + content: string; + images: PostImageType[]; + video?: string; + likes: Likes; + comments?: Comment[]; +}; + +export type PostType = { + id?: any; + profile: ProfileType; + data: PostDataType; +}; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/users.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/users.ts new file mode 100644 index 0000000..62ea420 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/apps/users.ts @@ -0,0 +1,15 @@ +export interface userType { + id: string; + avatar: string; + name: string; + role: string; + country: string; + isFollowed: boolean; +} + +export interface GallaryType { + id: string; + cover: string; + name: string; + time: string; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/auth/auth.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/auth/auth.ts new file mode 100644 index 0000000..039ca1e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/auth/auth.ts @@ -0,0 +1,15 @@ +export interface registerType { + title?: string; + subtitle?: any | any[]; + subtext?: any | any[]; +} + +export interface loginType { + title?: string; + subtitle?: any | any[]; + subtext?: any | any[]; +} + +export interface signInType { + title?: string; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/types/layout/sidebar.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/types/layout/sidebar.ts new file mode 100644 index 0000000..f3b2fa5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/types/layout/sidebar.ts @@ -0,0 +1,21 @@ +export interface navItemProps { + item: { + icon: string; + href?: string; + disabled?: boolean; + title?: string; + subtitle?: string; + chip?: string; + chipColor?: string; + variant?: string; + external?: boolean; + id: number; + }; +} + +export interface listItemType { + component: any; + href?: string; + target?: any; + to?: any; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/utils/axios.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/axios.ts new file mode 100644 index 0000000..523d1b7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/axios.ts @@ -0,0 +1,12 @@ + import axios from 'axios'; + + const axiosServices = axios.create(); + + // interceptor for http + axiosServices.interceptors.response.use( + (response) => response, + (error) => Promise.reject((error.response && error.response.data) || 'Wrong Services') + ); + + export default axiosServices; + \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/utils/i18n.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/i18n.ts new file mode 100644 index 0000000..eab04d0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/i18n.ts @@ -0,0 +1,33 @@ +import i18n from 'i18next'; +import { initReactI18next } from 'react-i18next'; +import english from 'src/utils/languages/en.json'; +import french from 'src/utils/languages/fr.json'; +import arabic from 'src/utils/languages/ar.json'; +import chinese from 'src/utils/languages/ch.json'; + +const resources = { + en: { + translation: english, + }, + fr: { + translation: french, + }, + ar: { + translation: arabic, + }, + ch: { + translation: chinese, + }, +}; + +i18n + .use(initReactI18next) // passes i18n down to react-i18next + .init({ + resources, + lng: 'en', + interpolation: { + escapeValue: false, // react already safes from xss + }, + }); + +export default i18n; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/ar.json b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/ar.json new file mode 100644 index 0000000..2277141 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/ar.json @@ -0,0 +1,22 @@ +{ + "Modern": "عصري", + "Ecommerce": "التجارة الإلكترونية", + "eCommerce": "التجارة الإلكترونية", + "Contacts": "جهات الاتصال", + "Blog": "مقالات", + "Posts": "المشاركات", + "Detail": "التفاصيل", + "Shop": "متجر", + "List": "قائمة", + "Checkout": "الدفع", + "Chats": "الدردشات", + "Users": "المستخدمون", + "Profile": "الملف الشخصي", + "Followers": "متابعون", + "Friends": "أصدقاء", + "Gallery": "صالة عرض", + "Notes": "ملاحظات", + "Calendar": "التقويم", + "Email": "بريد إلكتروني", + "Tickets": "تذاكر" +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/ch.json b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/ch.json new file mode 100644 index 0000000..ea86e0d --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/ch.json @@ -0,0 +1,22 @@ +{ + "Modern": "現代的", + "Ecommerce": "电子商务", + "eCommerce": "电子商务", + "Contacts": "聯繫人", + "Blog": "博客", + "Posts": "帖子", + "Detail": "细节", + "Shop": "店铺", + "List": "列表", + "Checkout": "查看", + "Chats": "聊天記錄", + "Users": "用户", + "Profile": "轮廓", + "Followers": "追随者", + "Friends": "朋友们", + "Gallery": "画廊", + "Notes": "笔记", + "Calendar": "日历", + "Email": "电子邮件", + "Tickets": "门票" +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/en.json b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/en.json new file mode 100644 index 0000000..6a9d43a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/en.json @@ -0,0 +1,22 @@ +{ + "Modern": "Modern", + "Ecommerce": "Ecommerce", + "eCommerce": "eCommerce", + "Contacts": "Contacts", + "Blog": "Blog", + "Posts": "Posts", + "Detail": "Detail", + "Shop": "Shop", + "List": "List", + "Checkout": "Checkout", + "Chats": "Chats", + "Users": "Users", + "Profile": "Profile", + "Followers": "Followers", + "Friends": "Friends", + "Gallery": "Gallery", + "Notes": "Notes", + "Calendar": "Calendar", + "Email": "Email", + "Tickets": "Tickets" +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/fr.json b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/fr.json new file mode 100644 index 0000000..91b8b6a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/utils/languages/fr.json @@ -0,0 +1,22 @@ +{ + "Modern": "Moderne", + "Ecommerce": "commerce électronique", + "eCommerce": "commerce électronique", + "Contacts": "Les contacts", + "Blog": "Blog", + "Posts": "des postes", + "Detail": "détail", + "Shop": "magasin", + "List": "liste", + "Checkout": "vérifier", + "Chats": "Chattes", + "Users": "Utilisatrices", + "Profile": "profil", + "Followers": "suiveuses", + "Friends": "copines", + "Gallery": "Galerie", + "Notes": "Remarques", + "Calendar": "Calendrier", + "Email": "E-mail", + "Tickets": "Des billets" +} \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/blog/Blog.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/blog/Blog.tsx new file mode 100644 index 0000000..7bc1983 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/blog/Blog.tsx @@ -0,0 +1,20 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import BlogListing from 'src/components/apps/blog/BlogListing'; + +const Blog = () => { + return ( + + + {/* ------------------------------------------- */} + {/* Blog Listing */} + {/* ------------------------------------------- */} + + + ); +}; + +export default Blog; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/blog/BlogPost.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/blog/BlogPost.tsx new file mode 100644 index 0000000..61f7718 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/blog/BlogPost.tsx @@ -0,0 +1,18 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import BlogDetail from 'src/components/apps/blog/detail/BlogDetail'; +import PageContainer from 'src/components/container/PageContainer'; + +const BlogPost = () => { + return ( + + {/* ------------------------------------------- */} + {/* Blog Listing */} + {/* ------------------------------------------- */} + + + ); +}; + +export default BlogPost; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/calendar/BigCalendar.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/calendar/BigCalendar.tsx new file mode 100644 index 0000000..404a910 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/calendar/BigCalendar.tsx @@ -0,0 +1,319 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + CardContent, + Button, + Dialog, + DialogActions, + DialogContent, + Fab, + TextField, + Typography, +} from '@mui/material'; +import { Calendar, momentLocalizer } from 'react-big-calendar'; +import { DatePicker } from '@mui/x-date-pickers/DatePicker'; +import { LocalizationProvider } from '@mui/x-date-pickers/LocalizationProvider'; +import moment from 'moment'; +import Events from './EventData'; +import 'react-big-calendar/lib/css/react-big-calendar.css'; +import dayjs from 'dayjs'; +import './Calendar.css'; +import PageContainer from 'src/components/container/PageContainer'; +import { AdapterDayjs } from '@mui/x-date-pickers/AdapterDayjs'; +import { IconCheck } from '@tabler/icons-react'; +import BlankCard from 'src/components/shared/BlankCard'; + +moment.locale('en-GB'); +const localizer = momentLocalizer(moment); + +type EvType = { + title: string; + allDay?: boolean; + start?: Date; + end?: Date; + color?: string; +}; + +const BigCalendar = () => { + const [calevents, setCalEvents] = React.useState(Events); + const [open, setOpen] = React.useState(false); + const [title, setTitle] = React.useState(""); + const [slot, setSlot] = React.useState(); + const [start, setStart] = React.useState(dayjs()); + const [end, setEnd] = React.useState(dayjs()); + const [color, setColor] = React.useState("default"); + const [update, setUpdate] = React.useState(); + // Example function to set and format the date + + const ColorVariation = [ + { + id: 1, + eColor: "#1a97f5", + value: "default", + }, + { + id: 2, + eColor: "#39b69a", + value: "green", + }, + { + id: 3, + eColor: "#fc4b6c", + value: "red", + }, + { + id: 4, + eColor: "#615dff", + value: "azure", + }, + { + id: 5, + eColor: "#fdd43f", + value: "warning", + }, + ]; + const addNewEventAlert = (slotInfo: EvType) => { + setOpen(true); + setSlot(slotInfo); + setStart(dayjs(slotInfo.start)); + setEnd(dayjs(slotInfo.end)); + }; + + + const editEvent = (event: any) => { + const newEditEvent = calevents.find( + (elem: any) => elem.title === event.title + ); + + setTitle(newEditEvent.title); + setColor(newEditEvent.color); + setStart(dayjs(newEditEvent.start)); + setEnd(dayjs(newEditEvent.end)); + setUpdate(event); + setOpen(true); + }; + + const updateEvent = (e: any) => { + e.preventDefault(); + setCalEvents( + calevents.map((elem: EvType) => { + if (elem.title === update.title) { + return { ...elem, title, start: start?.toISOString(), end: end?.toISOString(), color }; + } + return elem; + }) + ); + setOpen(false); + setTitle(""); + setStart(dayjs()); + setEnd(dayjs()); + setUpdate(null); + }; + const inputChangeHandler = (e: React.ChangeEvent) => + setTitle(e.target.value); + const selectinputChangeHandler = (id: string) => setColor(id); + + // When submitting or updating the event + const submitHandler = (e: React.ChangeEvent) => { + e.preventDefault(); + const newEvents = [...calevents]; + newEvents.push({ + title, + start: start ? start.toISOString() : "", + end: end ? end.toISOString() : "", + color, + }); + setCalEvents(newEvents); + setOpen(false); + setTitle(""); + setStart(dayjs()); + setEnd(dayjs()); + }; + + const deleteHandler = (event: EvType) => { + const updatecalEvents = calevents.filter( + (ind: EvType) => ind.title !== event.title + ); + setCalEvents(updatecalEvents); + }; + + const handleClose = () => { + // eslint-disable-line newline-before-return + setOpen(false); + setTitle(""); + setStart(dayjs()); + setEnd(dayjs()); + setUpdate(null); + }; + + const eventColors = (event: EvType) => { + if (event.color) { + return { className: `event-${event.color}` }; + } + + return { className: `event-default` }; + }; + + const handleStartChange = (newValue: any) => { + if (newValue instanceof Date) { + // Convert the native Date object to a dayjs object + setStart(dayjs(newValue)); + } else { + setStart(newValue); + } + }; + + const handleEndChange = (newValue: any) => { + if (newValue instanceof Date) { + // Convert the native Date object to a dayjs object + setEnd(dayjs(newValue)); + } else { + setEnd(newValue); + } + }; + + return ( + + + {/* ------------------------------------------- */} + {/* Calendar */} + {/* ------------------------------------------- */} + + editEvent(event)} + onSelectSlot={(slotInfo: any) => addNewEventAlert(slotInfo)} + eventPropGetter={(event: any) => eventColors(event)} + /> + + + + {/* ------------------------------------------- */} + {/* Add Calendar Event Dialog */} + {/* ------------------------------------------- */} + +
+ + {/* ------------------------------------------- */} + {/* Add Edit title */} + {/* ------------------------------------------- */} + + {update ? "Update Event" : "Add Event"} + + + {!update + ? "To add Event kindly fillup the title and choose the event color and press the add button" + : "To Edit/Update Event kindly change the title and choose the event color and press the update button"} + {slot?.title} + + + + {/* ------------------------------------------- */} + {/* Selection of Start and end date */} + {/* ------------------------------------------- */} + + + + + end, + helperText: start && end && start > end ? "End date must be later than start date" : "", + }, + }} + /> + + + + {/* ------------------------------------------- */} + {/* Calendar Event Color*/} + {/* ------------------------------------------- */} + + Select Event Color + + {/* ------------------------------------------- */} + {/* colors for event */} + {/* ------------------------------------------- */} + {ColorVariation.map((mcolor) => { + return ( + selectinputChangeHandler(mcolor.value)} + > + {mcolor.value === color ? : ""} + + ); + })} + + {/* ------------------------------------------- */} + {/* Action for dialog */} + {/* ------------------------------------------- */} + + + + {update ? ( + + ) : ( + "" + )} + + + {/* ------------------------------------------- */} + {/* End Calendar */} + {/* ------------------------------------------- */} +
+
+
+ ); +}; + +export default BigCalendar; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/calendar/Calendar.css b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/calendar/Calendar.css new file mode 100644 index 0000000..eced1b6 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/calendar/Calendar.css @@ -0,0 +1,92 @@ +.rbc-event.event-azure { + background-color: #1a97f5; +} + +.rbc-event.event-default { + background-color: #615dff; +} +.rbc-event.event-red { + background-color: #fc4b6c; +} +.rbc-event.event-green { + background-color: #39b69a; +} +.rbc-event.event-warning { + background-color: #fdd43f; +} +.rbc-off-range-bg { + background-color: #d2d2d20d; +} +.darkbg .rbc-today { + background-color: #8fbece; +} +.rbc-month-row + .rbc-month-row, +.rbc-day-bg + .rbc-day-bg, +.rbc-header, +.rbc-month-view, +.rbc-toolbar button, +.rbc-time-content > * + * > * { + border-color: #f6f6f6; +} +.darkbg .rbc-month-row + .rbc-month-row, +.darkbg .rbc-day-bg + .rbc-day-bg, +.darkbg .rbc-header, +.darkbg .rbc-month-view, +.darkbg .rbc-toolbar button, +.darkbg .rbc-time-content > * + * > * { + border-color: #343e54; +} +.rbc-event:focus, +.rbc-day-slot .rbc-background-event:focus { + outline: none; +} +.darkbg .rbc-toolbar button { + color: rgba(255, 255, 255, 0.5); +} +.darkbg .rbc-toolbar button:active, +.darkbg .rbc-toolbar button.rbc-active { + background-color: rgba(0, 0, 0, 0.5); + border-color: #d2d2d20d; +} +.form-control { + height: 50px; + line-height: 40px; + font-size: 18px; + width: 100%; + border-width: 1px; + padding: 5px; + border-color: rgba(0, 0, 0, 0.2); + border-radius: 5px; +} +.btn { + padding: 10px 15px; + box-shadow: none !important; + border-radius: 5px; + text-decoration: none; + color: white; +} +.btn-primary { + background-color: #2b2b2b; +} +.btn-secondary { + background-color: #1a97f5; +} + +@media (max-width: 767px) { + .rbc-btn-group { + width: 100%; + text-align: center; + margin-bottom: 15px; + } + .rbc-toolbar .rbc-toolbar-label { + margin-bottom: 15px; + display: block; + } + .rbc-calendar { + height: 100vh !important; + } +} + +.rbc-calendar { + min-height: 600px; +} diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/calendar/EventData.ts b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/calendar/EventData.ts new file mode 100644 index 0000000..3e1e8ba --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/calendar/EventData.ts @@ -0,0 +1,64 @@ +const today = new Date(); +const y = today.getFullYear(); +const m = today.getMonth(); +const d = today.getDate(); + +export interface EventType { + title?: string; + allDay?: boolean; + start?: Date; + end?: Date; + color?: string; +} + +const Events: EventType[] = [ + { + title: 'Twice event For two Days', + allDay: true, + start: new Date(y, m, 3), + end: new Date(y, m, 5), + color: 'default', + }, + { + title: 'Learn ReactJs', + start: new Date(y, m, d + 3, 10, 30), + end: new Date(y, m, d + 3, 11, 30), + allDay: false, + color: 'green', + }, + { + title: 'Launching MaterialArt Angular', + start: new Date(y, m, d + 7, 12, 0), + end: new Date(y, m, d + 7, 14, 0), + allDay: false, + color: 'red', + }, + { + title: 'Lunch with Mr.Raw', + start: new Date(y, m, d - 2), + end: new Date(y, m, d - 2), + allDay: true, + color: 'azure', + }, + { + title: 'Going For Party of Sahs', + start: new Date(y, m, d + 1, 19, 0), + end: new Date(y, m, d + 1, 22, 30), + allDay: false, + color: 'azure', + }, + { + title: 'Learn Ionic', + start: new Date(y, m, 23), + end: new Date(y, m, 25), + color: 'warning', + }, + { + title: 'Research of making own Browser', + start: new Date(y, m, 19), + end: new Date(y, m, 22), + color: 'default', + }, +]; + +export default Events; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/chat/Chat.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/chat/Chat.tsx new file mode 100644 index 0000000..e7f6b00 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/chat/Chat.tsx @@ -0,0 +1,41 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { Divider, Box } from '@mui/material'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ChatSidebar from 'src/components/apps/chats/ChatSidebar'; +import ChatContent from 'src/components/apps/chats/ChatContent'; +import ChatMsgSent from 'src/components/apps/chats/ChatMsgSent'; +import AppCard from 'src/components/shared/AppCard'; + +const Chats = () => { + const [isMobileSidebarOpen, setMobileSidebarOpen] = useState(false); + + return ( + + + + {/* ------------------------------------------- */} + {/* Left part */} + {/* ------------------------------------------- */} + + setMobileSidebarOpen(false)} + /> + {/* ------------------------------------------- */} + {/* Right part */} + {/* ------------------------------------------- */} + + + setMobileSidebarOpen(true)} /> + + + + + + ); +}; + +export default Chats; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/contacts/Contacts.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/contacts/Contacts.tsx new file mode 100644 index 0000000..00a3570 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/contacts/Contacts.tsx @@ -0,0 +1,93 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { Button, Box, Drawer, useMediaQuery, Theme } from '@mui/material'; +import PageContainer from 'src/components/container/PageContainer'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import ContactDetails from 'src/components/apps/contacts/ContactDetails'; +import ContactList from 'src/components/apps/contacts/ContactList'; +import ContactSearch from 'src/components/apps/contacts/ContactSearch'; +import ContactFilter from 'src/components/apps/contacts/ContactFilter'; +import AppCard from 'src/components/shared/AppCard'; + +const drawerWidth = 240; +const secdrawerWidth = 320; + +const Contacts = () => { + const [isLeftSidebarOpen, setLeftSidebarOpen] = useState(false); + const [isRightSidebarOpen, setRightSidebarOpen] = useState(false); + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + const mdUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('md')); + + return ( + + + + {/* ------------------------------------------- */} + {/* Left Part */} + {/* ------------------------------------------- */} + + setLeftSidebarOpen(false)} + sx={{ + width: drawerWidth, + [`& .MuiDrawer-paper`]: { width: drawerWidth, position: 'relative', zIndex: 2 }, + flexShrink: 0, + }} + variant={lgUp ? 'permanent' : 'temporary'} + > + + + {/* ------------------------------------------- */} + {/* Middle part */} + {/* ------------------------------------------- */} + + setLeftSidebarOpen(true)} /> + setRightSidebarOpen(true)} /> + + {/* ------------------------------------------- */} + {/* Right part */} + {/* ------------------------------------------- */} + setRightSidebarOpen(false)} + variant={mdUp ? 'permanent' : 'temporary'} + sx={{ + width: mdUp ? secdrawerWidth : '100%', + zIndex: lgUp ? 0 : 1, + flex: mdUp ? 'auto' : '', + [`& .MuiDrawer-paper`]: { width: '100%', position: 'relative' }, + }} + > + {/* back btn Part */} + {mdUp ? ( + '' + ) : ( + + + + )} + + + + + ); +}; + +export default Contacts; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcomProductList.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcomProductList.tsx new file mode 100644 index 0000000..acdb6a0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcomProductList.tsx @@ -0,0 +1,34 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ProductTableList from 'src/components/apps/ecommerce/ProductTableList/ProductTableList'; +import BlankCard from 'src/components/shared/BlankCard'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Shop', + }, +]; + +const EcomProductList = () => { + return ( + + {/* breadcrumb */} + + + {/* ------------------------------------------- */} + {/* Left part */} + {/* ------------------------------------------- */} + + + + ); +}; + +export default EcomProductList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/Ecommerce.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/Ecommerce.tsx new file mode 100644 index 0000000..2e69810 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/Ecommerce.tsx @@ -0,0 +1,46 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box } from '@mui/material'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ProductList from 'src/components/apps/ecommerce/productGrid/ProductList'; +import ProductSidebar from 'src/components/apps/ecommerce/productGrid/ProductSidebar'; +import AppCard from 'src/components/shared/AppCard'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Shop', + }, +]; +const Ecommerce = () => { + const [isMobileSidebarOpen, setMobileSidebarOpen] = React.useState(false); + + return ( + + {/* breadcrumb */} + + + {/* ------------------------------------------- */} + {/* Left part */} + {/* ------------------------------------------- */} + setMobileSidebarOpen(false)} + /> + {/* ------------------------------------------- */} + {/* Right part */} + {/* ------------------------------------------- */} + + setMobileSidebarOpen(!isMobileSidebarOpen)} /> + + + + ); +}; + +export default Ecommerce; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceAddProduct.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceAddProduct.tsx new file mode 100644 index 0000000..b356ebd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceAddProduct.tsx @@ -0,0 +1,92 @@ +import { Button, Grid2 as Grid, Stack } from '@mui/material'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; + +import GeneralCard from 'src/components/apps/ecommerce/productAdd/GeneralCard'; +import MediaCard from 'src/components/apps/ecommerce/productAdd/Media'; +import VariationCard from 'src/components/apps/ecommerce/productAdd/VariationCard'; +import PricingCard from 'src/components/apps/ecommerce/productAdd/Pricing'; +import Thumbnail from 'src/components/apps/ecommerce/productAdd/Thumbnail'; +import StatusCard from 'src/components/apps/ecommerce/productAdd/Status'; +import ProductDetails from 'src/components/apps/ecommerce/productAdd/ProductDetails'; +import ProductTemplate from 'src/components/apps/ecommerce/productAdd/ProductTemplate'; +import BlankCard from 'src/components/shared/BlankCard'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Add Product', + }, +]; + +const EcommerceAddProduct = () => { + return ( + ( + {/* breadcrumb */} + +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+
) + ); +}; + +export default EcommerceAddProduct; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceCheckout.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceCheckout.tsx new file mode 100644 index 0000000..aab4c3c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceCheckout.tsx @@ -0,0 +1,37 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box } from '@mui/material'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ProductChecout from 'src/components/apps/ecommerce/productCheckout/ProductCheckout'; +import ChildCard from 'src/components/shared/ChildCard'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Checkout', + }, +]; + +const EcommerceCheckout = () => { + return ( + + {/* breadcrumb */} + + + {/* ------------------------------------------- */} + {/* Right part */} + {/* ------------------------------------------- */} + + + + + + ); +}; + +export default EcommerceCheckout; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceDetail.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceDetail.tsx new file mode 100644 index 0000000..ebca511 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceDetail.tsx @@ -0,0 +1,84 @@ +import Grid from '@mui/material/Grid2'; +import ProductCarousel from 'src/components/apps/ecommerce/productDetail/ProductCarousel'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ProductDetail from 'src/components/apps/ecommerce/productDetail/ProductDetail'; +import ProductDesc from 'src/components/apps/ecommerce/productDetail/ProductDesc'; +import ProductRelated from 'src/components/apps/ecommerce/productDetail/ProductRelated'; +import ChildCard from 'src/components/shared/ChildCard'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Shop', + to: '/apps/ecommerce', + }, + { + title: 'detail', + }, +]; + +const EcommerceDetail = () => { + return ( + ( + {/* breadcrumb */} + + + + + {/* ------------------------------------------- */} + {/* Carousel */} + {/* ------------------------------------------- */} + + + + + + + + + + + + + + + + + + ) + ); +}; + +export default EcommerceDetail; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceEditProduct.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceEditProduct.tsx new file mode 100644 index 0000000..e438764 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/eCommerce/EcommerceEditProduct.tsx @@ -0,0 +1,102 @@ +import { Button, Grid2 as Grid, Stack } from '@mui/material'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; + +import GeneralCard from 'src/components/apps/ecommerce/productEdit/GeneralCard'; +import MediaCard from 'src/components/apps/ecommerce/productEdit/Media'; +import VariationCard from 'src/components/apps/ecommerce/productEdit/VariationCard'; +import PricingCard from 'src/components/apps/ecommerce/productEdit/Pricing'; +import Thumbnail from 'src/components/apps/ecommerce/productEdit/Thumbnail'; +import StatusCard from 'src/components/apps/ecommerce/productEdit/Status'; +import ProductDetails from 'src/components/apps/ecommerce/productEdit/ProductDetails'; +import ProductTemplate from 'src/components/apps/ecommerce/productEdit/ProductTemplate'; +import CustomersReviews from 'src/components/apps/ecommerce/productEdit/CustomersReviews'; +import ProductAvgSales from 'src/components/apps/ecommerce/productEdit/ProductAvgSales'; +import BlankCard from 'src/components/shared/BlankCard'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Edit Product', + }, +]; + +const EcommerceEditProduct = () => { + return ( + ( + {/* breadcrumb */} + +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+
) + ); +}; + +export default EcommerceEditProduct; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/email/Email.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/email/Email.tsx new file mode 100644 index 0000000..85b1f29 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/email/Email.tsx @@ -0,0 +1,114 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { Button, Box, Drawer, useMediaQuery, Theme } from '@mui/material'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import EmailLists from 'src/components/apps/email/EmailList'; +import EmailFilter from 'src/components/apps/email/EmailFilter'; +import EmailSearch from 'src/components/apps/email/EmailSearch'; +import EmailContent from 'src/components/apps/email/EmailContent'; +import PageContainer from 'src/components/container/PageContainer'; +import AppCard from 'src/components/shared/AppCard'; +import emailIcon from 'src/assets/images/breadcrumb/emailSv.png'; + +const drawerWidth = 240; +const secdrawerWidth = 340; + +const Email = () => { + const [isLeftSidebarOpen, setLeftSidebarOpen] = useState(false); + const [isRightSidebarOpen, setRightSidebarOpen] = useState(false); + const lgUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('lg')); + const mdUp = useMediaQuery((theme: Theme) => theme.breakpoints.up('md')); + + return ( + + + {emailIcon} + + + + {/* ------------------------------------------- */} + {/* Left part */} + {/* ------------------------------------------- */} + + setLeftSidebarOpen(false)} + sx={{ + width: drawerWidth, + [`& .MuiDrawer-paper`]: { width: drawerWidth, position: 'relative', zIndex: 2 }, + flexShrink: 0, + }} + variant={lgUp ? 'permanent' : 'temporary'} + > + + + + {/* ------------------------------------------- */} + {/* Middle part */} + {/* ------------------------------------------- */} + + + setLeftSidebarOpen(true)} /> + + setRightSidebarOpen(true)} /> + + + {/* ------------------------------------------- */} + {/* Right part */} + {/* ------------------------------------------- */} + + {mdUp ? ( + + + + + + ) : ( + setRightSidebarOpen(false)} + sx={{ + width: drawerWidth, + flexShrink: 0, + [`& .MuiDrawer-paper`]: { width: '85%' }, + }} + variant="temporary" + > + + + + + + )} + + + ); +}; + +export default Email; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/Create.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/Create.tsx new file mode 100644 index 0000000..5ed633a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/Create.tsx @@ -0,0 +1,33 @@ +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import CreateInvoiceApp from 'src/components/apps/invoice/Add-invoice'; +import BlankCard from 'src/components/shared/BlankCard'; +import { CardContent } from '@mui/material'; +import { InvoiceProvider } from 'src/context/InvoiceContext'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Invoice Create', + }, +]; + +const CreateInvoice = () => { + return ( + + + + + + + + + + + + ); +}; +export default CreateInvoice; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/Detail.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/Detail.tsx new file mode 100644 index 0000000..4f57afd --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/Detail.tsx @@ -0,0 +1,32 @@ +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import { InvoiceProvider } from 'src/context/InvoiceContext/index'; +import InvoiceDetail from 'src/components/apps/invoice/Invoice-detail/index'; +import BlankCard from 'src/components/shared/BlankCard'; +import { CardContent } from '@mui/material'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Invoice Details', + }, +]; + +const InvoiceDetailPage = () => { + return ( + + + + + + + + + + + ); +}; +export default InvoiceDetailPage; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/Edit.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/Edit.tsx new file mode 100644 index 0000000..9082b0f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/Edit.tsx @@ -0,0 +1,33 @@ +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import EditInvoicePage from 'src/components/apps/invoice/Edit-invoice/index'; +import { InvoiceProvider } from 'src/context/InvoiceContext/index'; +import BlankCard from 'src/components/shared/BlankCard'; +import { CardContent } from '@mui/material'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Invoice Edit', + }, +]; + +const InvoiceEdit = () => { + return ( + + + + + + + + + + + ); +}; + +export default InvoiceEdit; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/List.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/List.tsx new file mode 100644 index 0000000..2f22de2 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/invoice/List.tsx @@ -0,0 +1,32 @@ +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import InvoiceList from 'src/components/apps/invoice/Invoice-list/index'; +import { InvoiceProvider } from 'src/context/InvoiceContext/index'; +import BlankCard from 'src/components/shared/BlankCard'; +import { CardContent } from '@mui/material'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Invoice List', + }, +]; + +const InvoiceListing = () => { + return ( + + + + + + + + + + + ); +}; +export default InvoiceListing; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/kanban/Kanban.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/kanban/Kanban.tsx new file mode 100644 index 0000000..6bdca37 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/kanban/Kanban.tsx @@ -0,0 +1,33 @@ +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import TaskManager from 'src/components/apps/kanban/TaskManager'; +import { KanbanDataContextProvider } from 'src/context/kanbancontext/index'; +import BlankCard from 'src/components/shared/BlankCard'; +import { CardContent } from '@mui/material'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Kanban', + }, +]; + +const Kanban = () => { + return ( + + + + + + + + + + + ); +}; + +export default Kanban; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/notes/Notes.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/notes/Notes.tsx new file mode 100644 index 0000000..0b7d6ab --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/notes/Notes.tsx @@ -0,0 +1,46 @@ +import { useState } from 'react'; +import { Box, useMediaQuery } from '@mui/material'; +import Breadcrumb from '../../../layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from '../../../components/container/PageContainer'; +import NoteSidebar from '../../../components/apps/notes/NoteSidebar'; +import NoteContent from '../../../components/apps/notes/NoteContent'; +import AppCard from 'src/components/shared/AppCard'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Notes', + }, +]; + +const Notes = () => { + const [isMobileSidebarOpen, setMobileSidebarOpen] = useState(true); + const lgDown = useMediaQuery((theme: any) => theme.breakpoints.down('lg')); + + + return ( + + + + {lgDown ? + setMobileSidebarOpen(false)} + /> + : setMobileSidebarOpen(false)} + />} + + + setMobileSidebarOpen(!isMobileSidebarOpen)} /> + + + + ); +}; + +export default Notes; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/tickets/Tickets.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/tickets/Tickets.tsx new file mode 100644 index 0000000..2733e28 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/tickets/Tickets.tsx @@ -0,0 +1,29 @@ +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import TicketListing from 'src/components/apps/tickets/TicketListing'; +import TicketFilter from 'src/components/apps/tickets/TicketFilter'; +import ChildCard from 'src/components/shared/ChildCard'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Tickets', + }, +]; + +const TicketList = () => { + return ( + + + + + + + + ); +}; + +export default TicketList; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/Followers.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/Followers.tsx new file mode 100644 index 0000000..445ffa3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/Followers.tsx @@ -0,0 +1,31 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Grid from '@mui/material/Grid2'; +import PageContainer from 'src/components/container/PageContainer'; +import ProfileBanner from 'src/components/apps/userprofile/profile/ProfileBanner'; +import FollowerCard from 'src/components/apps/userprofile/followers/FollowerCard'; + + +const Followers = () => { + return ( + ( + + + + + + + + + ) + ); +}; + +export default Followers; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/Friends.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/Friends.tsx new file mode 100644 index 0000000..ec69332 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/Friends.tsx @@ -0,0 +1,30 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Grid from '@mui/material/Grid2'; +import PageContainer from 'src/components/container/PageContainer'; +import ProfileBanner from 'src/components/apps/userprofile/profile/ProfileBanner'; +import FriendsCard from 'src/components/apps/userprofile/friends/FriendsCard'; + +const Friends = () => { + return ( + ( + + + + + + + + + ) + ); +}; + +export default Friends; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/Gallery.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/Gallery.tsx new file mode 100644 index 0000000..0608f00 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/Gallery.tsx @@ -0,0 +1,31 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Grid from '@mui/material/Grid2'; +import PageContainer from 'src/components/container/PageContainer'; +import ProfileBanner from 'src/components/apps/userprofile/profile/ProfileBanner'; +import GalleryCard from 'src/components/apps/userprofile/gallery/GalleryCard'; + + +const Gallery = () => { + return ( + ( + + + + + + + + + ) + ); +}; + +export default Gallery; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/UserProfile.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/UserProfile.tsx new file mode 100644 index 0000000..c82a285 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/apps/user-profile/UserProfile.tsx @@ -0,0 +1,59 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Grid from '@mui/material/Grid2'; +import PageContainer from 'src/components/container/PageContainer'; + +import ProfileBanner from 'src/components/apps/userprofile/profile/ProfileBanner'; +import IntroCard from 'src/components/apps/userprofile/profile/IntroCard'; +import PhotosCard from 'src/components/apps/userprofile/profile/PhotosCard'; +import Post from 'src/components/apps/userprofile/profile/Post'; + +const UserProfile = () => { + return ( + ( + + + + + + {/* intro and Photos Card */} + + + + + + + + + + + {/* Posts Card */} + + + + + ) + ); +}; + +export default UserProfile; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/Error.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/Error.tsx new file mode 100644 index 0000000..4b259c6 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/Error.tsx @@ -0,0 +1,34 @@ +import { Box, Container, Typography, Button } from '@mui/material'; +import { Link } from 'react-router'; +import ErrorImg from 'src/assets/images/backgrounds/errorimg.svg'; + +const Error = () => ( + + + 404 + + Opps!!! + + + This page you are looking for could not be found. + + + + +); + +export default Error; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/Maintenance.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/Maintenance.tsx new file mode 100644 index 0000000..f5f2ce7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/Maintenance.tsx @@ -0,0 +1,28 @@ +import { Box, Container, Typography, Button } from '@mui/material'; +import { Link } from 'react-router'; +import MaintenanceImg from 'src/assets/images/backgrounds/maintenance.svg'; + +const Maintenance = () => ( + + + 404 + + Maintenance Mode!!! + + + Website is Under Construction. Check back later! + + + + +); + +export default Maintenance; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/ForgotPassword.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/ForgotPassword.tsx new file mode 100644 index 0000000..e220367 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/ForgotPassword.tsx @@ -0,0 +1,88 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Box, Typography } from '@mui/material'; + +import Logo from 'src/layouts/full/shared/logo/Logo'; +import PageContainer from 'src/components/container/PageContainer'; + +import img1 from 'src/assets/images/backgrounds/login-bg.svg'; + +import AuthForgotPassword from '../authForms/AuthForgotPassword'; + +const ForgotPassword = () => ( + + + + + + + + + bg + + + + + + + Forgot your password? + + + + Please enter the email address associated with your account and We will email you a link + to reset your password. + + + + + + +); + +export default ForgotPassword; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/Login.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/Login.tsx new file mode 100644 index 0000000..939f966 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/Login.tsx @@ -0,0 +1,103 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Link } from 'react-router'; +import { Grid2 as Grid, Box, Stack, Typography } from '@mui/material'; +import PageContainer from 'src/components/container/PageContainer'; +import img1 from 'src/assets/images/backgrounds/login-bg.svg'; +import Logo from 'src/layouts/full/shared/logo/Logo'; +import AuthLogin from '../authForms/AuthLogin'; + +const Login = () => ( + + + + + + + + + bg + + + + + + + Your Admin Dashboard + + } + subtitle={ + + + New to Modernize? + + + Create an account + + + } + /> + + + + +); + +export default Login; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/Register.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/Register.tsx new file mode 100644 index 0000000..90d886b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/Register.tsx @@ -0,0 +1,105 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Link } from 'react-router'; +import { Grid2 as Grid, Box, Typography, Stack } from '@mui/material'; + +import PageContainer from 'src/components/container/PageContainer'; +import img1 from 'src/assets/images/backgrounds/login-bg.svg'; +import Logo from 'src/layouts/full/shared/logo/Logo'; + +import AuthRegister from '../authForms/AuthRegister'; + +const Register = () => ( + + + + + + + + + bg + + + + + + + Your Admin Dashboard + + } + subtitle={ + + + Already have an Account? + + + Sign In + + + } + /> + + + + +); + +export default Register; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/TwoSteps.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/TwoSteps.tsx new file mode 100644 index 0000000..9174246 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth1/TwoSteps.tsx @@ -0,0 +1,90 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Box, Typography } from '@mui/material'; + +import PageContainer from 'src/components/container/PageContainer'; +import img1 from 'src/assets/images/backgrounds/login-bg.svg'; +import Logo from 'src/layouts/full/shared/logo/Logo'; + +import AuthTwoSteps from '../authForms/AuthTwoSteps'; + +const TwoSteps = () => ( + + + + + + + + + bg + + + + + + + Two Step Verification + + + + We sent a verification code to your mobile. Enter the code from the mobile in the field + below. + + + ******1234 + + + + + + +); + +export default TwoSteps; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/ForgotPassword2.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/ForgotPassword2.tsx new file mode 100644 index 0000000..90bdccb --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/ForgotPassword2.tsx @@ -0,0 +1,60 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Box, Card, Typography } from '@mui/material'; + +import Logo from 'src/layouts/full/shared/logo/Logo'; +import PageContainer from 'src/components/container/PageContainer'; + +import AuthForgotPassword from '../authForms/AuthForgotPassword'; + +const ForgotPassword2 = () => ( + + + + + + + + + + Please enter the email address associated with your account and We will email you a + link to reset your password. + + + + + + + +); + +export default ForgotPassword2; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/Login2.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/Login2.tsx new file mode 100644 index 0000000..558b8cc --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/Login2.tsx @@ -0,0 +1,76 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Link } from 'react-router'; +import { Grid2 as Grid, Box, Card, Stack, Typography } from '@mui/material'; + + + +// components +import PageContainer from 'src/components/container/PageContainer'; +import Logo from 'src/layouts/full/shared/logo/Logo'; +import AuthLogin from '../authForms/AuthLogin'; + +const Login2 = () => { + + return ( + ( + + + + + + + + + + New to Modernize? + + + Create an account + + + } + /> + + + + + ) + ); +}; + +export default Login2; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/Register2.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/Register2.tsx new file mode 100644 index 0000000..f15e8e1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/Register2.tsx @@ -0,0 +1,75 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Box, Card, Typography, Stack } from '@mui/material'; +import { Link } from 'react-router'; +import PageContainer from 'src/components/container/PageContainer'; +import Logo from 'src/layouts/full/shared/logo/Logo'; + +import AuthRegister from '../authForms/AuthRegister'; + +const Register2 = () => ( + + + + + + + + + + Your Social Campaigns + + } + subtitle={ + + + Already have an Account? + + + Sign In + + + } + /> + + + + + +); + +export default Register2; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/TwoSteps2.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/TwoSteps2.tsx new file mode 100644 index 0000000..2a7cc7a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/auth2/TwoSteps2.tsx @@ -0,0 +1,58 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Box, Card, Typography } from '@mui/material'; + +import Logo from 'src/layouts/full/shared/logo/Logo'; +import PageContainer from 'src/components/container/PageContainer'; + +import AuthTwoSteps from '../authForms/AuthTwoSteps'; + +const TwoSteps2 = () => ( + + + + + + + + + + We sent a verification code to your mobile. Enter the code from the mobile in the + field below. + + + ******1234 + + + + + + + +); + +export default TwoSteps2; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthForgotPassword.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthForgotPassword.tsx new file mode 100644 index 0000000..6af6362 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthForgotPassword.tsx @@ -0,0 +1,26 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Button, Stack } from '@mui/material'; +import { Link } from 'react-router'; + +import CustomTextField from '../../../components/forms/theme-elements/CustomTextField'; +import CustomFormLabel from '../../../components/forms/theme-elements/CustomFormLabel'; + +const AuthForgotPassword = () => ( + <> + + Email Adddress + + + + + + +); + +export default AuthForgotPassword; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthLogin.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthLogin.tsx new file mode 100644 index 0000000..97fabb7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthLogin.tsx @@ -0,0 +1,96 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Box, + Typography, + FormGroup, + FormControlLabel, + Button, + Stack, + Divider, +} from '@mui/material'; +import { Link } from 'react-router'; + +import { loginType } from 'src/types/auth/auth'; +import CustomCheckbox from '../../../components/forms/theme-elements/CustomCheckbox'; +import CustomTextField from '../../../components/forms/theme-elements/CustomTextField'; +import CustomFormLabel from '../../../components/forms/theme-elements/CustomFormLabel'; + +import AuthSocialButtons from './AuthSocialButtons'; + + + +const AuthLogin = ({ title, subtitle, subtext }: loginType) => ( + <> + {title ? ( + + {title} + + ) : null} + + {subtext} + + + + + + or sign in with + + + + + + + Username + + + + Password + + + + + } + label="Remeber this Device" + /> + + + Forgot Password ? + + + + + + + {subtitle} + +); + +export default AuthLogin; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthRegister.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthRegister.tsx new file mode 100644 index 0000000..8d8c985 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthRegister.tsx @@ -0,0 +1,56 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, Typography, Button, Divider, Stack } from '@mui/material'; +import { Link } from 'react-router'; + +import CustomTextField from '../../../components/forms/theme-elements/CustomTextField'; +import CustomFormLabel from '../../../components/forms/theme-elements/CustomFormLabel'; +import { registerType } from 'src/types/auth/auth'; +import AuthSocialButtons from './AuthSocialButtons'; + + +const AuthRegister = ({ title, subtitle, subtext }: registerType) => ( + <> + {title ? ( + + {title} + + ) : null} + + {subtext} + + + + + + or sign up with + + + + + + + Name + + Email Adddress + + Password + + + + + {subtitle} + +); + +export default AuthRegister; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthSocialButtons.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthSocialButtons.tsx new file mode 100644 index 0000000..3608fc7 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthSocialButtons.tsx @@ -0,0 +1,49 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import icon1 from 'src/assets/images/svgs/google-icon.svg'; +import icon2 from 'src/assets/images/svgs/facebook-icon.svg'; +import CustomSocialButton from '../../../components/forms/theme-elements/CustomSocialButton'; +import { Avatar, Box, Stack } from '@mui/material'; +import { signInType } from 'src/types/auth/auth'; + +const AuthSocialButtons = ({ title }: signInType) => ( + <> + + + + + {title}{' '} + {' '} + Google + + + + + {title}{' '} + {' '} + FB + + + +); + +export default AuthSocialButtons; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthTwoSteps.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthTwoSteps.tsx new file mode 100644 index 0000000..e4616d0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/authentication/authForms/AuthTwoSteps.tsx @@ -0,0 +1,61 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, Typography, Button, Stack } from '@mui/material'; +import { Link } from 'react-router'; + +import CustomTextField from '../../../components/forms/theme-elements/CustomTextField'; +import CustomFormLabel from '../../../components/forms/theme-elements/CustomFormLabel'; + +const AuthTwoSteps = () => ( + <> + + + Type your 6 digits security code + + + + + + + + + + + + + + + + + Didn't get the code? + + + Resend + + + + +); + +export default AuthTwoSteps; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/AreaChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/AreaChart.tsx new file mode 100644 index 0000000..a683552 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/AreaChart.tsx @@ -0,0 +1,104 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import PageContainer from '../../components/container/PageContainer'; +import Breadcrumb from '../../layouts/full/shared/breadcrumb/Breadcrumb'; +import ParentCard from '../../components/shared/ParentCard'; +import { Props } from 'react-apexcharts'; + +import AreaChartCode from 'src/components/charts/Area Chart/code/AreaChartCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Area Chart', + }, +]; + +const AreaChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + const optionsareachart: Props = { + chart: { + id: 'area-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + zoom: { + enabled: true, + }, + toolbar: { + show: false, + }, + }, + dataLabels: { + enabled: false, + }, + stroke: { + width: '3', + curve: 'smooth', + }, + colors: [primary, secondary], + xaxis: { + type: 'datetime', + categories: [ + '2018-09-19T00:00:00', + '2018-09-19T01:30:00', + '2018-09-19T02:30:00', + '2018-09-19T03:30:00', + '2018-09-19T04:30:00', + '2018-09-19T05:30:00', + '2018-09-19T06:30:00', + ], + }, + yaxis: { + opposite: false, + labels: { + show: true, + }, + }, + legend: { + show: true, + position: 'bottom', + width: '50px', + }, + grid: { + show: false, + }, + tooltip: { + theme: 'dark', + fillSeriesColor: false, + }, + }; + const seriesareachart = [ + { + name: 'Sales Summery 1', + data: [31, 40, 28, 51, 42, 109, 100], + }, + { + name: 'Sales Summery 2', + data: [11, 32, 45, 32, 34, 52, 41], + }, + ]; + + return ( + + {/* breadcrumb */} + + {/* end breadcrumb */} + }> + + + + ); +}; + +export default AreaChart; \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/CandlestickChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/CandlestickChart.tsx new file mode 100644 index 0000000..31ac99b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/CandlestickChart.tsx @@ -0,0 +1,147 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import PageContainer from '../../components/container/PageContainer'; +import Breadcrumb from '../../layouts/full/shared/breadcrumb/Breadcrumb'; +import ParentCard from '../../components/shared/ParentCard'; +import { Props } from 'react-apexcharts'; + +import CandlestickChartCode from 'src/components/charts/Candlestick Chart/code/CandlestickChartCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Candlestick Chart', + }, +]; + +const CandlestickChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + const optionscandlestickchart: Props = { + chart: { + height: 350, + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + }, + xaxis: { + type: 'datetime', + }, + yaxis: { + tooltip: { + enabled: true, + }, + }, + plotOptions: { + candlestick: { + colors: { + upward: primary, + downward: secondary, + }, + }, + }, + tooltip: { + theme: 'dark', + }, + grid: { + show: false, + }, + }; + const seriecandlestickchart: any = [ + { + data: [ + { x: new Date(1538778600000), y: [6629.81, 6650.5, 6623.04, 6633.33] }, + { x: new Date(1538780400000), y: [6632.01, 6643.59, 6620, 6630.11] }, + { x: new Date(1538782200000), y: [6630.71, 6648.95, 6623.34, 6635.65] }, + { x: new Date(1538784000000), y: [6635.65, 6651, 6629.67, 6638.24] }, + { x: new Date(1538785800000), y: [6638.24, 6640, 6620, 6624.47] }, + { x: new Date(1538787600000), y: [6624.53, 6636.03, 6621.68, 6624.31] }, + { x: new Date(1538789400000), y: [6624.61, 6632.2, 6617, 6626.02] }, + { x: new Date(1538791200000), y: [6627, 6627.62, 6584.22, 6603.02] }, + { x: new Date(1538793000000), y: [6605, 6608.03, 6598.95, 6604.01] }, + { x: new Date(1538794800000), y: [6604.5, 6614.4, 6602.26, 6608.02] }, + { x: new Date(1538796600000), y: [6608.02, 6610.68, 6601.99, 6608.91] }, + { x: new Date(1538798400000), y: [6608.91, 6618.99, 6608.01, 6612] }, + { x: new Date(1538800200000), y: [6612, 6615.13, 6605.09, 6612] }, + { x: new Date(1538802000000), y: [6612, 6624.12, 6608.43, 6622.95] }, + { x: new Date(1538803800000), y: [6623.91, 6623.91, 6615, 6615.67] }, + { x: new Date(1538805600000), y: [6618.69, 6618.74, 6610, 6610.4] }, + { x: new Date(1538807400000), y: [6611, 6622.78, 6610.4, 6614.9] }, + { x: new Date(1538809200000), y: [6614.9, 6626.2, 6613.33, 6623.45] }, + { x: new Date(1538811000000), y: [6623.48, 6627, 6618.38, 6620.35] }, + { x: new Date(1538812800000), y: [6619.43, 6620.35, 6610.05, 6615.53] }, + { x: new Date(1538814600000), y: [6615.53, 6617.93, 6610, 6615.19] }, + { x: new Date(1538816400000), y: [6615.19, 6621.6, 6608.2, 6620] }, + { x: new Date(1538818200000), y: [6619.54, 6625.17, 6614.15, 6620] }, + { x: new Date(1538820000000), y: [6620.33, 6634.15, 6617.24, 6624.61] }, + { x: new Date(1538821800000), y: [6625.95, 6626, 6611.66, 6617.58] }, + { x: new Date(1538823600000), y: [6619, 6625.97, 6595.27, 6598.86] }, + { x: new Date(1538825400000), y: [6598.86, 6598.88, 6570, 6587.16] }, + { x: new Date(1538827200000), y: [6588.86, 6600, 6580, 6593.4] }, + { x: new Date(1538829000000), y: [6593.99, 6598.89, 6585, 6587.81] }, + { x: new Date(1538830800000), y: [6587.81, 6592.73, 6567.14, 6578] }, + { x: new Date(1538832600000), y: [6578.35, 6581.72, 6567.39, 6579] }, + { x: new Date(1538834400000), y: [6579.38, 6580.92, 6566.77, 6575.96] }, + { x: new Date(1538836200000), y: [6575.96, 6589, 6571.77, 6588.92] }, + { x: new Date(1538838000000), y: [6588.92, 6594, 6577.55, 6589.22] }, + { x: new Date(1538839800000), y: [6589.3, 6598.89, 6589.1, 6596.08] }, + { x: new Date(1538841600000), y: [6597.5, 6600, 6588.39, 6596.25] }, + { x: new Date(1538843400000), y: [6598.03, 6600, 6588.73, 6595.97] }, + { x: new Date(1538845200000), y: [6595.97, 6602.01, 6588.17, 6602] }, + { x: new Date(1538847000000), y: [6602, 6607, 6596.51, 6599.95] }, + { x: new Date(1538848800000), y: [6600.63, 6601.21, 6590.39, 6591.02] }, + { x: new Date(1538850600000), y: [6591.02, 6603.08, 6591, 6591] }, + { x: new Date(1538852400000), y: [6591, 6601.32, 6585, 6592] }, + { x: new Date(1538854200000), y: [6593.13, 6596.01, 6590, 6593.34] }, + { x: new Date(1538856000000), y: [6593.34, 6604.76, 6582.63, 6593.86] }, + { x: new Date(1538857800000), y: [6593.86, 6604.28, 6586.57, 6600.01] }, + { x: new Date(1538859600000), y: [6601.81, 6603.21, 6592.78, 6596.25] }, + { x: new Date(1538861400000), y: [6596.25, 6604.2, 6590, 6602.99] }, + { x: new Date(1538863200000), y: [6602.99, 6606, 6584.99, 6587.81] }, + { x: new Date(1538865000000), y: [6587.81, 6595, 6583.27, 6591.96] }, + { x: new Date(1538866800000), y: [6591.97, 6596.07, 6585, 6588.39] }, + { x: new Date(1538868600000), y: [6587.6, 6598.21, 6587.6, 6594.27] }, + { x: new Date(1538870400000), y: [6596.44, 6601, 6590, 6596.55] }, + { x: new Date(1538872200000), y: [6598.91, 6605, 6596.61, 6600.02] }, + { x: new Date(1538874000000), y: [6600.55, 6605, 6589.14, 6593.01] }, + { x: new Date(1538875800000), y: [6593.15, 6605, 6592, 6603.06] }, + { x: new Date(1538877600000), y: [6603.07, 6604.5, 6599.09, 6603.89] }, + { x: new Date(1538879400000), y: [6604.44, 6604.44, 6600, 6603.5] }, + { x: new Date(1538881200000), y: [6603.5, 6603.99, 6597.5, 6603.86] }, + { x: new Date(1538883000000), y: [6603.85, 6605, 6600, 6604.07] }, + { x: new Date(1538884800000), y: [6604.98, 6606, 6604.07, 6606] }, + ], + }, + ]; + + return ( + + {/* breadcrumb */} + + {/* end breadcrumb */} + }> + + + + ); +}; + +export default CandlestickChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/ColumnChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/ColumnChart.tsx new file mode 100644 index 0000000..b1316b1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/ColumnChart.tsx @@ -0,0 +1,116 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import PageContainer from '../../components/container/PageContainer'; +import Breadcrumb from '../../layouts/full/shared/breadcrumb/Breadcrumb'; +import ParentCard from '../../components/shared/ParentCard'; +import { Props } from 'react-apexcharts'; + +import ColumnChartCode from 'src/components/charts/Column Chart/code/ColumnChartCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Column Chart', + }, +]; + +const ColumnChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const error = theme.palette.error.main; + + const optionscolumnchart: Props = { + chart: { + id: 'column-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + }, + colors: [primary, secondary, error], + plotOptions: { + bar: { + horizontal: false, + endingShape: 'rounded', + columnWidth: '20%', + }, + }, + dataLabels: { + enabled: false, + }, + stroke: { + show: true, + width: 2, + colors: ['transparent'], + }, + xaxis: { + categories: ['Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct'], + }, + yaxis: { + title: { + text: '$ (thousands)', + }, + }, + fill: { + opacity: 1, + }, + tooltip: { + y: { + formatter(val: any) { + return `$ ${val} thousands`; + }, + }, + theme: 'dark', + }, + grid: { + show: false, + }, + legend: { + show: true, + position: 'bottom', + width: '50px', + }, + }; + const seriescolumnchart: any = [ + { + name: 'Desktop', + data: [44, 55, 57, 56, 61, 58, 63, 60, 66], + }, + { + name: 'Mobile', + data: [76, 85, 101, 98, 87, 105, 91, 114, 94], + }, + { + name: 'Other', + data: [35, 41, 36, 26, 45, 48, 52, 53, 41], + }, + ]; + + return ( + + {/* breadcrumb */} + + {/* end breadcrumb */} + }> + + + + ); +}; + +export default ColumnChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/DoughnutChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/DoughnutChart.tsx new file mode 100644 index 0000000..806b2a0 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/DoughnutChart.tsx @@ -0,0 +1,133 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import Grid from '@mui/material/Grid2'; +import PageContainer from '../../components/container/PageContainer'; +import Breadcrumb from '../../layouts/full/shared/breadcrumb/Breadcrumb'; +import ParentCard from '../../components/shared/ParentCard'; +import { Props } from 'react-apexcharts'; + +import DoughnutChartsCode from 'src/components/charts/Doughnut Charts/code/DoughnutChartsCode'; +import PieChartsCode from 'src/components/charts/Pie Charts/code/PieChartsCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Doughtnut Chart', + }, +]; + +const DoughnutChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const primarylight = theme.palette.primary.light; + const secondary = theme.palette.secondary.main; + const secondarylight = theme.palette.secondary.light; + const warning = theme.palette.warning.main; + + // 1 + const optionsdoughnutchart: Props = { + chart: { + id: 'donut-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + }, + dataLabels: { + enabled: false, + }, + plotOptions: { + pie: { + donut: { + size: '70px', + }, + }, + }, + legend: { + show: true, + position: 'bottom', + width: '50px', + }, + colors: [primary, primarylight, secondary, secondarylight, warning], + tooltip: { + theme: 'dark', + fillSeriesColor: false, + }, + }; + const seriesdoughnutchart = [45, 15, 27, 18, 35]; + + // 2 + const optionspiechart: Props = { + chart: { + id: 'pie-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + }, + dataLabels: { + enabled: false, + }, + plotOptions: { + pie: { + donut: { + size: '70px', + }, + }, + }, + legend: { + show: true, + position: 'bottom', + width: '50px', + }, + colors: [primary, primarylight, secondary, secondarylight, warning], + tooltip: { + fillSeriesColor: false, + }, + }; + const seriespiechart = [45, 15, 27, 18, 35]; + + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + + + }> + + + + + }> + + + + + ) + ); +}; + +export default DoughnutChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/GredientChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/GredientChart.tsx new file mode 100644 index 0000000..5140073 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/GredientChart.tsx @@ -0,0 +1,133 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import PageContainer from '../../components/container/PageContainer'; +import Breadcrumb from '../../layouts/full/shared/breadcrumb/Breadcrumb'; +import ParentCard from '../../components/shared/ParentCard'; +import { Props } from 'react-apexcharts'; + +import GradientChartCode from 'src/components/charts/Gradient Chart/code/GradientChartCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Gradient Chart', + }, +]; + +const GredientChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + + const optionsgredientchart: Props = { + chart: { + height: 350, + type: 'line', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + dropShadow: { + enabled: true, + color: 'rgba(0,0,0,0.2)', + top: 12, + left: 4, + blur: 3, + opacity: 0.4, + }, + }, + stroke: { + width: 7, + curve: 'smooth', + }, + + xaxis: { + type: 'datetime', + categories: [ + '1/11/2000', + '2/11/2000', + '3/11/2000', + '4/11/2000', + '5/11/2000', + '6/11/2000', + '7/11/2000', + '8/11/2000', + '9/11/2000', + '10/11/2000', + '11/11/2000', + '12/11/2000', + '1/11/2001', + '2/11/2001', + '3/11/2001', + '4/11/2001', + '5/11/2001', + '6/11/2001', + ], + }, + fill: { + type: 'gradient', + gradient: { + shade: 'dark', + gradientToColors: [primary], + shadeIntensity: 1, + type: 'horizontal', + opacityFrom: 1, + opacityTo: 0.9, + stops: [0, 100, 100, 100], + }, + }, + markers: { + size: 4, + opacity: 0.9, + colors: [primary], + strokeColor: '#fff', + strokeWidth: 2, + + hover: { + size: 7, + }, + }, + yaxis: { + min: 0, + max: 40, + }, + tooltip: { + theme: 'dark', + }, + grid: { + show: false, + }, + }; + const seriesgredientchart: any = [ + { + name: 'Likes', + data: [4, 3, 10, 9, 35, 19, 22, 9, 12, 7, 19, 5, 13, 9, 17, 2, 7, 5], + }, + ]; + + return ( + + {/* breadcrumb */} + + {/* end breadcrumb */} + } > + + + + ); +}; + +export default GredientChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/LineChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/LineChart.tsx new file mode 100644 index 0000000..050cd02 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/LineChart.tsx @@ -0,0 +1,108 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import { useTheme } from '@mui/material/styles'; +import PageContainer from '../../components/container/PageContainer'; +import Breadcrumb from '../../layouts/full/shared/breadcrumb/Breadcrumb'; +import ParentCard from '../../components/shared/ParentCard'; +import { Props } from 'react-apexcharts'; + +import LineChartCode from 'src/components/charts/Line Chart/code/LineChartCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Line Chart', + }, +]; + +const LineChart = () => { + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + + const optionslinechart: Props = { + chart: { + height: 350, + type: 'line', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + zoom: { + type: 'x', + enabled: true, + }, + toolbar: { + show: false, + }, + shadow: { + enabled: true, + color: '#000', + top: 18, + left: 7, + blur: 10, + opacity: 1, + }, + }, + xaxis: { + categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul'], + title: { + text: 'Month', + }, + }, + grid: { + show: false, + }, + colors: [primary, secondary], + dataLabels: { + enabled: true, + }, + stroke: { + curve: 'straight', + width: '2', + }, + legend: { + position: 'top', + horizontalAlign: 'right', + floating: true, + offsetY: -25, + offsetX: -5, + }, + tooltip: { + theme: 'dark', + }, + }; + const serieslinechart: any = [ + { + name: 'High - 2013', + data: [28, 29, 33, 36, 32, 32, 33], + }, + { + name: 'Low - 2013', + data: [12, 11, 14, 18, 17, 13, 13], + }, + ]; + + return ( + + {/* breadcrumb */} + + {/* end breadcrumb */} + }> + + + + ); +}; + +export default LineChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/RadialbarChart.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/RadialbarChart.tsx new file mode 100644 index 0000000..7ad822e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/charts/RadialbarChart.tsx @@ -0,0 +1,132 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Chart from 'react-apexcharts'; +import Grid from '@mui/material/Grid2'; +import { useTheme } from '@mui/material/styles'; +import PageContainer from '../../components/container/PageContainer'; +import Breadcrumb from '../../layouts/full/shared/breadcrumb/Breadcrumb'; +import ParentCard from '../../components/shared/ParentCard'; +import { Props } from 'react-apexcharts'; + +import RadialbarChartsCode from 'src/components/charts/Radialbar Charts/code/RadialbarChartsCode'; +import RadarChartsCode from 'src/components/charts/Radar Charts/code/RadarChartsCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Radialbar Chart', + }, +]; + +const RadialbarChart = () => { + + // chart color + const theme = useTheme(); + const primary = theme.palette.primary.main; + const secondary = theme.palette.secondary.main; + const success = theme.palette.success.main; + const warning = theme.palette.warning.main; + + const optionsradialchart: Props = { + chart: { + id: 'pie-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + foreColor: '#adb0bb', + toolbar: { + show: false, + }, + }, + colors: [primary, secondary, success, warning], + plotOptions: { + radialBar: { + dataLabels: { + name: { + fontSize: '22px', + }, + value: { + fontSize: '16px', + }, + total: { + show: true, + label: 'Total', + formatter() { + return 249; + }, + }, + }, + }, + }, + tooltip: { + theme: 'dark', + }, + }; + const seriesradialchart: any = [44, 55, 67, 83]; + + // 2 + const optionsradarchart: Props = { + chart: { + id: 'pie-chart', + fontFamily: "'Plus Jakarta Sans', sans-serif", + toolbar: { + show: false, + }, + }, + colors: [primary], + labels: ['January', 'February', 'March', 'April', 'May', 'June'], + tooltip: { + theme: 'dark', + }, + }; + const seriesradarchart: any = [ + { + name: 'Sales', + data: [80, 50, 30, 40, 100, 20], + }, + ]; + + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + + + }> + + + + + }> + + + + + ) + ); +}; + +export default RadialbarChart; \ No newline at end of file diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/dashboard/Ecommerce.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/dashboard/Ecommerce.tsx new file mode 100644 index 0000000..754c3d1 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/dashboard/Ecommerce.tsx @@ -0,0 +1,149 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, Grid2 as Grid } from '@mui/material'; +import PageContainer from 'src/components/container/PageContainer'; + +import WeeklyStats from 'src/components/dashboards/modern/WeeklyStats'; +import YearlySales from 'src/components/dashboards/ecommerce/YearlySales'; +import PaymentGateways from 'src/components/dashboards/ecommerce/PaymentGateways'; +import WelcomeCard from 'src/components/dashboards/ecommerce/WelcomeCard'; +import Expence from 'src/components/dashboards/ecommerce/Expence'; +import Growth from 'src/components/dashboards/ecommerce/Growth'; +import RevenueUpdates from 'src/components/dashboards/ecommerce/RevenueUpdates'; +import SalesOverview from 'src/components/dashboards/ecommerce/SalesOverview'; +import SalesTwo from 'src/components/dashboards/ecommerce/SalesTwo'; +import Sales from 'src/components/dashboards/ecommerce/Sales'; +import MonthlyEarnings from 'src/components/dashboards/ecommerce/MonthlyEarnings'; +import ProductPerformances from 'src/components/dashboards/ecommerce/ProductPerformances'; +import RecentTransactions from 'src/components/dashboards/ecommerce/RecentTransactions'; + +const Ecommerce = () => { + return ( + ( + + + {/* column */} + + + + + {/* column */} + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + {/* column */} + + + + {/* column */} + + + + {/* column */} + + + + {/* column */} + + + + + {/* column */} + + + + + + + ) + ); +}; + +export default Ecommerce; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/dashboard/Modern.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/dashboard/Modern.tsx new file mode 100644 index 0000000..90bccba --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/dashboard/Modern.tsx @@ -0,0 +1,132 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Box, Grid2 as Grid } from '@mui/material'; +import PageContainer from 'src/components/container/PageContainer'; + +import TopCards from 'src/components/dashboards/modern/TopCards'; +import RevenueUpdates from 'src/components/dashboards/modern/RevenueUpdates'; +import YearlyBreakup from 'src/components/dashboards/modern/YearlyBreakup'; +import MonthlyEarnings from 'src/components/dashboards/modern/MonthlyEarnings'; +import EmployeeSalary from 'src/components/dashboards/modern/EmployeeSalary'; +import Customers from 'src/components/dashboards/modern/Customers'; +import Projects from 'src/components/dashboards/modern/Projects'; +import Social from 'src/components/dashboards/modern/Social'; +import SellingProducts from 'src/components/dashboards/modern/SellingProducts'; +import WeeklyStats from 'src/components/dashboards/modern/WeeklyStats'; +import TopPerformers from 'src/components/dashboards/modern/TopPerformers'; +import Welcome from 'src/layouts/full/shared/welcome/Welcome'; + +const Modern = () => { + return ( + ( + + + {/* column */} + + + + {/* column */} + + + + {/* column */} + + + + + + + + + + + {/* column */} + + + + {/* column */} + + + + + + + + + + + + + + {/* column */} + + + + {/* column */} + + + + {/* column */} + + + + + {/* column */} + + + ) + ); +}; + +export default Modern; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormCustom.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormCustom.tsx new file mode 100644 index 0000000..11aea65 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormCustom.tsx @@ -0,0 +1,470 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Grid2 as Grid, + Box, + Typography, + FormControl, + MenuItem, + RadioGroup, + FormControlLabel, + Button, + SliderValueLabelProps, + Stack +} from '@mui/material'; +import { SliderThumb } from '@mui/material/Slider'; + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; + +import { LocalizationProvider } from '@mui/x-date-pickers'; +import { AdapterDayjs } from "@mui/x-date-pickers/AdapterDayjs"; +import { DateTimePicker } from '@mui/x-date-pickers/DateTimePicker'; +import { TimePicker } from '@mui/x-date-pickers/TimePicker'; + +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import CustomSelect from 'src/components/forms/theme-elements/CustomSelect'; +import CustomSlider from 'src/components/forms/theme-elements/CustomSlider'; +import CustomRangeSlider from 'src/components/forms/theme-elements/CustomRangeSlider'; +import CustomSwitch from 'src/components/forms/theme-elements/CustomSwitch'; +import CustomDisabledButton from 'src/components/forms/theme-elements/CustomDisabledButton'; +import CustomOutlinedButton from 'src/components/forms/theme-elements/CustomOutlinedButton'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import CustomCheckbox from 'src/components/forms/theme-elements/CustomCheckbox'; +import CustomRadio from 'src/components/forms/theme-elements/CustomRadio'; +import ParentCard from 'src/components/shared/ParentCard'; +import { IconVolume, IconVolume2 } from '@tabler/icons-react'; + +import FormCustomCode from 'src/components/forms/form-custom/code/FormCustomCode'; + +function CustomThumbComponent(props: SliderValueLabelProps) { + const { children, ...other } = props; + + return ( + + {children} + + + + + ); +} + +const FormCustom = () => { + const [age, setAge] = React.useState('1'); + const [select1, setSelect] = React.useState('1'); + const [select2, setSelect2] = React.useState('1'); + + const handleChange = (event: any) => { + setAge(event.target.value); + }; + const handleChange4 = (event2: any) => { + setSelect(event2.target.value); + }; + + const handleChange5 = (event3: any) => { + setSelect2(event3.target.value); + }; + + const [value, setValue] = React.useState(null); + const [value2, setValue2] = React.useState(null); + + const [value3, setValue3] = React.useState(30); + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const handleChange6 = (event: any, newValue: any) => { + setValue3(newValue); + }; + + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + }> + + + Name + + Select Dropdown + + One + Two + Three + + + {/* ----------------------------------- */} + {/* column 2 */} + {/* ----------------------------------- */} + + Company Name + + Time + + { + setValue2(newValue); + }} + slotProps={{ + textField: { + fullWidth: true, + + sx: { + '& .MuiSvgIcon-root': { + width: '18px', + height: '18px', + }, + '& .MuiFormHelperText-root': { + display: 'none', + }, + }, + }, + }} + /> + + + {/* ----------------------------------- */} + {/* column 3 */} + {/* ----------------------------------- */} + + Industry Type + + `${theme.palette.mode === 'dark' + ? 'rgba(255, 255, 255, 0.12) !important' + : '#dee3e9 !important' + }`, + }, + }} + /> + Date + + { + setValue(newValue); + }} + /> + + + {/* ----------------------------------- */} + {/* column 4 */} + {/* ----------------------------------- */} + + Lorem ipsum dolor sit amet + + + + + } label="Male" /> + + + + + } label="Female" /> + + + + + } + label="Disabled" + /> + + + + + + {/* ----------------------------------- */} + {/* column 5 */} + {/* ----------------------------------- */} + + Industry Type + + + + } + label="Enter text" + /> + + + } label="Enter text" /> + + + } + label="Disabled" + /> + + + + + {/* ----------------------------------- */} + {/* column 6 */} + {/* ----------------------------------- */} + + Slider + (index === 0 ? 'Minimum price' : 'Maximum price')} + defaultValue={[20, 40]} + /> + + + + 750 + 850 + 950 + + + + + 950 + 1050 + 1150 + + + + Volume + + + + + + + + + + + + + + {/* ----------------------------------- */} + {/* column 7 */} + {/* ----------------------------------- */} + + + Switch + + + } label="Enter text" /> + + + } label="Enter text" /> + + + + } + label="Disabled" + /> + + + + } + label="Disabled" + /> + + + {/* button */} + + + + + Add New + + Add New + + + + + + + + + + ) + ); +}; + +export default FormCustom; + + + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormHorizontal.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormHorizontal.tsx new file mode 100644 index 0000000..24030f8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormHorizontal.tsx @@ -0,0 +1,71 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Typography } from '@mui/material'; + +// components +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ParentCard from 'src/components/shared/ParentCard'; +import BasicLayout from '../../components/forms/form-horizontal/BasicLayout'; +import BasicIcons from '../../components/forms/form-horizontal/BasicIcons'; +import FormSeparator from '../../components/forms/form-horizontal/FormSeparator'; +import FormLabelAlignment from '../../components/forms/form-horizontal/FormLabelAlignment'; +import CollapsibleForm from '../../components/forms/form-horizontal/CollapsibleForm'; +import FormTabs from '../../components/forms/form-horizontal/FormTabs'; + +import BasicLayoutCode from 'src/components/forms/form-horizontal/code/BasicIconsCode'; +import BasicIconsCode from 'src/components/forms/form-horizontal/code/BasicIconsCode'; +import FormSeparatorCode from 'src/components/forms/form-horizontal/code/FormSeparatorCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Horizontal Form', + }, +]; + +const FormHorizontal = () => { + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + + + }> + + + + + }> + + + + + }> + + + + + + + + + + Collapsible Section + + + + Form with Tabs + + + + ) + ); +}; + +export default FormHorizontal; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormLayouts.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormLayouts.tsx new file mode 100644 index 0000000..f23f622 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormLayouts.tsx @@ -0,0 +1,103 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Grid from '@mui/material/Grid2'; +import { + FbOrdinaryForm, + FbDefaultForm, + FbBasicHeaderForm, + FbReadonlyForm, + FbDisabledForm, + FbLeftIconForm, + FbRightIconForm, + FbInputVariants, +} from 'src/components/forms/form-layouts/index'; +import PageContainer from 'src/components/container/PageContainer'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Form Layouts', + }, +]; + +const FormLayouts = () => ( + + {/* breadcrumb */} + + {/* end breadcrumb */} + + + + + + + + + + + + + + + + + + + + + + + + + + + + +); + +export default FormLayouts; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormValidation.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormValidation.tsx new file mode 100644 index 0000000..328dc07 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormValidation.tsx @@ -0,0 +1,109 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + CardContent, + Grid2 as Grid +} from '@mui/material'; + +// common components +import PageContainer from 'src/components/container/PageContainer'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import ChildCard from 'src/components/shared/ChildCard'; +import BlankCard from 'src/components/shared/BlankCard'; +import Logo from "src/layouts/full/shared/logo/Logo"; + +// custom components +import FVLogin from 'src/components/forms/form-validation/FVLogin'; +import FVRegister from 'src/components/forms/form-validation/FVRegister'; +import FVOnLeave from 'src/components/forms/form-validation/FVOnLeave'; +import FVRadio from 'src/components/forms/form-validation/FVRadio'; +import FVCheckbox from 'src/components/forms/form-validation/FVCheckbox'; +import FVSelect from 'src/components/forms/form-validation/FVSelect'; + +import OnLeaveCode from "src/components/forms/form-validation/code/OnLeaveCode"; +import SelectCode from "src/components/forms/form-validation/code/SelectCode"; +import RadioCode from "src/components/forms/form-validation/code/RadioCode"; +import CheckboxCode from "src/components/forms/form-validation/code/CheckboxCode"; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Form Validation', + }, +]; + +const FormValidation = () => { + return ( + ( + + + + + + + + + + + + + + + + + + + + }> + + + + + }> + + + + + }> + + + + + }> + + + + + ) + ); +}; + +export default FormValidation; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormVertical.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormVertical.tsx new file mode 100644 index 0000000..8d0e986 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormVertical.tsx @@ -0,0 +1,75 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Typography } from '@mui/material'; + +// components +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ParentCard from 'src/components/shared/ParentCard'; + + +import BasicLayout from '../../components/forms/form-vertical/BasicLayout'; + +import BasicIcons from '../../components/forms/form-vertical/BasicIcons'; +import FormSeparator from '../../components/forms/form-vertical/FormSeparator'; +import CollapsibleForm from '../../components/forms/form-vertical/CollapsibleForm'; +import FormTabs from '../../components/forms/form-vertical/FormTabs'; + +import BasicLayoutCode from 'src/components/forms/form-vertical/code/BasicLayoutCode'; +import BasicIconsCode from 'src/components/forms/form-vertical/code/BasicIconsCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Vertical Form', + }, +]; + +const FormVertical = () => { + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + + + }> + + + + + }> + + + + + + + + + + Collapsible Section + + + + Form with Tabs + + + + ) + ); +}; + +export default FormVertical; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormWizard.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormWizard.tsx new file mode 100644 index 0000000..7297af8 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/FormWizard.tsx @@ -0,0 +1,189 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { + Box, + Stepper, + Step, + StepLabel, + Button, + Typography, + FormControlLabel, + Alert, + Stack +} from '@mui/material'; +import PageContainer from 'src/components/container/PageContainer'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import FormWizardCode from 'src/components/forms/form-wizard/code/FormWizardCode'; +import CustomTextField from 'src/components/forms/theme-elements/CustomTextField'; +import CustomCheckbox from 'src/components/forms/theme-elements/CustomCheckbox'; +import CustomFormLabel from 'src/components/forms/theme-elements/CustomFormLabel'; +import ParentCard from 'src/components/shared/ParentCard'; + +const steps = ['Account', 'Profile', 'Finish']; + +const FormWizard = () => { + const [activeStep, setActiveStep] = React.useState(0); + const [skipped, setSkipped] = React.useState(new Set()); + + const isStepOptional = (step:any) => step === 1; + + const isStepSkipped = (step:any) => skipped.has(step); + + const handleNext = () => { + let newSkipped = skipped; + if (isStepSkipped(activeStep)) { + newSkipped = new Set(newSkipped.values()); + newSkipped.delete(activeStep); + } + + setActiveStep((prevActiveStep) => prevActiveStep + 1); + setSkipped(newSkipped); + }; + + const handleBack = () => { + setActiveStep((prevActiveStep) => prevActiveStep - 1); + }; + + const handleSkip = () => { + if (!isStepOptional(activeStep)) { + // You probably want to guard against something like this, + // it should never occur unless someone's actively trying to break something. + throw new Error("You can't skip a step that isn't optional."); + } + + setActiveStep((prevActiveStep) => prevActiveStep + 1); + setSkipped((prevSkipped) => { + const newSkipped = new Set(prevSkipped.values()); + newSkipped.add(activeStep); + + return newSkipped; + }); + }; + + // eslint-disable-next-line consistent-return + const handleSteps = (step: any) => { + switch (step) { + case 0: + return ( + + Name + + Email + + Password + + + ); + case 1: + return ( + + First Name + + Last Name + + Address + + + ); + case 2: + return ( + + Terms and condition + + Sard about this site or you have been to it, but you cannot figure out what it is or + what it can do. MTA web directory isSard about this site or you have been to it, but + you cannot figure out what it is or what it can do. MTA web directory is + + } + label="Agree with terms?" + /> + + ); + default: + break; + } + }; + + const handleReset = () => { + setActiveStep(0); + }; + + return ( + + + }> + + + {steps.map((label, index) => { + const stepProps: { completed?: boolean } = {}; + const labelProps: { + optional?: React.ReactNode; + } = {}; + if (isStepOptional(index)) { + labelProps.optional = Optional; + } + if (isStepSkipped(index)) { + stepProps.completed = false; + } + + return ( + + {label} + + ); + })} + + {activeStep === steps.length ? ( + <> + + + All steps completed - you're finished + + + + + + + + ) : ( + <> + {handleSteps(activeStep)} + + + + + {isStepOptional(activeStep) && ( + + )} + + + + + )} + + + + ); +}; + +export default FormWizard; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiAutoComplete.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiAutoComplete.tsx new file mode 100644 index 0000000..6f04781 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiAutoComplete.tsx @@ -0,0 +1,134 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Grid from '@mui/material/Grid2'; + +import ComboBoxAutocomplete from 'src/components/forms/form-elements/autoComplete/ComboBoxAutocomplete'; +import CountrySelectAutocomplete from 'src/components/forms/form-elements/autoComplete/CountrySelectAutocomplete'; +import ControlledStateAutocomplete from 'src/components/forms/form-elements/autoComplete/ControlledStateAutocomplete'; +import FreeSoloAutocomplete from 'src/components/forms/form-elements/autoComplete/FreeSoloAutocomplete'; +import MultipleValuesAutocomplete from 'src/components/forms/form-elements/autoComplete/MultipleValuesAutocomplete'; +import CheckboxesAutocomplete from 'src/components/forms/form-elements/autoComplete/CheckboxesAutocomplete'; +import SizesAutocomplete from 'src/components/forms/form-elements/autoComplete/SizesAutocomplete'; + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ParentCard from 'src/components/shared/ParentCard'; +import ChildCard from 'src/components/shared/ChildCard'; + +// codeModel +import ComboBoxCode from 'src/components/forms/form-elements/autoComplete/code/ComboBoxCode'; +import CountrySelectCode from 'src/components/forms/form-elements/autoComplete/code/CountrySelectCode'; +import ControlledStateCode from 'src/components/forms/form-elements/autoComplete/code/ControlledStateCode'; +import FreeSoloCode from 'src/components/forms/form-elements/autoComplete/code/FreeSoloCode'; +import MultipleValuesCode from 'src/components/forms/form-elements/autoComplete/code/MultipleValuesCode'; +import CheckboxesCode from 'src/components/forms/form-elements/autoComplete/code/CheckboxesCode'; +import SizesCode from 'src/components/forms/form-elements/autoComplete/code/SizesCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'AutoComplete', + }, +]; + +const MuiAutoComplete = () => ( + + {/* breadcrumb */} + + {/* end breadcrumb */} + + + + + }> + + + + + }> + + + + + }> + + + + + }> + + + + + }> + + + + + }> + + + + + }> + + + + + + +); +export default MuiAutoComplete; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiButton.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiButton.tsx new file mode 100644 index 0000000..9a05588 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiButton.tsx @@ -0,0 +1,337 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Grid from '@mui/material/Grid2'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ParentCard from 'src/components/shared/ParentCard'; +import ChildCard from 'src/components/shared/ChildCard'; + +import DefaultButtons from 'src/components/forms/form-elements/button/DefaultButtons'; +import ColorButtons from 'src/components/forms/form-elements/button/ColorButtons'; +import IconLoadingButtons from 'src/components/forms/form-elements/button/IconLoadingButtons'; +import SizeButton from 'src/components/forms/form-elements/button/SizeButton'; + +import OutlinedIconButtons from 'src/components/forms/form-elements/button/OutlinedIconButtons'; +import OutlinedSizeButton from 'src/components/forms/form-elements/button/OutlinedSizeButton'; + +import TextDefaultButtons from 'src/components/forms/form-elements/button/TextDefaultButtons'; +import TextColorButtons from 'src/components/forms/form-elements/button/TextColorButtons'; +import TextIconButtons from 'src/components/forms/form-elements/button/TextIconButtons'; +import TextSizeButton from 'src/components/forms/form-elements/button/TextSizeButton'; + +import IconColorButtons from 'src/components/forms/form-elements/button/IconColorButtons'; +import IconSizeButtons from 'src/components/forms/form-elements/button/IconSizeButtons'; + +import FabDefaultButton from 'src/components/forms/form-elements/button/FabDefaultButton'; +import FabColorButtons from 'src/components/forms/form-elements/button/FabColorButtons'; +import FabSizeButtons from 'src/components/forms/form-elements/button/FabSizeButtons'; + +import DefaultButtonGroup from 'src/components/forms/form-elements/button/DefaultButtonGroup'; +import SizeButtonGroup from 'src/components/forms/form-elements/button/SizeButtonGroup'; +import VerticalButtonGroup from 'src/components/forms/form-elements/button/VerticalButtonGroup'; +import ColorButtonGroup from 'src/components/forms/form-elements/button/ColorButtonGroup'; +import TextButtonGroup from 'src/components/forms/form-elements/button/TextButtonGroup'; +import OutlinedColorButtons from '../../../components/forms/form-elements/button/OutlinedColorButtons'; + +// codeModel +import DefaultCode from 'src/components/forms/form-elements/button/code/DefaultCode'; +import ColorsCode from 'src/components/forms/form-elements/button/code/ColorsCode'; +import LoadingButtonsCode from 'src/components/forms/form-elements/button/code/LoadingButtonsCode'; +import SizesCode from 'src/components/forms/form-elements/button/code/SizesCode'; +import OutlinedCode from 'src/components/forms/form-elements/button/code/OutlinedCode'; +import OutlinedIconCode from 'src/components/forms/form-elements/button/code/OutlinedIconCode'; +import OutlineSizeCode from 'src/components/forms/form-elements/button/code/OutlineSizeCode'; +import TextCode from 'src/components/forms/form-elements/button/code/TextCode'; +import TextColorCode from 'src/components/forms/form-elements/button/code/TextColorCode'; +import TextIconColor from 'src/components/forms/form-elements/button/code/TextIconColor'; +import TextSizesCode from 'src/components/forms/form-elements/button/code/TextSizesCode'; +import IconColorCode from 'src/components/forms/form-elements/button/code/IconColorCode'; +import IconSizesCode from 'src/components/forms/form-elements/button/code/IconSizesCode'; +import FABCode from 'src/components/forms/form-elements/button/code/FABCode'; +import FABColorCode from 'src/components/forms/form-elements/button/code/FABColorCode'; +import FABSizeCode from 'src/components/forms/form-elements/button/code/FABSizeCode'; +import DefaultButtonGroupCode from 'src/components/forms/form-elements/button/code/DefaultButtonGroupCode'; +import SizeButtonGroupCode from 'src/components/forms/form-elements/button/code/SizeButtonGroupCode'; +import VerticalButtonGroupCode from 'src/components/forms/form-elements/button/code/VerticalButtonGroupCode'; +import TextButtonGroupCode from 'src/components/forms/form-elements/button/code/TextButtonGroupCode'; +import ColorButtonGroupCode from 'src/components/forms/form-elements/button/code/ColorButtonGroupCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Button', + }, +]; + +const MuiButton = () => ( + + {/* breadcrumb */} + + {/* end breadcrumb */} + + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + + + + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + {/* ------------------------- row 1 ------------------------- */} + + }> + + + + + + + + +); +export default MuiButton; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiCheckbox.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiCheckbox.tsx new file mode 100644 index 0000000..f7f311e --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiCheckbox.tsx @@ -0,0 +1,141 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ParentCard from 'src/components/shared/ParentCard'; +import ChildCard from 'src/components/shared/ChildCard'; + +import Grid from '@mui/material/Grid2'; + +// custom components +import PositionCheckbox from "src/components/forms/form-elements/checkbox/Position"; +import SizesCheckbox from "src/components/forms/form-elements/checkbox/Sizes"; +import DefaultcolorsCheckbox from "src/components/forms/form-elements/checkbox/DefaultColors" +import CustomEleCheckbox from "src/components/forms/form-elements/checkbox/Custom"; +import DefaultCheckbox from "src/components/forms/form-elements/checkbox/Default"; +import ColorsCheckbox from "src/components/forms/form-elements/checkbox/Colors"; + +// codeModel +import CustomEleCheckboxCode from 'src/components/forms/form-elements/checkbox/code/CustomEleCheckboxCode'; +import ColorsCheckboxCode from 'src/components/forms/form-elements/checkbox/code/ColorsCheckboxCode'; +import DefaultCheckboxCode from 'src/components/forms/form-elements/checkbox/code/DefaultCheckboxCode'; +import DefaultcolorsCheckboxCode from 'src/components/forms/form-elements/checkbox/code/DefaultcolorsCheckboxCode'; +import SizesCheckboxCode from 'src/components/forms/form-elements/checkbox/code/SizesCheckboxCode'; +import PositionCheckboxCode from 'src/components/forms/form-elements/checkbox/code/PositionCheckboxCode'; +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Checkbox', + }, +]; + +const MuiCheckbox = () => { + + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + + + {/* ------------------------------------------------------------------- */} + {/* Custom */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Colors */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Default Checkbox */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Default with colors */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Sizes */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Position */} + {/* ------------------------------------------------------------------- */} + + }> + + + + + + ) + ); +}; + +export default MuiCheckbox; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiDateTime.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiDateTime.tsx new file mode 100644 index 0000000..d7a23d4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiDateTime.tsx @@ -0,0 +1,161 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import dayjs, { Dayjs } from 'dayjs'; +import Grid from '@mui/material/Grid2'; +import ParentCard from 'src/components/shared/ParentCard'; +import ChildCard from 'src/components/shared/ChildCard'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import { LocalizationProvider } from '@mui/x-date-pickers'; +import { AdapterDayjs } from '@mui/x-date-pickers/AdapterDayjs' +import { MobileDateTimePicker } from '@mui/x-date-pickers/MobileDateTimePicker'; +import { DateTimePicker } from '@mui/x-date-pickers/DateTimePicker'; +import { TimePicker } from '@mui/x-date-pickers/TimePicker'; +import { renderTimeViewClock } from '@mui/x-date-pickers/timeViewRenderers' + +// codeModel +import BasicDateTimeCode from 'src/components/forms/form-elements/date-time/code/BasicDateTimeCode'; +import DifferentDesignCode from 'src/components/forms/form-elements/date-time/code/DifferentDesignCode'; +import TimepickerCode from 'src/components/forms/form-elements/date-time/code/TimepickerCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Date Time', + }, +]; + +const MuiDateTime = () => { + const [value, setValue] = React.useState(null); + const [value2, setValue2] = React.useState(null); + + // date time + const [value3, setValue3] = React.useState(dayjs('2018-01-01T00:00:00.000Z')); + + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + + + {/* ------------------------------------------------------------------- */} + {/* Basic */} + {/* ------------------------------------------------------------------- */} + + }> + + { + setValue3(newValue); + }} + slotProps={{ + textField: { + fullWidth: true, + variant: 'outlined', + size: 'small', + inputProps: { 'aria-label': 'basic date picker' }, + }, + }} + value={value3} + /> + + + + {/* ------------------------------------------------------------------- */} + {/* Different */} + {/* ------------------------------------------------------------------- */} + + }> + + { + setValue(newValue) + }} + /> + + + + {/* ------------------------------------------------------------------- */} + {/* Timepicker */} + {/* ------------------------------------------------------------------- */} + + }> + + { + setValue2(newValue) + }} + viewRenderers={{ + hours: renderTimeViewClock, + minutes: renderTimeViewClock, + seconds: renderTimeViewClock, + }} + slotProps={{ + textField: { + size: 'small', + fullWidth: true, + sx: { + '& .MuiSvgIcon-root': { + width: '18px', + height: '18px', + }, + '& .MuiFormHelperText-root': { + display: 'none', + }, + }, + }, + }} + /> + + + + + + ) + ); +}; + +export default MuiDateTime; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiRadio.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiRadio.tsx new file mode 100644 index 0000000..6b5e29b --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiRadio.tsx @@ -0,0 +1,139 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Grid from '@mui/material/Grid2'; +import ParentCard from 'src/components/shared/ParentCard'; +import ChildCard from 'src/components/shared/ChildCard'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ColorLabelRadio from "src/components/forms/form-elements/radio/ColorLabel"; +import DefaultRadio from "src/components/forms/form-elements/radio/Default"; +import ColorsRadio from "src/components/forms/form-elements/radio/Colors"; +import SizesRadio from "src/components/forms/form-elements/radio/Sizes"; +import CustomExRadio from "src/components/forms/form-elements/radio/Custom"; +import PositionRadio from "src/components/forms/form-elements/radio/Position"; + +// codeModel +import CustomExRadioCode from 'src/components/forms/form-elements/radio/code/CustomExRadioCode'; +import ColorLabelRadioCode from 'src/components/forms/form-elements/radio/code/ColorLabelRadioCode'; +import DefaultRadioCode from 'src/components/forms/form-elements/radio/code/DefaultRadioCode'; +import ColorsRadioCode from 'src/components/forms/form-elements/radio/code/ColorsRadioCode'; +import SizesRadioCode from 'src/components/forms/form-elements/radio/code/SizesRadioCode'; +import PositionRadioCode from 'src/components/forms/form-elements/radio/code/PositionRadioCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Radio', + }, +]; + +const ExRadio = () => { + + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + + + {/* ------------------------------------------------------------------- */} + {/* Custom */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Color with label */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Default */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Default Colors */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Sizes */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Position */} + {/* ------------------------------------------------------------------- */} + + }> + + + + + + ) + ); +}; + +export default ExRadio; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiSlider.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiSlider.tsx new file mode 100644 index 0000000..cab3619 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiSlider.tsx @@ -0,0 +1,251 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import { Grid2 as Grid, Box, Slider, Typography, SliderThumb, SliderValueLabelProps, Stack } from '@mui/material'; +import ParentCard from 'src/components/shared/ParentCard'; +import ChildCard from 'src/components/shared/ChildCard'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import CustomRangeSlider from 'src/components/forms/theme-elements/CustomRangeSlider'; +import CustomSlider from 'src/components/forms/theme-elements/CustomSlider'; +import { IconVolume, IconVolume2 } from '@tabler/icons-react'; + +// codeModel +import CustomSliderCode from 'src/components/forms/form-elements/slider/code/CustomSliderCode'; +import VolumesliderCode from 'src/components/forms/form-elements/slider/code/VolumesliderCode'; +import RangesliderCode from 'src/components/forms/form-elements/slider/code/RangesliderCode'; +import DefaultsliderCode from 'src/components/forms/form-elements/slider/code/DefaultsliderCode'; +import DisabledSliderCode from 'src/components/forms/form-elements/slider/code/DisabledSliderCode'; +import DiscreteSliderCode from 'src/components/forms/form-elements/slider/code/DiscreteSliderCode'; +import TemperatureRangeCode from 'src/components/forms/form-elements/slider/code/TemperatureRangeCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Slider', + }, +]; + +const valuetext = (value: any) => `${value}°C`; + +function valuetext2(value: any) { + return `${value}°C`; +} + +function AirbnbThumbComponent(props: SliderValueLabelProps) { + const { children, ...other } = props; + + return ( + + {children} + + + + + ); +} + +const MuiSlider = () => { + const [value, setValue] = React.useState(30); + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const handleChange = (event: any, newValue: any) => { + setValue(newValue); + }; + const [value2, setValue2] = React.useState([20, 37]); + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const handleChange2 = (event2: any, newValue2: any) => { + setValue2(newValue2); + }; + + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + + + {/* ------------------------------------------------------------------- */} + {/* Custom */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Volume */} + {/* ------------------------------------------------------------------- */} + + }> + + + + + + + + + + + + + + {/* ------------------------------------------------------------------- */} + {/* Range */} + {/* ------------------------------------------------------------------- */} + + }> + (index === 0 ? 'Minimum price' : 'Maximum price')} + defaultValue={[20, 40]} + /> + + + {/* ------------------------------------------------------------------- */} + {/* Default */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Disabled */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Volume */} + {/* ------------------------------------------------------------------- */} + + + + + + + + + + {/* ------------------------------------------------------------------- */} + {/* Discrete */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Range Default */} + {/* ------------------------------------------------------------------- */} + + }> + 'Temperature range'} + value={value2} + onChange={handleChange2} + valueLabelDisplay="auto" + getAriaValueText={valuetext2} + /> + + + + + ) + ); +}; + +export default MuiSlider; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiSwitch.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiSwitch.tsx new file mode 100644 index 0000000..5e3605c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/form-elements/MuiSwitch.tsx @@ -0,0 +1,134 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import Grid from '@mui/material/Grid2'; +import ParentCard from 'src/components/shared/ParentCard'; +import ChildCard from 'src/components/shared/ChildCard'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import CustomExSwitch from 'src/components/forms/form-elements/switch/Custom'; +import DefaultSwitch from 'src/components/forms/form-elements/switch/Default'; +import DefaultLabelSwitch from 'src/components/forms/form-elements/switch/DefaultLabel'; +import SizesSwitch from 'src/components/forms/form-elements/switch/Sizes'; +import ColorsSwitch from 'src/components/forms/form-elements/switch/Colors'; +import PositionSwitch from 'src/components/forms/form-elements/switch/Position'; + +import CustomSwitchCode from 'src/components/forms/form-elements/switch/code/ColorsSwitchCode'; +import DefaultSwitchCode from 'src/components/forms/form-elements/switch/code/DefaultSwitchCode'; +import DefaultLabelSwitchCode from 'src/components/forms/form-elements/switch/code/DefaultLabelSwitchCode'; +import SizesSwitchCode from 'src/components/forms/form-elements/switch/code/SizesSwitchCode'; +import ColorsSwitchCode from 'src/components/forms/form-elements/switch/code/ColorsSwitchCode'; +import PositionSwitchCode from 'src/components/forms/form-elements/switch/code/PositionSwitchCode'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Switch', + }, +]; + +const MuiSwitch = () => ( + + {/* breadcrumb */} + + {/* end breadcrumb */} + + + {/* ------------------------------------------------------------------- */} + {/* Custom */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Default */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Default with label */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Sizes */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Default Colors */} + {/* ------------------------------------------------------------------- */} + + }> + + + + {/* ------------------------------------------------------------------- */} + {/* Placement */} + {/* ------------------------------------------------------------------- */} + + }> + + + + + + +); +export default MuiSwitch; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/from-tiptap/Tiptap.css b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/from-tiptap/Tiptap.css new file mode 100644 index 0000000..a440845 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/from-tiptap/Tiptap.css @@ -0,0 +1,3 @@ +.MuiTiptap-FieldContainer-root{ + min-height: 250px; + } diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/from-tiptap/TiptapEdit.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/from-tiptap/TiptapEdit.tsx new file mode 100644 index 0000000..22e1ba4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/from-tiptap/TiptapEdit.tsx @@ -0,0 +1,72 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; +import { useEditor } from "@tiptap/react"; +import StarterKit from "@tiptap/starter-kit"; +import { + MenuButtonBold, + MenuButtonItalic, + MenuControlsContainer, + MenuDivider, + MenuSelectHeading, + RichTextEditorProvider, + RichTextField, + MenuButtonStrikethrough, + MenuButtonOrderedList, + MenuButtonBulletedList, + MenuButtonBlockquote, + MenuButtonCode, + MenuButtonHorizontalRule, + MenuButtonUndo, + MenuButtonRedo, + MenuButtonRemoveFormatting, +} from "mui-tiptap"; +import './Tiptap.css'; + + +const TiptapEdit = () => { + + const editor = useEditor({ + extensions: [StarterKit], + content: "

Type here...

", + }); + + + + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + + } + + /> + + + ); +}; +export default TiptapEdit; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/from-tiptap/TiptapEditor.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/from-tiptap/TiptapEditor.tsx new file mode 100644 index 0000000..fc8b367 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/forms/from-tiptap/TiptapEditor.tsx @@ -0,0 +1,34 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React, { useState } from 'react'; + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import ParentCard from 'src/components/shared/ParentCard'; +import TiptapEdit from './TiptapEdit'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Tiptap Editor', + }, +]; + +const TiptapEditor = () => { + return ( + + {/* breadcrumb */} + + {/* end breadcrumb */} + + + + + ); +}; + +export default TiptapEditor; + diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-customization/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-customization/page.tsx new file mode 100644 index 0000000..292e33f --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-customization/page.tsx @@ -0,0 +1,33 @@ + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; + +import { Grid2 as Grid } from "@mui/material"; +import BasicCustomIcons from "src/components/muitrees/simpletree/BasicCustomIcons"; +import CustomTreeItemView from "src/components/muitrees/simpletree/CustomTreeItemView"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "SimpleTreeView ", + }, +]; + +const SimpleTreeView = () => { + return ( + + + + + + + + + + ); +}; + +export default SimpleTreeView; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-expansion/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-expansion/page.tsx new file mode 100644 index 0000000..a235577 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-expansion/page.tsx @@ -0,0 +1,36 @@ + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; + + +import { Grid2 as Grid } from "@mui/material"; +import ControlledExpansionTree from "src/components/muitrees/simpletree/ControlledExpansionTree"; +import ApiMethodSetItemExpansion from "src/components/muitrees/simpletree/ApiMethodSetItemExpansion"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "SimpleTreeView ", + }, +]; + +const SimpleTreeView = () => { + return ( + + + + + + + + + + + + ); +}; + +export default SimpleTreeView; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-focus/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-focus/page.tsx new file mode 100644 index 0000000..35d98ca --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-focus/page.tsx @@ -0,0 +1,31 @@ + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; + + +import { Grid2 as Grid } from "@mui/material"; +import ApiMethodFocusItem from "src/components/muitrees/simpletree/ApiMethodFocusItem"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "SimpleTreeView ", + }, +]; + +const SimpleTreeView = () => { + return ( + + + + + + + + ); +}; + +export default SimpleTreeView; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-items/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-items/page.tsx new file mode 100644 index 0000000..96692c5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-items/page.tsx @@ -0,0 +1,34 @@ + + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import { Grid2 as Grid } from "@mui/material"; +import BasicSimpleTreeView from "src/components/muitrees/simpletree/BasicSimpleTreeView"; +import TrackitemclicksTree from "src/components/muitrees/simpletree/TrackitemclicksTree"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "SimpleTreeView ", + }, +]; + +const SimpleTreeView = () => { + return ( + + + + + + + + + + + ); +}; + +export default SimpleTreeView; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-selection/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-selection/page.tsx new file mode 100644 index 0000000..40a1b84 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/mui-trees/simpletree/simpletree-selection/page.tsx @@ -0,0 +1,40 @@ + + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import { Grid2 as Grid } from "@mui/material"; +import MultiSelectTreeView from "src/components/muitrees/simpletree/MultiSelectTreeView"; +import CheckboxSelection from "src/components/muitrees/simpletree/CheckboxSelection"; +import ControlledSelectiontree from "src/components/muitrees/simpletree/ControlledSelectiontree"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "SimpleTreeView ", + }, +]; + +const SimpleTreeView = () => { + return ( + + + + + + + + + + + + + + + + ); +}; + +export default SimpleTreeView; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/barcharts/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/barcharts/page.tsx new file mode 100644 index 0000000..173fee5 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/barcharts/page.tsx @@ -0,0 +1,76 @@ + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; + +import TinyBarChart from 'src/components/muicharts/barcharts/SimpleBarChart' +import StackedBarChart from 'src/components/muicharts/barcharts/StackedBarChart' +import SimpleBarChart from "src/components/muicharts/barcharts/SimpleBarChart"; +import MixedBarChart from 'src/components/muicharts/barcharts/MixedBarChart' +import PositiveAndNegativeBarChart from "src/components/muicharts/barcharts/PositiveAndNegativeBarChart"; +import BarChartStackedBySignChart from "src/components/muicharts/barcharts/BarChartStackedBySignChart"; +import { Grid2 as Grid } from "@mui/material"; +import BiaxialBarChart from "src/components/muicharts/barcharts/BiaxialBarChart"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "Bar Charts", + }, +]; + +const BarChart = () => { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default BarChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/gaugecharts/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/gaugecharts/page.tsx new file mode 100644 index 0000000..4b37fad --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/gaugecharts/page.tsx @@ -0,0 +1,57 @@ +"use client" + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; + +import { Grid2 as Grid } from "@mui/material"; +import BasicGaugesChart from "src/components/muicharts/gaugecharts/BasicGaugesChart"; +import ArcDesignChart from "src/components/muicharts/gaugecharts/ArcDesignChart"; +import GaugePointerChart from "src/components/muicharts/gaugecharts/GaugePointerChart"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "GaugeCharts ", + }, +]; + +const GaugeCharts = () => { + return ( + + + + + + + + + + + + + + + + + + + + ); +}; + +export default GaugeCharts; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/linecharts/area/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/linecharts/area/page.tsx new file mode 100644 index 0000000..5e11ab4 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/linecharts/area/page.tsx @@ -0,0 +1,52 @@ + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import { Grid2 as Grid } from "@mui/material"; +import SimpleAreaChart from "src/components/muicharts/linescharts/areacharts/SimpleAreaChart"; +import StackedAreaChart from "src/components/muicharts/linescharts/areacharts/StackedAreaChart"; +import TinyAreaChart from "src/components/muicharts/linescharts/areacharts/TinyAreaChart"; +import PercentAreaChart from "src/components/muicharts/linescharts/areacharts/PercentAreaChart"; +import AreaChartConnectNulls from "src/components/muicharts/linescharts/areacharts/AreaChartConnectNullsChart"; +import AreaChartFillByValueChart from "src/components/muicharts/linescharts/areacharts/AreaChartFillByValueChart"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "Mui Area Charts", + }, +]; + +const AreaCharts = () => { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default AreaCharts; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/linecharts/line/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/linecharts/line/page.tsx new file mode 100644 index 0000000..e9bbe2a --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/linecharts/line/page.tsx @@ -0,0 +1,52 @@ + +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; + +import { Grid2 as Grid } from "@mui/material"; +import SimpleLineChart from "src/components/muicharts/linescharts/linechart/SimpleLineChart"; +import TinyLineChart from "src/components/muicharts/linescharts/linechart/TinyLineChart"; +import DashedLineChart from "src/components/muicharts/linescharts/linechart/DashedLineChart"; +import BiaxialLineChart from "src/components/muicharts/linescharts/linechart/BiaxialLineChart"; +import LineChartWithReferenceLines from "src/components/muicharts/linescharts/linechart/LineChartWithReferenceLinesChart"; +import LinewithforecastChart from "src/components/muicharts/linescharts/linechart/LinewithforecastChart"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "Mui Line Charts", + }, +]; + +const LineChart = () => { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default LineChart; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/piecharts/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/piecharts/page.tsx new file mode 100644 index 0000000..9ba5304 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/piecharts/page.tsx @@ -0,0 +1,107 @@ + +"use client" +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; + +import { Grid2 as Grid } from "@mui/material"; +import BasicPieChart from "src/components/muicharts/piecharts/BasicPieChart"; +import TwoLevelPieChart from "src/components/muicharts/piecharts/TwoLevelPieChart"; +import StraightAnglePieChart from "src/components/muicharts/piecharts/StraightAnglePieChart"; +import TwoSimplePieChart from "src/components/muicharts/piecharts/TwoSimplePieChart"; +import PieChartWithCustomizedLabel from "src/components/muicharts/piecharts/PieChartWithCustomizedLabel"; +import PieChartWithPaddingAngleChart from "src/components/muicharts/piecharts/PieChartWithPaddingAngleChart"; +import PieChartWithCenterLabelChart from "src/components/muicharts/piecharts/PieChartWithCenterLabelChart"; +import OnSeriesItemClickChart from "src/components/muicharts/piecharts/OnSeriesItemClickChart"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "PieCharts ", + }, +]; + +const PieCharts = () => { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default PieCharts; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/scattercharts/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/scattercharts/page.tsx new file mode 100644 index 0000000..5c71904 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/scattercharts/page.tsx @@ -0,0 +1,41 @@ +"use client" +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import { Grid2 as Grid } from "@mui/material"; +import BasicScatterChart from "src/components/muicharts/scattercharts/BasicScatterChart"; +import ScatterDatasetChart from "src/components/muicharts/scattercharts/ScatterDatasetChart"; +import VoronoiInteractionChart from "src/components/muicharts/scattercharts/VoronoiInteractionChart"; +import ScatterClickNoSnapChart from "src/components/muicharts/scattercharts/ScatterClickNoSnapChart"; + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "ScatterCharts ", + }, +]; + +const ScatterCharts = () => { + return ( + + + + + + + + + + + + + + + + + ); +}; + +export default ScatterCharts; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/sparklinecharts/page.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/sparklinecharts/page.tsx new file mode 100644 index 0000000..3bd04a3 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/muicharts/sparklinecharts/page.tsx @@ -0,0 +1,34 @@ +"use client" +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import PageContainer from 'src/components/container/PageContainer'; +import { Grid2 as Grid } from "@mui/material"; +import BasicSparkLine from "src/components/muicharts/sparklinecharts/BasicSparkLine"; +import AreaSparkLineChart from "src/components/muicharts/sparklinecharts/AreaSparkLineChart"; +import BasicSparkLineCustomizationChart from "src/components/muicharts/sparklinecharts/BasicSparkLineCustomizationChart"; + + +const BCrumb = [ + { + to: "/", + title: "Home", + }, + { + title: "SparkLineCharts ", + }, +]; + +const SparkLineCharts = () => { + return ( + + + + + + + + + + ); +}; + +export default SparkLineCharts; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/pages/account-setting/AccountSetting.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/pages/account-setting/AccountSetting.tsx new file mode 100644 index 0000000..044a091 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/pages/account-setting/AccountSetting.tsx @@ -0,0 +1,129 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import * as React from 'react'; +import PageContainer from 'src/components/container/PageContainer'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import { Grid2 as Grid, Tabs, Tab, Box, CardContent, Divider } from '@mui/material'; + +// components +import AccountTab from '../../../components/pages/account-setting/AccountTab'; +import { IconArticle, IconBell, IconLock, IconUserCircle } from '@tabler/icons-react'; +import BlankCard from '../../../components/shared/BlankCard'; +import NotificationTab from '../../../components/pages/account-setting/NotificationTab'; +import BillsTab from '../../../components/pages/account-setting/BillsTab'; +import SecurityTab from '../../../components/pages/account-setting/SecurityTab'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'Account Setting', + }, +]; + +interface TabPanelProps { + children?: React.ReactNode; + index: number; + value: number; +} + +function TabPanel(props: TabPanelProps) { + const { children, value, index, ...other } = props; + + return ( + + ); +} + +function a11yProps(index: number) { + return { + id: `simple-tab-${index}`, + 'aria-controls': `simple-tabpanel-${index}`, + }; +} + +const AccountSetting = () => { + const [value, setValue] = React.useState(0); + + // eslint-disable-next-line @typescript-eslint/ban-ts-comment + // @ts-ignore + const handleChange = (event: React.SyntheticEvent, newValue: number) => { + setValue(newValue); + }; + + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + + + + + + } + label="Account" + {...a11yProps(0)} + /> + + } + label="Notifications" + {...a11yProps(1)} + /> + } + label="Bills" + {...a11yProps(2)} + /> + } + label="Security" + {...a11yProps(3)} + /> + + + + + + + + + + + + + + + + + + + + + ) + ); +}; + +export default AccountSetting; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/pages/faq/Faq.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/pages/faq/Faq.tsx new file mode 100644 index 0000000..3b6c15c --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/pages/faq/Faq.tsx @@ -0,0 +1,37 @@ +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import React from 'react'; +import PageContainer from 'src/components/container/PageContainer'; +import Breadcrumb from 'src/layouts/full/shared/breadcrumb/Breadcrumb'; +import Grid from '@mui/material/Grid2'; + +import Questions from '../../../components/pages/faq/Questions'; +import StillQuestions from '../../../components/pages/faq/StillQuestions'; + +const BCrumb = [ + { + to: '/', + title: 'Home', + }, + { + title: 'FAQ', + }, +]; + +const Faq = () => { + return ( + ( + {/* breadcrumb */} + + {/* end breadcrumb */} + + + + + + + ) + ); +}; + +export default Faq; diff --git a/Modernize/Modernize/react-version/packages/typescript/main/src/views/pages/frontend-pages/About.tsx b/Modernize/Modernize/react-version/packages/typescript/main/src/views/pages/frontend-pages/About.tsx new file mode 100644 index 0000000..b9cca76 --- /dev/null +++ b/Modernize/Modernize/react-version/packages/typescript/main/src/views/pages/frontend-pages/About.tsx @@ -0,0 +1,32 @@ +import PageContainer from 'src/components/container/PageContainer'; +import HeaderAlert from '../../../components/frontend-pages/shared/header/HeaderAlert'; +import HpHeader from '../../../components/frontend-pages/shared/header/HpHeader'; +import Leadership from '../../../components/frontend-pages/shared/leadership'; +import Reviews from '../../../components/frontend-pages/shared/reviews'; +import Pricing from '../../../components/frontend-pages/shared/pricing'; +import C2a from '../../../components/frontend-pages/shared/c2a'; +import Footer from '../../../components/frontend-pages/shared/footer'; +import Banner from '../../../components/frontend-pages/about/banner'; +import Process from '../../../components/frontend-pages/about/process'; +import KeyMetric from '../../../components/frontend-pages/about/key-metric'; +import ScrollToTop from '../../../components/frontend-pages/shared/scroll-to-top'; + +const About = () => { + return ( + + + + + + + + + + +
+ ), + }); + }} + > + Error + + + + + {[ + 'top-left', + 'top-center', + 'top-right', + 'bottom-left', + 'bottom-center', + 'bottom-right', + ].map((position) => ( + + ))} + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/extra/upload-view/index.js b/front_minimal/src/sections/_examples/extra/upload-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/extra/upload-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/extra/upload-view/view.jsx b/front_minimal/src/sections/_examples/extra/upload-view/view.jsx new file mode 100644 index 0000000..0923250 --- /dev/null +++ b/front_minimal/src/sections/_examples/extra/upload-view/view.jsx @@ -0,0 +1,150 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Switch from '@mui/material/Switch'; +import Typography from '@mui/material/Typography'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { fData } from 'src/utils/format-number'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; +import { Upload, UploadBox, UploadAvatar } from 'src/components/upload'; + +import { ComponentHero } from '../../component-hero'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +export function UploadView() { + const preview = useBoolean(); + + const [files, setFiles] = useState([]); + + const [file, setFile] = useState(null); + + const [avatarUrl, setAvatarUrl] = useState(null); + + const handleDropSingleFile = useCallback((acceptedFiles) => { + const newFile = acceptedFiles[0]; + setFile(newFile); + }, []); + + const handleDropAvatar = useCallback((acceptedFiles) => { + const newFile = acceptedFiles[0]; + setAvatarUrl(newFile); + }, []); + + const handleDropMultiFile = useCallback( + (acceptedFiles) => { + setFiles([...files, ...acceptedFiles]); + }, + [files] + ); + + const handleRemoveFile = (inputFile) => { + const filesFiltered = files.filter((fileFiltered) => fileFiltered !== inputFile); + setFiles(filesFiltered); + }; + + const handleRemoveAllFiles = () => { + setFiles([]); + }; + + const DEMO = [ + { + name: 'Upload multi file', + component: ( + <> + } + label="Show Thumbnail" + sx={{ mb: 3, width: 1, justifyContent: 'flex-end' }} + /> + console.info('ON UPLOAD')} + /> + + ), + }, + { + name: 'Upload single file', + component: ( + setFile(null)} /> + ), + }, + { + name: 'Upload avatar', + component: ( + { + if (fileData.size > 1000000) { + return { code: 'file-too-large', message: `File is larger than ${fData(1000000)}` }; + } + return null; + }} + helperText={ + + Allowed *.jpeg, *.jpg, *.png, *.gif +
max size of {fData(3145728)} +
+ } + /> + ), + }, + { + name: 'Upload box', + component: ( + + + + + Upload file + + } + sx={{ mb: 3, py: 2.5, flexGrow: 1, height: 'auto' }} + /> + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/extra/utilities-view/copy-to-clipboard.jsx b/front_minimal/src/sections/_examples/extra/utilities-view/copy-to-clipboard.jsx new file mode 100644 index 0000000..c878302 --- /dev/null +++ b/front_minimal/src/sections/_examples/extra/utilities-view/copy-to-clipboard.jsx @@ -0,0 +1,80 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Tooltip from '@mui/material/Tooltip'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { useDoubleClick } from 'src/hooks/use-double-click'; +import { useCopyToClipboard } from 'src/hooks/use-copy-to-clipboard'; + +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; + +import { ComponentBlock, ComponentContainer } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function CopyToClipboard() { + const { copy } = useCopyToClipboard(); + + const [value, setValue] = useState('https://www.npmjs.com/package/'); + + const textOnClick = `Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia + Curae; Sed aliquam, nisi quis porttitor congue, elit erat euismod orci, ac placerat + dolor lectus quis orci. Cras non dolor. + `; + + const onCopy = useCallback( + (text) => { + if (text) { + toast.success('Copied!'); + copy(text); + } + }, + [copy] + ); + + const handleClick = useDoubleClick({ doubleClick: () => onCopy(textOnClick) }); + + const handleChange = useCallback((event) => { + setValue(event.target.value); + }, []); + + return ( + + + + + onCopy(value)}> + + + + + ), + }} + /> + + + + {textOnClick} + + + ); +} diff --git a/front_minimal/src/sections/_examples/extra/utilities-view/countdown.jsx b/front_minimal/src/sections/_examples/extra/utilities-view/countdown.jsx new file mode 100644 index 0000000..465761b --- /dev/null +++ b/front_minimal/src/sections/_examples/extra/utilities-view/countdown.jsx @@ -0,0 +1,64 @@ +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; + +import { useCountdownDate, useCountdownSeconds } from 'src/hooks/use-countdown'; + +import { ComponentBlock, ComponentContainer } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function Countdown() { + const countdownDate = useCountdownDate(new Date('08/08/2025 21:30')); + + const { countdown, startCountdown, counting } = useCountdownSeconds(30); + + return ( + + + +
+ {countdownDate.days} + days +
+
+ {countdownDate.hours} + hours +
+
+ {countdownDate.minutes} + minutes +
+
+ {countdownDate.seconds} + seconds +
+
+
+ + + + + + +
+ ); +} diff --git a/front_minimal/src/sections/_examples/extra/utilities-view/gradient.jsx b/front_minimal/src/sections/_examples/extra/utilities-view/gradient.jsx new file mode 100644 index 0000000..a6e3e8e --- /dev/null +++ b/front_minimal/src/sections/_examples/extra/utilities-view/gradient.jsx @@ -0,0 +1,51 @@ +import Box from '@mui/material/Box'; +import { useTheme } from '@mui/material/styles'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, bgGradient, textGradient } from 'src/theme/styles'; + +import { ComponentBlock, ComponentContainer } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function Gradient() { + const theme = useTheme(); + + return ( + + + + Minimals UI + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/extra/utilities-view/index.js b/front_minimal/src/sections/_examples/extra/utilities-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/extra/utilities-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/extra/utilities-view/text-max-line.jsx b/front_minimal/src/sections/_examples/extra/utilities-view/text-max-line.jsx new file mode 100644 index 0000000..f3638fb --- /dev/null +++ b/front_minimal/src/sections/_examples/extra/utilities-view/text-max-line.jsx @@ -0,0 +1,87 @@ +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { maxLine } from 'src/theme/styles'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const content = ` +Donec posuere vulputate arcu. Fusce vulputate eleifend sapien. Phasellus magna. Proin +sapien ipsum, porta a, auctor quis, euismod ut, mi. Suspendisse faucibus, nunc et +pellentesque egestas, lacus ante convallis tellus, vitae iaculis lacus elit id tortor. +`; + +// ---------------------------------------------------------------------- + +export function TextMaxLine() { + const theme = useTheme(); + + return ( + + + + {content} + + + + + {content} + + + + {content} + + + + {content} + + + + + {content} + + + + + + Donec posuere vulputate arcu. + + + + ); +} diff --git a/front_minimal/src/sections/_examples/extra/utilities-view/view.jsx b/front_minimal/src/sections/_examples/extra/utilities-view/view.jsx new file mode 100644 index 0000000..232d0b4 --- /dev/null +++ b/front_minimal/src/sections/_examples/extra/utilities-view/view.jsx @@ -0,0 +1,36 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { Gradient } from './gradient'; +import { Countdown } from './countdown'; +import { TextMaxLine } from './text-max-line'; +import { ComponentHero } from '../../component-hero'; +import { CopyToClipboard } from './copy-to-clipboard'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +export function UtilitiesView() { + const DEMO = [ + { name: 'Text max line', component: }, + { name: 'Copy to clipboard', component: }, + { name: 'Gradient', component: }, + { name: 'Countdown', component: }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/extra/walktour-view/index.js b/front_minimal/src/sections/_examples/extra/walktour-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/extra/walktour-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/extra/walktour-view/view.jsx b/front_minimal/src/sections/_examples/extra/walktour-view/view.jsx new file mode 100644 index 0000000..dcbd63c --- /dev/null +++ b/front_minimal/src/sections/_examples/extra/walktour-view/view.jsx @@ -0,0 +1,392 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Paper from '@mui/material/Paper'; +import Button from '@mui/material/Button'; +import Switch from '@mui/material/Switch'; +import { useTheme } from '@mui/material/styles'; +import Container from '@mui/material/Container'; +import Grid from '@mui/material/Unstable_Grid2'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { MotivationIllustration } from 'src/assets/illustrations'; +import { + _mock, + _ecommerceNewProducts, + _ecommerceBestSalesman, + _ecommerceSalesOverview, + _ecommerceLatestProducts, +} from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; +import { Walktour, useWalktour } from 'src/components/walktour'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { EcommerceWelcome } from 'src/sections/overview/e-commerce/ecommerce-welcome'; +import { EcommerceNewProducts } from 'src/sections/overview/e-commerce/ecommerce-new-products'; +import { EcommerceYearlySales } from 'src/sections/overview/e-commerce/ecommerce-yearly-sales'; +import { EcommerceBestSalesman } from 'src/sections/overview/e-commerce/ecommerce-best-salesman'; +import { EcommerceSaleByGender } from 'src/sections/overview/e-commerce/ecommerce-sale-by-gender'; +import { EcommerceSalesOverview } from 'src/sections/overview/e-commerce/ecommerce-sales-overview'; +import { EcommerceWidgetSummary } from 'src/sections/overview/e-commerce/ecommerce-widget-summary'; +import { EcommerceLatestProducts } from 'src/sections/overview/e-commerce/ecommerce-latest-products'; +import { EcommerceCurrentBalance } from 'src/sections/overview/e-commerce/ecommerce-current-balance'; + +import { ComponentHero } from '../../component-hero'; + +// ---------------------------------------------------------------------- + +export function WalktourView() { + const theme = useTheme(); + + const router = useRouter(); + + const walktour = useWalktour({ + defaultRun: true, + steps: [ + { + target: 'body', + title: `Let's begin our journey!`, + placement: 'center', + hideCloseButton: true, + content: ( + + Aenean posuere, tortor sed cursus feugiat, nunc augue blandit nunc, eu sollicitudin urna + dolor sagittis lacus. + + ), + }, + { + target: '#demo__2', + title: 'Step 2', + placement: 'left-start', + content: ( + <> + + Aenean posuere, tortor sed cursus feugiat, nunc augue blandit nunc, eu sollicitudin + urna dolor sagittis lacus. + + + + ), + }, + { + target: '#demo__3', + title: 'Step 3', + placement: 'bottom', + content: ( + <> + + Weekly magic on your inbox + + + Send + + ), + }} + /> + + ), + }, + { + target: '#demo__4', + title: 'Step 4', + placement: 'left', + content: ( + + + Aenean posuere, tortor sed cursus feugiat, nunc augue blandit nunc, eu sollicitudin + urna dolor sagittis lacus. + + + {[ + { label: 'Wi-Fi', icon: 'solar:home-wifi-bold-duotone', defaultChecked: true }, + { + label: 'Bluetooth', + icon: 'solar:bluetooth-square-bold-duotone', + defaultChecked: true, + }, + { label: 'Airbuds', icon: 'solar:airbuds-bold-duotone', defaultChecked: false }, + { label: 'Alarm', icon: 'solar:alarm-bold-duotone', defaultChecked: false }, + ].map((option) => ( + + + + {option.label} + + + + ))} + + + ), + }, + { + target: '#demo__5', + title: 'Step 5', + placement: 'left', + styles: { options: { arrowColor: theme.vars.palette.grey[800] } }, + slotProps: { + root: { + width: 480, + bgcolor: theme.vars.palette.grey[800], + color: theme.vars.palette.common.white, + }, + }, + content: ( + + + Aenean posuere, tortor sed cursus feugiat, nunc augue blandit nunc, eu sollicitudin + urna dolor sagittis lacus. + + + {[...Array(6)].map((_, index) => ( + + ))} + + + ), + }, + ], + }); + + return ( + <> + + + + + + + + + + + + + + } + action={ + + } + /> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/foundation/colors-view/index.js b/front_minimal/src/sections/_examples/foundation/colors-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/foundation/colors-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/foundation/colors-view/view.jsx b/front_minimal/src/sections/_examples/foundation/colors-view/view.jsx new file mode 100644 index 0000000..8920881 --- /dev/null +++ b/front_minimal/src/sections/_examples/foundation/colors-view/view.jsx @@ -0,0 +1,143 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import { useTheme, hexToRgb } from '@mui/material/styles'; + +import { paths } from 'src/routes/paths'; + +import { useCopyToClipboard } from 'src/hooks/use-copy-to-clipboard'; + +import { toast } from 'src/components/snackbar'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const PALETTE = ['primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const VARIATIONS = ['lighter', 'light', 'main', 'dark', 'darker']; + +const GREY = ['50', '100', '200', '300', '400', '500', '600', '700', '800', '900']; + +const boxProps = { + display: 'grid', + gridTemplateColumns: { xs: 'repeat(1, 1fr)', sm: 'repeat(2, 1fr)', md: 'repeat(3, 1fr)' }, +}; + +// ---------------------------------------------------------------------- + +export function ColorsView() { + const theme = useTheme(); + + const { copy } = useCopyToClipboard(); + + const onCopy = (color) => { + if (color) { + toast.success(`Copied: ${color}`); + copy(color); + } + }; + + const BASE = PALETTE.map((color) => ({ + name: color[0].toUpperCase() + color.substring(1), + component: ( + + {VARIATIONS.map((variation) => ( + onCopy(theme.palette[color][variation])} + /> + ))} + + ), + })); + + const DEMO = [ + ...BASE, + { + name: 'Grey', + component: ( + + {GREY.map((variation) => ( + onCopy(theme.palette.grey[variation])} + /> + ))} + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} + +// ---------------------------------------------------------------------- + +function ColorCard({ varColor, hexColor, variation, onCopy }) { + return ( + theme.palette.getContrastText(hexColor), + transition: (theme) => + theme.transitions.create(['opacity', 'background-color'], { + easing: theme.transitions.easing.sharp, + duration: theme.transitions.duration.shorter, + }), + '&:hover': { opacity: 0.8 }, + }} + > + + {variation} + + + + + Var + + {varColor} + + + + + Hex + + {hexColor} + + + + + Rgb + + {hexToRgb(hexColor).replace('rgb(', '').replace(')', '')} + + + ); +} diff --git a/front_minimal/src/sections/_examples/foundation/grid-view/index.js b/front_minimal/src/sections/_examples/foundation/grid-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/foundation/grid-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/foundation/grid-view/view.jsx b/front_minimal/src/sections/_examples/foundation/grid-view/view.jsx new file mode 100644 index 0000000..599e3b5 --- /dev/null +++ b/front_minimal/src/sections/_examples/foundation/grid-view/view.jsx @@ -0,0 +1,113 @@ +'use client'; + +import { useState } from 'react'; + +import Radio from '@mui/material/Radio'; +import Paper from '@mui/material/Paper'; +import Grid from '@mui/material/Unstable_Grid2'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; +import RadioGroup from '@mui/material/RadioGroup'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock, ComponentContainer } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const LABELS = ['1col', '2col', '3col', '4col', '6col', '12col']; + +// ---------------------------------------------------------------------- + +export function GridView() { + const theme = useTheme(); + + const [spacing, setSpacing] = useState(2); + + const [column, setColumn] = useState(3); + + const handleChangeSpacing = (event) => { + setSpacing(Number(event.target.value)); + }; + + const handleChangeColumn = (event) => { + setColumn(Number(event.target.value)); + }; + + return ( + <> + + + + + + + + Spacing: {theme.spacing(Number(spacing))} + + + + {[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11].map((value) => ( + + + + ))} + + + + {[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10].map((value) => ( + } + /> + ))} + + + + + + {[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11].map((value) => ( + + + xs = {column} + + + ))} + + + + {[12, 6, 4, 3, 2, 1].map((value, index) => ( + } + /> + ))} + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/foundation/icons-view/index.js b/front_minimal/src/sections/_examples/foundation/icons-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/foundation/icons-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/foundation/icons-view/view.jsx b/front_minimal/src/sections/_examples/foundation/icons-view/view.jsx new file mode 100644 index 0000000..1d0fdbd --- /dev/null +++ b/front_minimal/src/sections/_examples/foundation/icons-view/view.jsx @@ -0,0 +1,124 @@ +'use client'; + +import Link from '@mui/material/Link'; +import Tooltip from '@mui/material/Tooltip'; + +import { paths } from 'src/routes/paths'; + +import { CONFIG } from 'src/config-global'; +import { countries } from 'src/assets/data'; + +import { SvgColor } from 'src/components/svg-color'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; +import { Iconify, FlagIcon, SocialIcon } from 'src/components/iconify'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock, ComponentContainer } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function IconsView() { + return ( + <> + + + + + + + + https://mui.com/components/icons/#main-content + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + {countries.map((country) => + country.label ? ( + + + + ) : null + )} + + + + ); +} diff --git a/front_minimal/src/sections/_examples/foundation/shadows-view/index.js b/front_minimal/src/sections/_examples/foundation/shadows-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/foundation/shadows-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/foundation/shadows-view/view.jsx b/front_minimal/src/sections/_examples/foundation/shadows-view/view.jsx new file mode 100644 index 0000000..2055b2e --- /dev/null +++ b/front_minimal/src/sections/_examples/foundation/shadows-view/view.jsx @@ -0,0 +1,118 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Paper from '@mui/material/Paper'; +import { useTheme } from '@mui/material/styles'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const boxProps = { + gap: 3, + display: 'grid', + gridTemplateColumns: { xs: 'repeat(2, 1fr)', md: 'repeat(3, 1fr)' }, +}; + +// ---------------------------------------------------------------------- + +export function ShadowsView() { + const theme = useTheme(); + + const SYSTEM = theme.shadows.slice(1, theme.shadows.length); + + const CUSTOMS = [ + ['z1', theme.customShadows.z1], + ['z4', theme.customShadows.z4], + ['z8', theme.customShadows.z8], + ['z12', theme.customShadows.z12], + ['z16', theme.customShadows.z16], + ['z20', theme.customShadows.z20], + ['z24', theme.customShadows.z24], + ['card', theme.customShadows.card], + ['dropdown', theme.customShadows.dropdown], + ['dialog', theme.customShadows.dialog], + ]; + + const COLORS = ['primary', 'secondary', 'info', 'success', 'warning', 'error']; + + const DEMO = [ + { + name: 'System', + component: ( + + {SYSTEM.map((shadow, index) => ( + + ))} + + ), + }, + { + name: 'Customs', + component: ( + + {CUSTOMS.map((shadow) => ( + + ))} + + ), + }, + { + name: 'Colors', + component: ( + + {COLORS.map((color) => ( + + ))} + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} + +// ---------------------------------------------------------------------- + +function ShadowCard({ sx, title }) { + return ( + + {title} + + ); +} diff --git a/front_minimal/src/sections/_examples/foundation/typography-view/index.js b/front_minimal/src/sections/_examples/foundation/typography-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/foundation/typography-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/foundation/typography-view/view.jsx b/front_minimal/src/sections/_examples/foundation/typography-view/view.jsx new file mode 100644 index 0000000..5d77869 --- /dev/null +++ b/front_minimal/src/sections/_examples/foundation/typography-view/view.jsx @@ -0,0 +1,153 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Paper from '@mui/material/Paper'; +import Stack from '@mui/material/Stack'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +import { remToPx } from 'src/theme/styles'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const VARIANTS = [ + 'h1', + 'h2', + 'h3', + 'h4', + 'h5', + 'h6', + 'subtitle1', + 'subtitle2', + 'body1', + 'body2', + 'caption', + 'overline', + 'button', +]; + +const BASE = VARIANTS.map((variant) => ({ + name: variant[0].toUpperCase() + variant.substring(1), + component: , +})); + +// ---------------------------------------------------------------------- + +export function TypographyView() { + const DEMO = [ + ...BASE, + { + name: 'Colors', + component: ( + + {['primary', 'secondary', 'disabled'].map((color) => ( + + + text {color} + + + Cras ultricies mi eu turpis hendrerit fringilla. Fusce vel dui. Pellentesque auctor + neque nec urna. Sed cursus turpis vitae tortor. Curabitur suscipit suscipit tellus. + + + ))} + + {['primary', 'secondary', 'info', 'warning', 'error'].map((color) => ( + + + {color} + + + Cras ultricies mi eu turpis hendrerit fringilla. Fusce vel dui. Pellentesque auctor + neque nec urna. Sed cursus turpis vitae tortor. Curabitur suscipit suscipit tellus. + + + ))} + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} + +function BlockVariant({ variant }) { + const theme = useTheme(); + + const upSm = useResponsive('up', 'sm'); + + const upMd = useResponsive('up', 'md'); + + const upLg = useResponsive('up', 'lg'); + + const fontProperties = theme.typography[variant]; + + const keysStartWith = (obj) => Object.keys(obj).some((key) => key.startsWith('@media')); + + const hasMedia = keysStartWith(fontProperties); + + let { fontSize } = fontProperties; + + if (hasMedia) { + if (upSm) { + fontSize = fontProperties[theme.breakpoints.up('sm')]?.fontSize; + } + if (upMd) { + fontSize = fontProperties[theme.breakpoints.up('md')]?.fontSize; + } + if (upLg) { + fontSize = fontProperties[theme.breakpoints.up('lg')]?.fontSize; + } + } + + return ( + + How can you choose a typeface? + + + fontSize: {`${remToPx(fontSize)}px`} + + lineHeight: {Number(fontProperties.lineHeight).toFixed(2)} + + fontWeight: {fontProperties.fontWeight} + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/accordion-view/index.js b/front_minimal/src/sections/_examples/mui/accordion-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/accordion-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/accordion-view/view.jsx b/front_minimal/src/sections/_examples/mui/accordion-view/view.jsx new file mode 100644 index 0000000..ab886af --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/accordion-view/view.jsx @@ -0,0 +1,102 @@ +'use client'; + +import { useState } from 'react'; + +import Accordion from '@mui/material/Accordion'; +import Typography from '@mui/material/Typography'; +import AccordionSummary from '@mui/material/AccordionSummary'; +import AccordionDetails from '@mui/material/AccordionDetails'; + +import { paths } from 'src/routes/paths'; + +import { _mock } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const _accordions = [...Array(4)].map((_, index) => ({ + id: _mock.id(index), + value: `panel${index + 1}`, + heading: `Accordion ${index + 1}`, + subHeading: _mock.postTitle(index), + detail: _mock.description(index), +})); + +// ---------------------------------------------------------------------- + +export function AccordionView() { + const [controlled, setControlled] = useState(false); + + const handleChangeControlled = (panel) => (event, isExpanded) => { + setControlled(isExpanded ? panel : false); + }; + + const DEMO = [ + { + name: 'Simple', + component: ( + +
+ {_accordions.map((accordion, index) => ( + + }> + {accordion.heading} + + + {accordion.detail} + + + ))} +
+
+ ), + }, + { + name: 'Controlled', + component: ( + +
+ {_accordions.map((item, index) => ( + + }> + + {item.heading} + + {item.subHeading} + + + {item.detail} + + + ))} +
+
+ ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/alert-view/index.js b/front_minimal/src/sections/_examples/mui/alert-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/alert-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/alert-view/view.jsx b/front_minimal/src/sections/_examples/mui/alert-view/view.jsx new file mode 100644 index 0000000..80ac355 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/alert-view/view.jsx @@ -0,0 +1,149 @@ +'use client'; + +import Alert from '@mui/material/Alert'; +import Button from '@mui/material/Button'; +import AlertTitle from '@mui/material/AlertTitle'; + +import { paths } from 'src/routes/paths'; + +import { varAlpha } from 'src/theme/styles'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const COLORS = ['info', 'success', 'warning', 'error']; + +// ---------------------------------------------------------------------- + +export function AlertView() { + const DEMO = [ + { + name: 'Standard', + component: ( + + {COLORS.map((color) => ( + {}}> + This is an {color} alert — check it out! + + ))} + + ), + }, + { + name: 'Filled', + component: ( + + {COLORS.map((color) => ( + {}}> + This is an {color} alert — check it out! + + ))} + + ), + }, + { + name: 'Outlined', + component: ( + + {COLORS.map((color) => ( + {}}> + This is an {color} alert — check it out! + + ))} + + ), + }, + { + name: 'Description', + component: ( + + {COLORS.map((color) => ( + {}}> + {color} + This is an {color} alert — check it out! + + ))} + + ), + }, + { + name: 'Actions', + component: ( + + + Action + + } + > + This is an info alert — check it out! + + + + + + + } + > + This is an info alert — check it out! + + + + + + + } + > + This is an info alert — check it out! + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/autocomplete-view/index.js b/front_minimal/src/sections/_examples/mui/autocomplete-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/autocomplete-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/autocomplete-view/view.jsx b/front_minimal/src/sections/_examples/mui/autocomplete-view/view.jsx new file mode 100644 index 0000000..d11b0f6 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/autocomplete-view/view.jsx @@ -0,0 +1,466 @@ +'use client'; + +import { useState } from 'react'; + +import Chip from '@mui/material/Chip'; +import Stack from '@mui/material/Stack'; +import Checkbox from '@mui/material/Checkbox'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import Autocomplete from '@mui/material/Autocomplete'; + +import { paths } from 'src/routes/paths'; + +import { CountrySelect } from 'src/components/country-select'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock, ComponentContainer } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const options = ['Option 1', 'Option 2']; + +export function AutocompleteView() { + const [inputValue, setInputValue] = useState(''); + + const [value, setValue] = useState(options[0]); + + const [singleLabel, setSingleLabel] = useState('Armenia'); + + const [singleCode, setSingleCode] = useState('AR'); + + const [multiLabel, setMultiLabel] = useState(['Austria', 'Australia', 'Bulgaria']); + + const [multiCode, setMultiCode] = useState(['BJ', 'BL', 'BM']); + + return ( + <> + + + + + + + option.title} + renderInput={(params) => } + renderOption={(props, option) => ( +
  • + {option.title} +
  • + )} + /> +
    + + + { + setValue(newValue); + }} + inputValue={inputValue} + onInputChange={(event, newInputValue) => { + setInputValue(newInputValue); + }} + getOptionLabel={(option) => option} + renderInput={(params) => } + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + /> + + {`value: ${ + value !== null ? `'${value}'` : 'null' + }`} + + {`inputValue: '${inputValue}'`} +
    + + + option.title)} + getOptionLabel={(option) => option} + renderInput={(params) => } + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + /> + + option.title)} + getOptionLabel={(option) => option} + renderInput={(params) => ( + + )} + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + /> +
    + + + option.title} + defaultValue={top100Films.slice(0, 8)} + renderInput={(params) => ( + + )} + renderOption={(props, option) => ( +
  • + {option.title} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + /> +
    + + + option.title} + defaultValue={top100Films.slice(0, 1)} + renderInput={(params) => ( + + )} + renderOption={(props, option, { selected }) => ( +
  • + + {option.title} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + /> +
    + + + option.title} + defaultValue={top100Films[13]} + renderInput={(params) => ( + + )} + renderOption={(props, option) => ( +
  • + {option.title} +
  • + )} + /> + + option.title} + defaultValue={[top100Films[13]]} + renderInput={(params) => ( + + )} + renderOption={(props, option) => ( +
  • + {option.title} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + /> +
    + + + + setSingleLabel(newValue)} + /> + + Output: + + {singleLabel ?? '-'} + + + + + + setSingleCode(newValue)} + /> + + Output: + + {singleCode ?? '-'} + + + + + + setMultiLabel(newValue)} + /> + + Output:{' '} + + {multiLabel.join(', ') ?? '-'} + + + + + + setMultiCode(newValue)} + /> + + Output:{' '} + + {multiCode.join(', ') ?? '-'} + + + + +
    + + ); +} + +// ---------------------------------------------------------------------- + +const top100Films = [ + { title: 'The Shawshank Redemption', year: 1994 }, + { title: 'The Godfather', year: 1972 }, + { title: 'The Godfather: Part II', year: 1974 }, + { title: 'The Dark Knight', year: 2008 }, + { title: '12 Angry Men', year: 1957 }, + { title: "Schindler's List", year: 1993 }, + { title: 'Pulp Fiction', year: 1994 }, + { title: 'The Lord of the Rings: The Return of the King', year: 2003 }, + { title: 'The Good, the Bad and the Ugly', year: 1966 }, + { title: 'Fight Club', year: 1999 }, + { title: 'The Lord of the Rings: The Fellowship of the Ring', year: 2001 }, + { title: 'Star Wars: Episode V - The Empire Strikes Back', year: 1980 }, + { title: 'Forrest Gump', year: 1994 }, + { title: 'Inception', year: 2010 }, + { title: 'The Lord of the Rings: The Two Towers', year: 2002 }, + { title: "One Flew Over the Cuckoo's Nest", year: 1975 }, + { title: 'Goodfellas', year: 1990 }, + { title: 'The Matrix', year: 1999 }, + { title: 'Seven Samurai', year: 1954 }, + { title: 'Star Wars: Episode IV - A New Hope', year: 1977 }, + { title: 'City of God', year: 2002 }, + { title: 'Se7en', year: 1995 }, + { title: 'The Silence of the Lambs', year: 1991 }, + { title: "It's a Wonderful Life", year: 1946 }, + { title: 'Life Is Beautiful', year: 1997 }, + { title: 'The Usual Suspects', year: 1995 }, + { title: 'Léon: The Professional', year: 1994 }, + { title: 'Spirited Away', year: 2001 }, + { title: 'Saving Private Ryan', year: 1998 }, + { title: 'Once Upon a Time in the West', year: 1968 }, + { title: 'American History X', year: 1998 }, + { title: 'Interstellar', year: 2014 }, + { title: 'Casablanca', year: 1942 }, + { title: 'City Lights', year: 1931 }, + { title: 'Psycho', year: 1960 }, + { title: 'The Green Mile', year: 1999 }, + { title: 'The Intouchables', year: 2011 }, + { title: 'Modern Times', year: 1936 }, + { title: 'Raiders of the Lost Ark', year: 1981 }, + { title: 'Rear Window', year: 1954 }, + { title: 'The Pianist', year: 2002 }, + { title: 'The Departed', year: 2006 }, + { title: 'Terminator 2: Judgment Day', year: 1991 }, + { title: 'Back to the Future', year: 1985 }, + { title: 'Whiplash', year: 2014 }, + { title: 'Gladiator', year: 2000 }, + { title: 'Memento', year: 2000 }, + { title: 'The Prestige', year: 2006 }, + { title: 'The Lion King', year: 1994 }, + { title: 'Apocalypse Now', year: 1979 }, + { title: 'Alien', year: 1979 }, + { title: 'Sunset Boulevard', year: 1950 }, + { + title: 'Dr. Strangelove or: How I Learned to Stop Worrying and Love the Bomb', + year: 1964, + }, + { title: 'The Great Dictator', year: 1940 }, + { title: 'Cinema Paradiso', year: 1988 }, + { title: 'The Lives of Others', year: 2006 }, + { title: 'Grave of the Fireflies', year: 1988 }, + { title: 'Paths of Glory', year: 1957 }, + { title: 'Django Unchained', year: 2012 }, + { title: 'The Shining', year: 1980 }, + { title: 'WALL·E', year: 2008 }, + { title: 'American Beauty', year: 1999 }, + { title: 'The Dark Knight Rises', year: 2012 }, + { title: 'Princess Mononoke', year: 1997 }, + { title: 'Aliens', year: 1986 }, + { title: 'Oldboy', year: 2003 }, + { title: 'Once Upon a Time in America', year: 1984 }, + { title: 'Witness for the Prosecution', year: 1957 }, + { title: 'Das Boot', year: 1981 }, + { title: 'Citizen Kane', year: 1941 }, + { title: 'North by Northwest', year: 1959 }, + { title: 'Vertigo', year: 1958 }, + { title: 'Star Wars: Episode VI - Return of the Jedi', year: 1983 }, + { title: 'Reservoir Dogs', year: 1992 }, + { title: 'Braveheart', year: 1995 }, + { title: 'M', year: 1931 }, + { title: 'Requiem for a Dream', year: 2000 }, + { title: 'Amélie', year: 2001 }, + { title: 'A Clockwork Orange', year: 1971 }, + { title: 'Like Stars on Earth', year: 2007 }, + { title: 'Taxi Driver', year: 1976 }, + { title: 'Lawrence of Arabia', year: 1962 }, + { title: 'Double Indemnity', year: 1944 }, + { title: 'Eternal Sunshine of the Spotless Mind', year: 2004 }, + { title: 'Amadeus', year: 1984 }, + { title: 'To Kill a Mockingbird', year: 1962 }, + { title: 'Toy Story 3', year: 2010 }, + { title: 'Logan', year: 2017 }, + { title: 'Full Metal Jacket', year: 1987 }, + { title: 'Dangal', year: 2016 }, + { title: 'The Sting', year: 1973 }, + { title: '2001: A Space Odyssey', year: 1968 }, + { title: "Singin' in the Rain", year: 1952 }, + { title: 'Toy Story', year: 1995 }, + { title: 'Bicycle Thieves', year: 1948 }, + { title: 'The Kid', year: 1921 }, + { title: 'Inglourious Basterds', year: 2009 }, + { title: 'Snatch', year: 2000 }, + { title: '3 Idiots', year: 2009 }, + { title: 'Monty Python and the Holy Grail', year: 1975 }, +]; diff --git a/front_minimal/src/sections/_examples/mui/avatar-view/index.js b/front_minimal/src/sections/_examples/mui/avatar-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/avatar-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/avatar-view/view.jsx b/front_minimal/src/sections/_examples/mui/avatar-view/view.jsx new file mode 100644 index 0000000..e863d05 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/avatar-view/view.jsx @@ -0,0 +1,197 @@ +'use client'; + +import Badge from '@mui/material/Badge'; +import Avatar from '@mui/material/Avatar'; +import Tooltip from '@mui/material/Tooltip'; +import { useTheme } from '@mui/material/styles'; +import AvatarGroup, { avatarGroupClasses } from '@mui/material/AvatarGroup'; + +import { paths } from 'src/routes/paths'; + +import { _mock } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const COLORS = ['default', 'primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const SIZES = [24, 32, 40, 56]; + +const VARIANTS = ['circular', 'rounded', 'square']; + +const STATUS = ['online', 'alway', 'busy', 'offline']; + +// ---------------------------------------------------------------------- + +export function AvatarView() { + const theme = useTheme(); + + const DEMO = [ + { + name: 'Image', + component: ( + + {[1, 2, 3, 4, 5].map((_, index) => ( + + ))} + + ), + }, + { + name: 'Letter', + component: ( + + {COLORS.map((color, index) => ( + + + {_mock + .fullName(index + 3) + .charAt(0) + .toUpperCase()} + + + ))} + + ), + }, + { + name: 'Icon', + component: ( + + {COLORS.map((color) => ( + + + + ))} + + ), + }, + { + name: 'Variant', + component: ( + + {VARIANTS.map((variant) => ( + + + + ))} + + ), + }, + { + name: 'Grouped', + component: ( + + {SIZES.map((size) => ( + + + {COLORS.map((color, index) => ( + + ))} + + + ))} + + + + + {COLORS.slice(0, 2).map((color, index) => ( + + ))} + + + + + ), + }, + { + name: 'With badge', + component: ( + + + } + > + + + + {STATUS.map((status, index) => ( + + + + ))} + + ), + }, + { + name: 'Sizes', + component: ( + + {[24, 32, 48, 56, 64, 80, 128].map((size, index) => ( + + ))} + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/badge-view/index.js b/front_minimal/src/sections/_examples/mui/badge-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/badge-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/badge-view/view.jsx b/front_minimal/src/sections/_examples/mui/badge-view/view.jsx new file mode 100644 index 0000000..c3ea701 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/badge-view/view.jsx @@ -0,0 +1,145 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Badge from '@mui/material/Badge'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const COLORS = ['default', 'primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const STATUS = ['alway', 'online', 'busy', 'offline']; + +// ---------------------------------------------------------------------- + +export function BadgeView() { + const DEMO = [ + { + name: 'Basic', + component: ( + + {COLORS.map((color) => ( + + + + ))} + + ), + }, + { + name: 'Maximum value', + component: ( + + } + /> + } + /> + } + /> + + ), + }, + { + name: 'Dot badge', + component: ( + + + + + + Typography + + + ), + }, + { + name: 'Badge overlap', + component: ( + + + + + + + + + + + + + + + ), + }, + { + name: 'Status', + component: ( + + {STATUS.map((status) => ( + + + + ))} + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/breadcrumbs-view/index.js b/front_minimal/src/sections/_examples/mui/breadcrumbs-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/breadcrumbs-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/breadcrumbs-view/view.jsx b/front_minimal/src/sections/_examples/mui/breadcrumbs-view/view.jsx new file mode 100644 index 0000000..cdafae0 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/breadcrumbs-view/view.jsx @@ -0,0 +1,118 @@ +'use client'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Typography from '@mui/material/Typography'; +import Breadcrumbs from '@mui/material/Breadcrumbs'; + +import { paths } from 'src/routes/paths'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +export function BreadcrumbsView() { + const DEMO = [ + { + name: 'Text', + component: ( + + + + Material-UI + + + Core + + Breadcrumb + + + ), + }, + { + name: 'With icon', + component: ( + + + + + Material-UI + + + + Core + + + + Breadcrumb + + + + ), + }, + { + name: 'Customized', + component: ( + + + , + }, + { name: 'Link1', href: '#', icon: }, + { name: 'Link2', href: '#', icon: }, + { name: 'Link3', icon: }, + ]} + /> + + + + , + }, + { name: 'Link1', href: '#', icon: }, + { name: 'Link2', href: '#', icon: }, + { name: 'Link3', icon: }, + ]} + action={ + + } + /> + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/button-view/button-groups.jsx b/front_minimal/src/sections/_examples/mui/button-view/button-groups.jsx new file mode 100644 index 0000000..a3ff8e1 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/button-view/button-groups.jsx @@ -0,0 +1,115 @@ +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import ButtonGroup from '@mui/material/ButtonGroup'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const COLORS = ['inherit', 'primary', 'secondary', 'success', 'error', 'info', 'warning']; + +const SIZES = ['small', 'medium', 'large']; + +const VARIANTS = ['contained', 'outlined', 'text', 'soft']; + +// ---------------------------------------------------------------------- + +export function ButtonGroups() { + return ( + + + {COLORS.map((color) => ( + + + + + + ))} + + + + + + + + + + {COLORS.map((color) => ( + + + + + + ))} + + + + + + + + + + {COLORS.map((color) => ( + + + + + + ))} + + + + + + + + + + {COLORS.map((color) => ( + + + + + + ))} + + + + + + + + + + {SIZES.map((size) => ( + + + + + + ))} + + + + {VARIANTS.map((variant) => ( + + + + + + ))} + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/button-view/button-variants.jsx b/front_minimal/src/sections/_examples/mui/button-view/button-variants.jsx new file mode 100644 index 0000000..a32edec --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/button-view/button-variants.jsx @@ -0,0 +1,129 @@ +import Stack from '@mui/material/Stack'; +import LoadingButton from '@mui/lab/LoadingButton'; +import Button, { buttonClasses } from '@mui/material/Button'; + +import { Iconify } from 'src/components/iconify'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const COLORS = ['inherit', 'primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const SIZES = ['small', 'medium', 'large']; + +// ---------------------------------------------------------------------- + +export function ButtonVariants({ variant = 'text' }) { + return ( + + + + + + + + + + + {COLORS.map((color) => ( + + ))} + + + + + + + + + Submit + + + + Fetch data + + + } + variant={variant} + > + Start + + + } + variant={variant} + > + End + + + + + {SIZES.map((size) => ( + + ))} + + {SIZES.map((size) => ( + } + variant={variant} + > + {size} + + ))} + + {SIZES.map((size) => ( + } + variant={variant} + > + {size} + + ))} + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/button-view/floating-action-button.jsx b/front_minimal/src/sections/_examples/mui/button-view/floating-action-button.jsx new file mode 100644 index 0000000..84745d2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/button-view/floating-action-button.jsx @@ -0,0 +1,172 @@ +import { m } from 'framer-motion'; + +import Stack from '@mui/material/Stack'; +import Fab, { fabClasses } from '@mui/material/Fab'; + +import { Iconify } from 'src/components/iconify'; +import { varHover } from 'src/components/animate'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const COLORS = [ + 'default', + 'inherit', + 'primary', + 'secondary', + 'info', + 'success', + 'warning', + 'error', +]; + +const SIZES = ['small', 'medium', 'large']; + +// ---------------------------------------------------------------------- + +export function FloatingActionButton() { + return ( + + + {COLORS.map((color) => ( + + + + ))} + + {COLORS.map((color) => ( + + + {color} + + ))} + + + + + + + disabled + + + + + {COLORS.map((color) => ( + + + + ))} + + {COLORS.map((color) => ( + + + {color} + + ))} + + + + + + + + disabled + + + + + {COLORS.map((color) => ( + + + + ))} + + {COLORS.map((color) => ( + + + {color} + + ))} + + + + + + + + disabled + + + + + {SIZES.map((size) => ( + + + + ))} + + {SIZES.map((size) => ( + + + {size} + + ))} + + {SIZES.map((size) => ( + + + + ))} + + {SIZES.map((size) => ( + + + {size} + + ))} + + {SIZES.map((size) => ( + + + + ))} + + {SIZES.map((size) => ( + + + {size} + + ))} + + + + {SIZES.map((size) => ( + + + {size} + + ))} + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/button-view/icon-buttons.jsx b/front_minimal/src/sections/_examples/mui/button-view/icon-buttons.jsx new file mode 100644 index 0000000..505e1b7 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/button-view/icon-buttons.jsx @@ -0,0 +1,95 @@ +import { m } from 'framer-motion'; + +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; + +import { Iconify } from 'src/components/iconify'; +import { varHover } from 'src/components/animate'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const COLORS = [ + 'inherit', + 'default', + 'primary', + 'secondary', + 'info', + 'success', + 'warning', + 'error', +]; + +const SIZES = ['small', 'medium', 'large']; + +// ---------------------------------------------------------------------- + +export function IconButtons() { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + {COLORS.map((color) => ( + + + + ))} + + + + {SIZES.map((size) => ( + + + + ))} + + + + {SIZES.map((size) => ( + + + + ))} + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/button-view/index.js b/front_minimal/src/sections/_examples/mui/button-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/button-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/button-view/toggle-buttons.jsx b/front_minimal/src/sections/_examples/mui/button-view/toggle-buttons.jsx new file mode 100644 index 0000000..3a0f4d6 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/button-view/toggle-buttons.jsx @@ -0,0 +1,188 @@ +import { useState } from 'react'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import ToggleButton from '@mui/material/ToggleButton'; +import ToggleButtonGroup from '@mui/material/ToggleButtonGroup'; + +import { Iconify } from 'src/components/iconify'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const COLORS = ['standard', 'primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const SIZES = ['small', 'medium', 'large']; + +// ---------------------------------------------------------------------- + +export function ToggleButtons() { + const [alignment, setAlignment] = useState('left'); + + const [formats, setFormats] = useState(() => ['bold', 'italic']); + + const [view, setView] = useState('list'); + + const [selected, setSelected] = useState(true); + + const handleAlignment = (event, newAlignment) => { + setAlignment(newAlignment); + }; + + const handleFormat = (event, newFormats) => { + setFormats(newFormats); + }; + + const handleChange = (event, nextView) => { + setView(nextView); + }; + + const viewContent = [ + + + , + + + , + + + , + ]; + + const alignContent = [ + + + , + + + , + + + , + + + , + ]; + + const formatContent = [ + + + , + + + , + + + , + + + + , + ]; + + return ( + + + + {alignContent} + + + + + + {formatContent} + + + + + {SIZES.map((size) => ( + + + + ))} + + {SIZES.map((size) => ( + + {alignContent} + + ))} + + + + + + + + + + + + + {alignContent} + + + + {alignContent} + + + + + {COLORS.map((color) => ( + + {viewContent} + + ))} + + + + {COLORS.map((color) => ( + { + setSelected(!selected); + }} + > + + + ))} + + + + + {viewContent} + + + { + setSelected(!selected); + }} + > + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/button-view/view.jsx b/front_minimal/src/sections/_examples/mui/button-view/view.jsx new file mode 100644 index 0000000..1e3f364 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/button-view/view.jsx @@ -0,0 +1,47 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { IconButtons } from './icon-buttons'; +import { ButtonGroups } from './button-groups'; +import { ToggleButtons } from './toggle-buttons'; +import { ButtonVariants } from './button-variants'; +import { ComponentHero } from '../../component-hero'; +import { ScrollToViewTemplate } from '../../component-template'; +import { FloatingActionButton } from './floating-action-button'; + +// ---------------------------------------------------------------------- + +export function ButtonView() { + const DEMO = [ + { name: 'Contained', component: }, + { name: 'Outlined', component: }, + { name: 'Text', component: }, + { name: 'Soft', component: }, + { name: 'Icon button', component: }, + { name: 'Fab', component: }, + { name: 'Groups', component: }, + { name: 'Toggle', component: }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/checkbox-view/index.js b/front_minimal/src/sections/_examples/mui/checkbox-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/checkbox-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/checkbox-view/view.jsx b/front_minimal/src/sections/_examples/mui/checkbox-view/view.jsx new file mode 100644 index 0000000..909ac47 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/checkbox-view/view.jsx @@ -0,0 +1,198 @@ +'use client'; + +import { useState } from 'react'; + +import Checkbox from '@mui/material/Checkbox'; +import FormGroup from '@mui/material/FormGroup'; +import FormControl from '@mui/material/FormControl'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const COLORS = ['default', 'primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const PLACEMENTS = ['top', 'start', 'bottom', 'end']; + +// ---------------------------------------------------------------------- + +export function CheckboxView() { + const [checked, setChecked] = useState([true, false]); + + const handleChange1 = (event) => { + setChecked([event.target.checked, event.target.checked]); + }; + + const handleChange2 = (event) => { + setChecked([event.target.checked, checked[1]]); + }; + + const handleChange3 = (event) => { + setChecked([checked[0], event.target.checked]); + }; + + const DEMO = [ + { + name: 'Basic', + component: ( + + + + + + + + + ), + }, + { + name: 'Size & custom icon', + component: ( + + } /> + } /> + } + checkedIcon={} + inputProps={{ id: 'favorite-checkbox' }} + /> + } + label="Custom icon" + /> + + } + checkedIcon={} + inputProps={{ id: 'award-checkbox' }} + /> + } + label="Custom icon" + /> + + ), + }, + { + name: 'Placement', + component: ( + + + + {PLACEMENTS.map((placement) => ( + } + sx={{ textTransform: 'capitalize' }} + /> + ))} + + + + ), + }, + { + name: 'Colors', + component: ( + + + {COLORS.map((color) => ( + } + label={color} + sx={{ textTransform: 'capitalize' }} + /> + ))} + + } + label="Disabled" + /> + + + + + {COLORS.map((color) => ( + } + label={color} + sx={{ textTransform: 'capitalize' }} + /> + ))} + + } + label="Disabled" + /> + + + + ), + }, + { + name: 'Indeterminate', + component: ( + +
    + + } + /> +
    + } + /> + } + /> +
    +
    +
    + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/chip-view/chip.jsx b/front_minimal/src/sections/_examples/mui/chip-view/chip.jsx new file mode 100644 index 0000000..661766a --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/chip-view/chip.jsx @@ -0,0 +1,194 @@ +import Chip from '@mui/material/Chip'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; + +import { _mock } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function Chips({ variant = 'filled' }) { + const handleDelete = () => { + console.info('You clicked the delete icon.'); + }; + + return ( + + + M} + onDelete={handleDelete} + /> + + M} /> + + } + color="primary" + onDelete={handleDelete} + /> + + } + color="primary" + /> + + } + label="Secondary deletable" + onDelete={handleDelete} + color="secondary" + /> + + } + label="Secondary clickable" + color="secondary" + /> + + } + label="Info deletable" + onDelete={handleDelete} + color="info" + /> + + } + label="Info clickable" + color="info" + /> + + } + label="Success deletable" + onDelete={handleDelete} + color="success" + /> + + } + label="Success clickable" + color="success" + /> + + } + label="Warning deletable" + onDelete={handleDelete} + color="warning" + /> + + } + label="Warning clickable" + color="warning" + /> + + } + label="Error deletable" + onDelete={handleDelete} + color="error" + /> + + } + label="Error clickable" + color="error" + /> + + + + + } + label="Custom icon" + onDelete={handleDelete} + deleteIcon={} + /> + + M} + label="Custom icon" + onDelete={handleDelete} + deleteIcon={} + color="info" + /> + + + + } + label="Disabled" + onDelete={handleDelete} + /> + + M} + label="Disabled" + onDelete={handleDelete} + color="info" + /> + + + + } + label="Normal" + onDelete={handleDelete} + color="info" + /> + + M} + label="Small" + onDelete={handleDelete} + color="info" + /> + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/chip-view/index.js b/front_minimal/src/sections/_examples/mui/chip-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/chip-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/chip-view/view.jsx b/front_minimal/src/sections/_examples/mui/chip-view/view.jsx new file mode 100644 index 0000000..e90d551 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/chip-view/view.jsx @@ -0,0 +1,33 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { Chips } from './chip'; +import { ComponentHero } from '../../component-hero'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +export function ChipView() { + const DEMO = [ + { name: 'Filled', component: }, + { name: 'Outlined', component: }, + { name: 'Soft', component: }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/data-grid-view/data-grid-basic.jsx b/front_minimal/src/sections/_examples/mui/data-grid-view/data-grid-basic.jsx new file mode 100644 index 0000000..c833da1 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/data-grid-view/data-grid-basic.jsx @@ -0,0 +1,75 @@ +import { DataGrid, GridActionsCellItem } from '@mui/x-data-grid'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +const columns = [ + { field: 'id', headerName: 'ID', width: 120 }, + { + field: 'firstName', + headerName: 'First name', + width: 160, + editable: true, + }, + { + field: 'lastName', + headerName: 'Last name', + width: 160, + editable: true, + }, + { + field: 'age', + headerName: 'Age', + type: 'number', + width: 120, + editable: true, + align: 'center', + headerAlign: 'center', + }, + { + field: 'fullName', + headerName: 'Full name', + description: 'This column has a value getter and is not sortable.', + flex: 1, + renderCell: (params) => `${params.row.firstName} ${params.row.lastName}`, + }, + { + type: 'actions', + field: 'actions', + headerName: 'Actions', + align: 'right', + headerAlign: 'right', + width: 80, + sortable: false, + filterable: false, + disableColumnMenu: true, + getActions: (params) => [ + } + label="View" + onClick={() => console.info('VIEW', params.row.id)} + />, + } + label="Edit" + onClick={() => console.info('EDIT', params.row.id)} + />, + } + label="Delete" + onClick={() => console.info('DELETE', params.row.id)} + sx={{ color: 'error.main' }} + />, + ], + }, +]; + +// ---------------------------------------------------------------------- + +export function DataGridBasic({ data }) { + return ; +} diff --git a/front_minimal/src/sections/_examples/mui/data-grid-view/data-grid-custom.jsx b/front_minimal/src/sections/_examples/mui/data-grid-view/data-grid-custom.jsx new file mode 100644 index 0000000..7e5f966 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/data-grid-view/data-grid-custom.jsx @@ -0,0 +1,300 @@ +import { useRef, useMemo, useState, useImperativeHandle } from 'react'; + +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Rating from '@mui/material/Rating'; +import Typography from '@mui/material/Typography'; +import LinearProgress from '@mui/material/LinearProgress'; +import { + DataGrid, + gridClasses, + GridToolbarExport, + GridActionsCellItem, + GridToolbarContainer, + GridToolbarQuickFilter, + GridToolbarFilterButton, + GridToolbarColumnsButton, + GridToolbarDensitySelector, +} from '@mui/x-data-grid'; + +import { fPercent } from 'src/utils/format-number'; +import { fDate, fTime } from 'src/utils/format-time'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { EmptyContent } from 'src/components/empty-content'; + +// ---------------------------------------------------------------------- + +const baseColumns = [ + { field: 'id', headerName: 'Id', filterable: false }, + { + field: 'name', + headerName: 'Name', + flex: 1, + minWidth: 160, + hideable: false, + renderCell: (params) => ( + + + {params.row.name.charAt(0).toUpperCase()} + + + {params.row.name} + + + ), + }, + { + field: 'email', + headerName: 'Email', + flex: 1, + minWidth: 160, + editable: true, + renderCell: (params) => ( + + {params.row.email} + + ), + }, + { + type: 'string', + field: 'lastLogin', + headerName: 'Last login', + align: 'right', + headerAlign: 'right', + width: 120, + renderCell: (params) => ( + + {fDate(params.row.lastLogin)} + + {fTime(params.row.lastLogin)} + + + ), + }, + { + type: 'number', + field: 'rating', + headerName: 'Rating', + width: 140, + renderCell: (params) => ( + + ), + }, + { + type: 'singleSelect', + field: 'status', + headerName: 'Status', + align: 'center', + headerAlign: 'center', + width: 100, + editable: true, + valueOptions: ['online', 'alway', 'busy'], + renderCell: (params) => ( + + ), + }, + { + type: 'boolean', + field: 'isAdmin', + align: 'center', + headerAlign: 'center', + width: 80, + renderCell: (params) => + params.row.isAdmin ? ( + + ) : ( + '-' + ), + }, + { + type: 'number', + field: 'performance', + headerName: 'Performance', + align: 'center', + headerAlign: 'center', + width: 160, + renderCell: (params) => ( + + 30 && params.row.performance < 70 && 'warning') || + 'primary' + } + sx={{ width: 1, height: 6 }} + /> + + {fPercent(params.row.performance)} + + + ), + }, + { + type: 'actions', + field: 'actions', + headerName: 'Actions', + align: 'right', + headerAlign: 'right', + width: 80, + sortable: false, + filterable: false, + disableColumnMenu: true, + getActions: (params) => [ + } + label="View" + onClick={() => console.info('VIEW', params.row.id)} + />, + } + label="Edit" + onClick={() => console.info('EDIT', params.row.id)} + />, + } + label="Delete" + onClick={() => console.info('DELETE', params.row.id)} + sx={{ color: 'error.main' }} + />, + ], + }, +]; + +const HIDE_COLUMNS = { id: false }; + +const HIDE_COLUMNS_TOGGLABLE = ['id', 'actions']; + +// ---------------------------------------------------------------------- + +export function DataGridCustom({ data: rows }) { + const [filterButtonEl, setFilterButtonEl] = useState(null); + + const [selectedRows, setSelectedRows] = useState([]); + + const [columnVisibilityModel, setColumnVisibilityModel] = useState(HIDE_COLUMNS); + + const columns = useMemo( + () => + baseColumns.map((col) => + col.field === 'rating' ? { ...col, filterOperators: ratingOnlyOperators } : col + ), + [] + ); + + const getTogglableColumns = () => + columns + .filter((column) => !HIDE_COLUMNS_TOGGLABLE.includes(column.field)) + .map((column) => column.field); + + const selected = rows.filter((row) => selectedRows.includes(row.id)).map((_row) => _row.id); + + console.info('SELECTED ROWS', selected); + + return ( + { + setSelectedRows(newSelectionModel); + }} + columnVisibilityModel={columnVisibilityModel} + onColumnVisibilityModelChange={(newModel) => setColumnVisibilityModel(newModel)} + slots={{ + toolbar: CustomToolbar, + noRowsOverlay: () => , + noResultsOverlay: () => , + }} + slotProps={{ + panel: { anchorEl: filterButtonEl }, + toolbar: { setFilterButtonEl, showQuickFilter: true }, + columnsManagement: { getTogglableColumns }, + }} + sx={{ [`& .${gridClasses.cell}`]: { alignItems: 'center', display: 'inline-flex' } }} + /> + ); +} + +function CustomToolbar({ setFilterButtonEl }) { + return ( + + + + + + + + + ); +} + +// ---------------------------------------------------------------------- + +function RatingInputValue({ item, applyValue, focusElementRef }) { + const ratingRef = useRef(null); + + useImperativeHandle(focusElementRef, () => ({ + focus: () => { + ratingRef.current.querySelector(`input[value="${Number(item.value) || ''}"]`).focus(); + }, + })); + + const handleFilter = (event, newValue) => { + applyValue({ ...item, value: newValue }); + }; + + return ( + + ); +} + +const ratingOnlyOperators = [ + { + label: 'Above', + value: 'above', + getApplyFilterFn: (filterItem) => { + if (!filterItem.field || !filterItem.value || !filterItem.operator) { + return null; + } + + return (params) => Number(params.value) >= Number(filterItem.value); + }, + InputComponent: RatingInputValue, + InputComponentProps: { type: 'number' }, + getValueAsString: (value) => `${value} Stars`, + }, +]; diff --git a/front_minimal/src/sections/_examples/mui/data-grid-view/index.js b/front_minimal/src/sections/_examples/mui/data-grid-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/data-grid-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/data-grid-view/view.jsx b/front_minimal/src/sections/_examples/mui/data-grid-view/view.jsx new file mode 100644 index 0000000..847e59c --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/data-grid-view/view.jsx @@ -0,0 +1,85 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Container from '@mui/material/Container'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; + +import { _mock } from 'src/_mock'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { DataGridBasic } from './data-grid-basic'; +import { DataGridCustom } from './data-grid-custom'; +import { ComponentHero } from '../../component-hero'; + +// ---------------------------------------------------------------------- + +const _dataGrid = [...Array(20)].map((_, index) => { + const status = + (index % 2 && 'online') || (index % 3 && 'alway') || (index % 4 && 'busy') || 'offline'; + + return { + id: _mock.id(index), + status, + email: _mock.email(index), + name: _mock.fullName(index), + age: _mock.number.age(index), + lastLogin: _mock.time(index), + isAdmin: _mock.boolean(index), + lastName: _mock.lastName(index), + rating: _mock.number.rating(index), + firstName: _mock.firstName(index), + performance: _mock.number.percent(index), + }; +}); + +// ---------------------------------------------------------------------- + +export function DataGridView() { + return ( + <> + + + + + This component includes 2 Free and Paid versions from + MUI. +
    + Paid version will have more features. Please read more{' '} + + here + +
    +
    + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/dialog-view/alert-dialog.jsx b/front_minimal/src/sections/_examples/mui/dialog-view/alert-dialog.jsx new file mode 100644 index 0000000..3f0bcd8 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/dialog-view/alert-dialog.jsx @@ -0,0 +1,39 @@ +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +// ---------------------------------------------------------------------- + +export function AlertDialog() { + const dialog = useBoolean(); + + return ( + <> + + + + {`Use Google's location service?`} + + + Let Google help apps determine location. This means sending anonymous location data to + Google, even when no apps are running. + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/dialog-view/form-dialog.jsx b/front_minimal/src/sections/_examples/mui/dialog-view/form-dialog.jsx new file mode 100644 index 0000000..9991f4e --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/dialog-view/form-dialog.jsx @@ -0,0 +1,52 @@ +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +// ---------------------------------------------------------------------- + +export function FormDialog() { + const dialog = useBoolean(); + + return ( +
    + + + + Subscribe + + + + To subscribe to this website, please enter your email address here. We will send updates + occasionally. + + + + + + + + + + +
    + ); +} diff --git a/front_minimal/src/sections/_examples/mui/dialog-view/full-screen-dialog.jsx b/front_minimal/src/sections/_examples/mui/dialog-view/full-screen-dialog.jsx new file mode 100644 index 0000000..088d036 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/dialog-view/full-screen-dialog.jsx @@ -0,0 +1,74 @@ +import { forwardRef } from 'react'; + +import Box from '@mui/material/Box'; +import Slide from '@mui/material/Slide'; +import Button from '@mui/material/Button'; +import AppBar from '@mui/material/AppBar'; +import Dialog from '@mui/material/Dialog'; +import Divider from '@mui/material/Divider'; +import Toolbar from '@mui/material/Toolbar'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +const Transition = forwardRef((props, ref) => ); + +// ---------------------------------------------------------------------- + +export function FullScreenDialog() { + const dialog = useBoolean(); + + return ( + <> + + + + + + + + + + + Sound + + + + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/dialog-view/index.js b/front_minimal/src/sections/_examples/mui/dialog-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/dialog-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/dialog-view/max-width-dialog.jsx b/front_minimal/src/sections/_examples/mui/dialog-view/max-width-dialog.jsx new file mode 100644 index 0000000..342a5aa --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/dialog-view/max-width-dialog.jsx @@ -0,0 +1,100 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import Switch from '@mui/material/Switch'; +import Dialog from '@mui/material/Dialog'; +import Select from '@mui/material/Select'; +import MenuItem from '@mui/material/MenuItem'; +import InputLabel from '@mui/material/InputLabel'; +import Typography from '@mui/material/Typography'; +import FormControl from '@mui/material/FormControl'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +// ---------------------------------------------------------------------- + +export function MaxWidthDialog() { + const dialog = useBoolean(); + + const [fullWidth, setFullWidth] = useState(true); + + const [maxWidth, setMaxWidth] = useState('sm'); + + const handleMaxWidthChange = useCallback((event) => { + // @ts-expect-error autofill of arbitrary value is not handled. + setMaxWidth(event.target.value); + }, []); + + const handleFullWidthChange = useCallback((event) => { + setFullWidth(event.target.checked); + }, []); + + return ( + <> + + + + Optional sizes + + + + You can set my maximum width and whether to adapt or not. + + + + + maxWidth + + + + } + label="Full width" + sx={{ mt: 1 }} + /> + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/dialog-view/scroll-dialog.jsx b/front_minimal/src/sections/_examples/mui/dialog-view/scroll-dialog.jsx new file mode 100644 index 0000000..a833d73 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/dialog-view/scroll-dialog.jsx @@ -0,0 +1,74 @@ +import { useRef, useState, useEffect, useCallback } from 'react'; + +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; +import DialogContentText from '@mui/material/DialogContentText'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +// ---------------------------------------------------------------------- + +export function ScrollDialog() { + const dialog = useBoolean(); + + const [scroll, setScroll] = useState('paper'); + + const handleClickOpen = useCallback( + (scrollType) => () => { + dialog.onTrue(); + setScroll(scrollType); + }, + [dialog] + ); + + const descriptionElementRef = useRef(null); + + useEffect(() => { + if (dialog.value) { + const { current: descriptionElement } = descriptionElementRef; + if (descriptionElement) { + descriptionElement.focus(); + } + } + }, [dialog.value]); + + return ( + <> + + + + + + Subscribe + + + + {[...new Array(50)] + .map( + () => `Cras mattis consectetur purus sit amet fermentum. +Cras justo odio, dapibus ac facilisis in, egestas eget quam. +Morbi leo risus, porta ac consectetur ac, vestibulum at eros. +Praesent commodo cursus magna, vel scelerisque nisl consectetur et.` + ) + .join('\n')} + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/dialog-view/simple-dialog.jsx b/front_minimal/src/sections/_examples/mui/dialog-view/simple-dialog.jsx new file mode 100644 index 0000000..f4ee1c8 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/dialog-view/simple-dialog.jsx @@ -0,0 +1,70 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Dialog from '@mui/material/Dialog'; +import Typography from '@mui/material/Typography'; +import DialogTitle from '@mui/material/DialogTitle'; +import ListItemText from '@mui/material/ListItemText'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +const emails = ['username@gmail.com', 'user02@gmail.com']; + +// ---------------------------------------------------------------------- + +export function SimpleDialog() { + const dialog = useBoolean(); + + const [selectedValue, setSelectedValue] = useState(emails[1]); + + const handleClose = useCallback( + (value) => { + dialog.onFalse(); + setSelectedValue(value); + }, + [dialog] + ); + + return ( + <> + + + Selected: {selectedValue} + + handleClose(selectedValue)}> + Set backup account + + + {emails.map((email) => ( + + handleClose(email)}> + + + + + + + ))} + + + handleClose('addAccount')}> + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/dialog-view/transitions-dialog.jsx b/front_minimal/src/sections/_examples/mui/dialog-view/transitions-dialog.jsx new file mode 100644 index 0000000..10a2de9 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/dialog-view/transitions-dialog.jsx @@ -0,0 +1,51 @@ +import { forwardRef } from 'react'; + +import Slide from '@mui/material/Slide'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +// ---------------------------------------------------------------------- + +const Transition = forwardRef((props, ref) => ); + +// ---------------------------------------------------------------------- + +export function TransitionsDialog() { + const dialog = useBoolean(); + + return ( +
    + + + + {`Use Google's location service?`} + + + Let Google help apps determine location. This means sending anonymous location data to + Google, even when no apps are running. + + + + + + + +
    + ); +} diff --git a/front_minimal/src/sections/_examples/mui/dialog-view/view.jsx b/front_minimal/src/sections/_examples/mui/dialog-view/view.jsx new file mode 100644 index 0000000..b9e042b --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/dialog-view/view.jsx @@ -0,0 +1,68 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { FormDialog } from './form-dialog'; +import { AlertDialog } from './alert-dialog'; +import { ScrollDialog } from './scroll-dialog'; +import { SimpleDialog } from './simple-dialog'; +import { MaxWidthDialog } from './max-width-dialog'; +import { ComponentHero } from '../../component-hero'; +import { FullScreenDialog } from './full-screen-dialog'; +import { TransitionsDialog } from './transitions-dialog'; +import { ComponentBlock, ComponentContainer } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function DialogView() { + return ( + <> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/list-view/index.js b/front_minimal/src/sections/_examples/mui/list-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/list-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/list-view/view.jsx b/front_minimal/src/sections/_examples/mui/list-view/view.jsx new file mode 100644 index 0000000..380ec37 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/list-view/view.jsx @@ -0,0 +1,346 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import List from '@mui/material/List'; +import Avatar from '@mui/material/Avatar'; +import Switch from '@mui/material/Switch'; +import Divider from '@mui/material/Divider'; +import ListItem from '@mui/material/ListItem'; +import Collapse from '@mui/material/Collapse'; +import Checkbox from '@mui/material/Checkbox'; +import IconButton from '@mui/material/IconButton'; +import ListItemIcon from '@mui/material/ListItemIcon'; +import ListItemText from '@mui/material/ListItemText'; +import ListSubheader from '@mui/material/ListSubheader'; +import ListItemAvatar from '@mui/material/ListItemAvatar'; +import ListItemButton from '@mui/material/ListItemButton'; +import ListItemSecondaryAction from '@mui/material/ListItemSecondaryAction'; + +import { paths } from 'src/routes/paths'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +export function ListView() { + const [open, setOpen] = useState(true); + + const [checked, setChecked] = useState([0]); + + const [toggle, setToggle] = useState(['wifi']); + + const [selectedIndex, setSelectedIndex] = useState(1); + + const handleClick = useCallback(() => { + setOpen((prev) => !prev); + }, []); + + const handleListItemClick = useCallback((event, index) => { + setSelectedIndex(index); + }, []); + + const handleCheck = (value) => () => { + const currentIndex = checked.indexOf(value); + const newChecked = [...checked]; + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + setChecked(newChecked); + }; + + const handleToggle = (value) => () => { + const currentIndex = toggle.indexOf(value); + const newChecked = [...toggle]; + + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + + setToggle(newChecked); + }; + + const DEMO = [ + { + name: 'Simple', + component: ( + + + + + + + + + ), + }, + { + name: 'Nested', + component: ( + + + Nested List Items + + } + > + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ), + }, + { + name: 'Folder', + component: ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ), + }, + { + name: 'Selected', + component: ( + + + + handleListItemClick(event, 0)} + > + + + + + + handleListItemClick(event, 1)} + > + + + + + + + + + handleListItemClick(event, 2)} + > + + + handleListItemClick(event, 3)} + > + + + + + + ), + }, + { + name: 'Controls', + component: ( + + + {[0, 1, 2, 3].map((value) => { + const labelId = `checkbox-list-label-${value}`; + return ( + + + + } + disablePadding + > + + + + + + + + + ); + })} + + + ), + }, + { + name: 'Switch', + component: ( + + Settings} + sx={{ bgcolor: 'background.paper' }} + > + + + + + + + + + + + + + + + + + + + + + + + + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/menu-view/index.js b/front_minimal/src/sections/_examples/mui/menu-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/menu-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/menu-view/view.jsx b/front_minimal/src/sections/_examples/mui/menu-view/view.jsx new file mode 100644 index 0000000..39721df --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/menu-view/view.jsx @@ -0,0 +1,166 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Menu from '@mui/material/Menu'; +import Button from '@mui/material/Button'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import ListItemText from '@mui/material/ListItemText'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { paths } from 'src/routes/paths'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock, ComponentContainer } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const OPTIONS = [ + 'Show some love to Material-UI', + 'Show all notification content', + 'Hide sensitive notification content', + 'Hide all notification content', +]; + +const OPTIONS_MAXHEIGHT = [ + 'None', + 'Atria', + 'Callisto', + 'Dione', + 'Ganymede', + 'Hangouts Call', + 'Luna', + 'Oberon', + 'Phobos', + 'Pyxis', + 'Sedna', + 'Titania', + 'Triton', + 'Umbriel', +]; + +// ---------------------------------------------------------------------- + +export function MenuView() { + const [selectedIndex, setSelectedIndex] = useState(1); + + const [isOpen, setOpen] = useState(null); + + const [isOpenList, setOpenList] = useState(null); + + const [isOpenMaxHeight, setOpenMaxHeight] = useState(null); + + const handleClick = useCallback((event) => { + setOpenMaxHeight(event.currentTarget); + }, []); + + const handleClickListItem = useCallback((event) => { + setOpenList(event.currentTarget); + }, []); + + const handleMenuItemClick = useCallback((event, index) => { + setSelectedIndex(index); + setOpenList(null); + }, []); + + const handleOpen = useCallback((event) => { + setOpen(event.currentTarget); + }, []); + + const handleClose = useCallback(() => { + setOpen(null); + }, []); + + const handleMaxHeightClose = useCallback(() => { + setOpenMaxHeight(null); + }, []); + + return ( + <> + + + + + + + + + {['Profile', 'My account', 'Logout'].map((option) => ( + + {option} + + ))} + + + + + + + + {OPTIONS.map((option, index) => ( + handleMenuItemClick(event, index)} + > + {option} + + ))} + + + + + + + + + + {OPTIONS_MAXHEIGHT.map((option) => ( + + {option} + + ))} + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/pagination-view/index.js b/front_minimal/src/sections/_examples/mui/pagination-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/pagination-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/pagination-view/pagination-items.jsx b/front_minimal/src/sections/_examples/mui/pagination-view/pagination-items.jsx new file mode 100644 index 0000000..409a7de --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/pagination-view/pagination-items.jsx @@ -0,0 +1,84 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Select from '@mui/material/Select'; +import MenuItem from '@mui/material/MenuItem'; +import Pagination from '@mui/material/Pagination'; +import InputLabel from '@mui/material/InputLabel'; +import FormControl from '@mui/material/FormControl'; + +import { varAlpha } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +const items = [...Array(100)].map((_, index) => index + 1); + +// ---------------------------------------------------------------------- + +export function PaginationItems() { + const [page, setPage] = useState(1); + + const [rowsPerPage, setRowsPerPage] = useState(12); + + const handleChangePage = useCallback((event, newPage) => { + setPage(newPage); + }, []); + + const handleChangeRowsPerPage = useCallback((event) => { + setRowsPerPage(parseInt(event.target.value, 10)); + setPage(1); + }, []); + + return ( + + + {items + .slice((page - 1) * rowsPerPage, (page - 1) * rowsPerPage + rowsPerPage) + .map((item) => ( + varAlpha(theme.vars.palette.text.disabledChannel, 0.48), + }} + > + {item} + + ))} + + + + + + + Items per page + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/pagination-view/view.jsx b/front_minimal/src/sections/_examples/mui/pagination-view/view.jsx new file mode 100644 index 0000000..66cd70a --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/pagination-view/view.jsx @@ -0,0 +1,156 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Pagination from '@mui/material/Pagination'; +import TablePagination from '@mui/material/TablePagination'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { PaginationItems } from './pagination-items'; +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const COLORS = ['standard', 'primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const SIZES = ['small', 'medium', 'large']; + +// ---------------------------------------------------------------------- + +const blockProps = { gap: 3, flexDirection: 'column' }; + +// ---------------------------------------------------------------------- + +export function PaginationView() { + const [page, setPage] = useState(2); + + const [rowsPerPage, setRowsPerPage] = useState(10); + + const handleChangePage = useCallback((event, newPage) => { + setPage(newPage); + }, []); + + const handleChangeRowsPerPage = useCallback((event) => { + setRowsPerPage(parseInt(event.target.value, 10)); + setPage(0); + }, []); + + const DEMO = [ + { + name: 'Circular', + component: ( + + + + + + + + + ), + }, + { + name: 'Rounded', + component: ( + + + + + + + + + ), + }, + { + name: 'Colors', + component: ( + + {COLORS.map((color) => ( + + ))} + + {COLORS.map((color) => ( + + ))} + + {COLORS.map((color) => ( + + ))} + + ), + }, + { + name: 'Sizes', + component: ( + + {SIZES.map((size) => ( + + ))} + + ), + }, + { + name: 'Buttons', + component: ( + + + + + ), + }, + { + name: 'Ranges', + component: ( + + + + + + + ), + }, + { + name: 'Table', + component: ( + + + + ), + }, + { + name: 'Items', + component: ( + + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/picker-view/index.js b/front_minimal/src/sections/_examples/mui/picker-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/picker-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/picker-view/picker-date-range.jsx b/front_minimal/src/sections/_examples/mui/picker-view/picker-date-range.jsx new file mode 100644 index 0000000..cca2865 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/picker-view/picker-date-range.jsx @@ -0,0 +1,85 @@ +import dayjs from 'dayjs'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; + +import { fDate } from 'src/utils/format-time'; + +import { useDateRangePicker, CustomDateRangePicker } from 'src/components/custom-date-range-picker'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function PickerDateRange() { + const rangeInputPicker = useDateRangePicker(dayjs(), dayjs()); + + const rangeCalendarPicker = useDateRangePicker(dayjs(new Date('2024/08/08')), null); + + return ( + <> + +
    This is the custom component from minimal.
    +
    You can use more advanced components by MUI.
    + + + https://mui.com/x/react-date-pickers/date-range-picker/ + +
    + + + + + + +
    + Start: {fDate(rangeInputPicker.startDate)} +
    +
    + End: {fDate(rangeInputPicker.endDate)} +
    +
    + + +
    + + + + + +
    + Start: {fDate(rangeCalendarPicker.startDate)} +
    +
    + End: {fDate(rangeCalendarPicker.endDate)} +
    +
    + + +
    +
    + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/picker-view/picker-date-time.jsx b/front_minimal/src/sections/_examples/mui/picker-view/picker-date-time.jsx new file mode 100644 index 0000000..844a1b1 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/picker-view/picker-date-time.jsx @@ -0,0 +1,56 @@ +import dayjs from 'dayjs'; +import { useState } from 'react'; + +import Stack from '@mui/material/Stack'; +import { DateTimePicker } from '@mui/x-date-pickers/DateTimePicker'; +import { MobileDateTimePicker } from '@mui/x-date-pickers/MobileDateTimePicker'; +import { DesktopDateTimePicker } from '@mui/x-date-pickers/DesktopDateTimePicker'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function PickerDateTime() { + const [value, setValue] = useState(dayjs(new Date())); + + const [valueResponsive, setValueResponsive] = useState(dayjs('2018-01-01T00:00:00.000Z')); + + return ( + + + + + + + { + setValueResponsive(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + + { + setValueResponsive(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + + { + setValueResponsive(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/picker-view/picker-date.jsx b/front_minimal/src/sections/_examples/mui/picker-view/picker-date.jsx new file mode 100644 index 0000000..0aeea14 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/picker-view/picker-date.jsx @@ -0,0 +1,105 @@ +import dayjs from 'dayjs'; +import { useState } from 'react'; + +import Stack from '@mui/material/Stack'; +import NoSsr from '@mui/material/NoSsr'; +import { DatePicker } from '@mui/x-date-pickers/DatePicker'; +import { StaticDatePicker } from '@mui/x-date-pickers/StaticDatePicker'; +import { MobileDatePicker } from '@mui/x-date-pickers/MobileDatePicker'; +import { DesktopDatePicker } from '@mui/x-date-pickers/DesktopDatePicker'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function PickerDate() { + const [value, setValue] = useState(dayjs(new Date())); + + return ( + + + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + + + + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + + + + + { + setValue(newValue); + }} + /> + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/picker-view/picker-time.jsx b/front_minimal/src/sections/_examples/mui/picker-view/picker-time.jsx new file mode 100644 index 0000000..e3878f4 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/picker-view/picker-time.jsx @@ -0,0 +1,84 @@ +import dayjs from 'dayjs'; +import { useState } from 'react'; + +import Stack from '@mui/material/Stack'; +import { TimePicker } from '@mui/x-date-pickers/TimePicker'; +import { MobileTimePicker } from '@mui/x-date-pickers/MobileTimePicker'; +import { StaticTimePicker } from '@mui/x-date-pickers/StaticTimePicker'; +import { DesktopTimePicker } from '@mui/x-date-pickers/DesktopTimePicker'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function PickerTime() { + const [value, setValue] = useState(dayjs(new Date())); + + return ( + + + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + + + + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + { + setValue(newValue); + }} + slotProps={{ textField: { fullWidth: true } }} + /> + + + + + { + setValue(newValue); + }} + /> + { + setValue(newValue); + }} + /> + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/picker-view/view.jsx b/front_minimal/src/sections/_examples/mui/picker-view/view.jsx new file mode 100644 index 0000000..d04f168 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/picker-view/view.jsx @@ -0,0 +1,40 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { PickerDate } from './picker-date'; +import { PickerTime } from './picker-time'; +import { PickerDateTime } from './picker-date-time'; +import { ComponentHero } from '../../component-hero'; +import { PickerDateRange } from './picker-date-range'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +export function PickerView() { + const DEMO = [ + { name: 'Date', component: }, + { name: 'DateTime', component: }, + { name: 'Time', component: }, + { name: 'Range', component: }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/popover-view/index.js b/front_minimal/src/sections/_examples/mui/popover-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/popover-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/popover-view/view.jsx b/front_minimal/src/sections/_examples/mui/popover-view/view.jsx new file mode 100644 index 0000000..1ce0628 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/popover-view/view.jsx @@ -0,0 +1,175 @@ +'use client'; + +import { useRef, useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Radio from '@mui/material/Radio'; +import Button from '@mui/material/Button'; +import FormLabel from '@mui/material/FormLabel'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import RadioGroup from '@mui/material/RadioGroup'; +import FormControl from '@mui/material/FormControl'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock, ComponentContainer } from '../../component-block'; + +// ---------------------------------------------------------------------- + +export function PopoverView() { + const [arrow, setArrow] = useState('top-left'); + + const clickPopover = usePopover(); + + const customizedPopover = usePopover(); + + const hoverPopoverRef = useRef(null); + + const [hoverPopoverOpen, setHoverPopoverOpen] = useState(false); + + const handleChangePopoverArrow = useCallback((event) => { + setArrow(event.target.value); + }, []); + + const handleHoverPopoverOpen = useCallback(() => { + setHoverPopoverOpen(true); + }, []); + + const handleHoverPopoverClose = useCallback(() => { + setHoverPopoverOpen(false); + }, []); + + return ( + <> + + + + + + +
    + + + + + Etiam feugiat lorem non metus + + + Fusce vulputate eleifend sapien. Curabitur at lacus ac velit ornare lobortis. + + + +
    + +
    + + + + + + Etiam feugiat lorem non metus + + + Fusce vulputate eleifend sapien. Curabitur at lacus ac velit ornare lobortis. + + + +
    +
    + + + + + + + + Arrow + + {[ + 'top-left', + 'top-center', + 'top-right', + 'bottom-left', + 'bottom-center', + 'bottom-right', + 'left-top', + 'left-center', + 'left-bottom', + 'right-top', + 'right-center', + 'right-bottom', + ].map((position) => ( + } + label={position} + /> + ))} + + + + + + + Etiam feugiat lorem non metus + + + Fusce vulputate eleifend sapien. Curabitur at lacus ac velit ornare lobortis. + + + + +
    + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/progress-view/index.js b/front_minimal/src/sections/_examples/mui/progress-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/progress-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/progress-view/progress-circular.jsx b/front_minimal/src/sections/_examples/mui/progress-view/progress-circular.jsx new file mode 100644 index 0000000..9f9542f --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/progress-view/progress-circular.jsx @@ -0,0 +1,38 @@ +import Stack from '@mui/material/Stack'; +import CircularProgress from '@mui/material/CircularProgress'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const COLORS = ['inherit', 'primary', 'secondary', 'info', 'success', 'warning', 'error']; + +// ---------------------------------------------------------------------- + +export function ProgressCircular({ progress }) { + return ( + + + {COLORS.map((color) => ( + + ))} + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/progress-view/progress-linear.jsx b/front_minimal/src/sections/_examples/mui/progress-view/progress-linear.jsx new file mode 100644 index 0000000..e0a2221 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/progress-view/progress-linear.jsx @@ -0,0 +1,67 @@ +import Stack from '@mui/material/Stack'; +import LinearProgress from '@mui/material/LinearProgress'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const COLORS = ['inherit', 'primary', 'secondary', 'info', 'success', 'warning', 'error']; + +// ---------------------------------------------------------------------- + +export function ProgressLinear({ progress, buffer }) { + return ( + + + {COLORS.map((color) => ( + + ))} + + + + {COLORS.map((color) => ( + + ))} + + + + {COLORS.map((color) => ( + + ))} + + + + {COLORS.map((color) => ( + + ))} + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/progress-view/view.jsx b/front_minimal/src/sections/_examples/mui/progress-view/view.jsx new file mode 100644 index 0000000..a70c97e --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/progress-view/view.jsx @@ -0,0 +1,81 @@ +'use client'; + +import { useRef, useState, useEffect } from 'react'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ProgressLinear } from './progress-linear'; +import { ComponentHero } from '../../component-hero'; +import { ProgressCircular } from './progress-circular'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +export function ProgressView() { + const [progress, setProgress] = useState(0); + + const [buffer, setBuffer] = useState(10); + + useEffect(() => { + const timer = setInterval(() => { + setProgress((oldProgress) => { + if (oldProgress === 100) { + return 0; + } + const diff = Math.random() * 10; + return Math.min(oldProgress + diff, 100); + }); + }, 500); + + return () => { + clearInterval(timer); + }; + }, []); + + const progressRef = useRef(() => {}); + + useEffect(() => { + progressRef.current = () => { + if (progress > 100) { + setProgress(0); + setBuffer(10); + } else { + const diff = Math.random() * 10; + const diff2 = Math.random() * 10; + setProgress(progress + diff); + setBuffer(progress + diff + diff2); + } + }; + }); + + useEffect(() => { + const timer = setInterval(() => { + progressRef.current(); + }, 500); + + return () => { + clearInterval(timer); + }; + }, []); + + const DEMO = [ + { name: 'Circular', component: }, + { name: 'Linear', component: }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/radio-button-view/index.js b/front_minimal/src/sections/_examples/mui/radio-button-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/radio-button-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/radio-button-view/view.jsx b/front_minimal/src/sections/_examples/mui/radio-button-view/view.jsx new file mode 100644 index 0000000..bfea7a9 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/radio-button-view/view.jsx @@ -0,0 +1,122 @@ +'use client'; + +import { useState } from 'react'; + +import Radio from '@mui/material/Radio'; +import RadioGroup from '@mui/material/RadioGroup'; +import FormControl from '@mui/material/FormControl'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const COLORS = ['default', 'primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const PLACEMENTS = ['top', 'start', 'bottom', 'end']; + +// ---------------------------------------------------------------------- + +export function RadioButtonView() { + const [value, setValue] = useState('a1'); + + const handleChange = (event) => { + setValue(event.target.value); + }; + + const DEMO = [ + { + name: 'Basic', + component: ( + + + + + + + + + + ), + }, + { + name: 'Sizes', + component: ( + + + } label="Normal" /> + } label="Small" /> + + + ), + }, + { + name: 'Placement', + component: ( + + + + {PLACEMENTS.map((placement) => ( + } + sx={{ textTransform: 'capitalize' }} + /> + ))} + + + + ), + }, + { + name: 'Colors', + component: ( + + + + {COLORS.map((color) => ( + } + label={color} + sx={{ textTransform: 'capitalize' }} + /> + ))} + + } + label="Disabled" + /> + + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/rating-view/index.js b/front_minimal/src/sections/_examples/mui/rating-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/rating-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/rating-view/view.jsx b/front_minimal/src/sections/_examples/mui/rating-view/view.jsx new file mode 100644 index 0000000..cd40fd4 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/rating-view/view.jsx @@ -0,0 +1,192 @@ +'use client'; + +import { useState } from 'react'; + +import Box from '@mui/material/Box'; +import Rating from '@mui/material/Rating'; + +import { paths } from 'src/routes/paths'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const labels = { + 0.5: 'Useless', + 1: 'Useless+', + 1.5: 'Poor', + 2: 'Poor+', + 2.5: 'Ok', + 3: 'Ok+', + 3.5: 'Good', + 4: 'Good+', + 4.5: 'Excellent', + 5: 'Excellent+', +}; + +const customIcons = { + 1: { icon: , label: 'Very Dissatisfied' }, + 2: { icon: , label: 'Dissatisfied' }, + 3: { icon: , label: 'Neutral' }, + 4: { icon: , label: 'Satisfied' }, + 5: { icon: , label: 'Very Satisfied' }, +}; + +// ---------------------------------------------------------------------- + +export function RatingView() { + const [value, setValue] = useState(2); + + const [hover, setHover] = useState(-1); + + const DEMO = [ + { + name: 'Controlled', + component: ( + + { + setValue(newValue); + }} + /> + + ), + }, + { + name: 'Read only', + component: ( + + + + ), + }, + { + name: 'Disabled', + component: ( + + + + ), + }, + { + name: 'Pristine', + component: ( + + + + ), + }, + { + name: 'Custom empty icon', + component: ( + + + + ), + }, + { + name: 'Custom icon and color', + component: ( + + `${ratingValue} Heart${ratingValue !== 1 ? 's' : ''}`} + precision={0.5} + icon={} + emptyIcon={} + sx={{ color: 'info.main', '&:hover': { color: 'info.dark' } }} + /> + + ), + }, + { + name: '10 stars', + component: ( + + + + ), + }, + { + name: 'Custom icon set', + component: ( + + customIcons[ratingValue].label} + IconContainerComponent={IconContainer} + /> + + ), + }, + { + name: 'Hover feedback', + component: ( + + { + setValue(newValue); + }} + onChangeActive={(event, newHover) => { + setHover(newHover); + }} + /> + {value !== null && {labels[hover !== -1 ? hover : value]}} + + ), + }, + { + name: 'Half ratings', + component: ( + + + + + ), + }, + { + name: 'Sizes', + component: ( + + + + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} + +// ---------------------------------------------------------------------- + +function IconContainer(props) { + const { value, ...other } = props; + + return {customIcons[value].icon}; +} diff --git a/front_minimal/src/sections/_examples/mui/slider-view/index.js b/front_minimal/src/sections/_examples/mui/slider-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/slider-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/slider-view/view.jsx b/front_minimal/src/sections/_examples/mui/slider-view/view.jsx new file mode 100644 index 0000000..a0b68dd --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/slider-view/view.jsx @@ -0,0 +1,254 @@ +'use client'; + +import { useState } from 'react'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Slider, { sliderClasses } from '@mui/material/Slider'; + +import { paths } from 'src/routes/paths'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const COLORS = ['inherit', 'primary', 'secondary', 'error', 'info', 'success', 'warning']; + +const marks = [ + { value: 0, label: '0°C' }, + { value: 20, label: '20°C' }, + { value: 37, label: '37°C' }, + { value: 100, label: '100°C' }, +]; + +const prices = [ + { value: 0, label: '$0' }, + { value: 25, label: '250' }, + { value: 50, label: '500' }, + { value: 75, label: '750' }, + { value: 100, label: '1000' }, +]; + +// ---------------------------------------------------------------------- + +function valuePrice(value) { + return value > 0 ? `$${value}0` : `${value}`; +} + +function valueLabelFormatPrice(value) { + return value > 0 ? `$${value}` : value; +} + +function valuetext(value) { + return `$${value}°C`; +} + +function valueLabelFormat(value) { + return marks.findIndex((mark) => mark.value === value) + 1; +} + +// ---------------------------------------------------------------------- + +export function SliderView() { + const [value, setValue] = useState(30); + + const [price, setPrice] = useState([20, 37]); + + const handleChange = (event, newValue) => { + setValue(newValue); + }; + + const handleChangePrice = (event, newValue) => { + setPrice(newValue); + }; + + const DEMO = [ + { + name: 'Volume', + component: ( + + + + + + + + ), + }, + { + name: 'Disabled', + component: ( + + + + ), + }, + { + name: 'Temperature', + component: ( + + + + ), + }, + { + name: 'Sizes', + component: ( + + + + + ), + }, + { + name: 'Small steps', + component: ( + + + + ), + }, + { + name: 'Custom marks', + component: ( + + + + ), + }, + { + name: 'Restricted values', + component: ( + + + + ), + }, + { + name: 'Range', + component: ( + + x * 10} + step={10} + marks={prices} + value={price} + onChange={handleChangePrice} + valueLabelDisplay="on" + getAriaValueText={valuePrice} + valueLabelFormat={valueLabelFormatPrice} + sx={{ [`& .${sliderClasses.mark}[data-index="4"]`]: { display: 'none' } }} + /> + + varAlpha(theme.vars.palette.grey['500Channel'], 0.12), + }} + > + Min: {valuePrice(price[0])} + Max: {valuePrice(price[1])} + + + ), + }, + { + name: 'Color', + component: ( + + {COLORS.map((color) => ( + + ))} + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/stepper-view/customized-steppers.jsx b/front_minimal/src/sections/_examples/mui/stepper-view/customized-steppers.jsx new file mode 100644 index 0000000..20daca8 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/stepper-view/customized-steppers.jsx @@ -0,0 +1,236 @@ +import { useState } from 'react'; + +import Box from '@mui/material/Box'; +import Step from '@mui/material/Step'; +import Paper from '@mui/material/Paper'; +import Button from '@mui/material/Button'; +import Stepper from '@mui/material/Stepper'; +import { styled } from '@mui/material/styles'; +import StepLabel from '@mui/material/StepLabel'; +import Typography from '@mui/material/Typography'; +import StepConnector, { stepConnectorClasses } from '@mui/material/StepConnector'; + +import { varAlpha, bgGradient, stylesMode } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +const STEPS = ['Select campaign settings', 'Create an ad group', 'Create an ad']; + +const QontoConnector = styled(StepConnector)(({ theme }) => ({ + [`&.${stepConnectorClasses.alternativeLabel}`]: { + top: 10, + left: 'calc(-50% + 16px)', + right: 'calc(50% + 16px)', + }, + [`&.${stepConnectorClasses.active}`]: { + [`& .${stepConnectorClasses.line}`]: { borderColor: theme.vars.palette.success.main }, + }, + [`&.${stepConnectorClasses.completed}`]: { + [`& .${stepConnectorClasses.line}`]: { borderColor: theme.vars.palette.success.main }, + }, + [`& .${stepConnectorClasses.line}`]: { + borderRadius: 1, + borderTopWidth: 3, + borderColor: theme.vars.palette.divider, + }, +})); + +const QontoStepIconRoot = styled('div')(({ theme, ownerState }) => ({ + height: 22, + display: 'flex', + alignItems: 'center', + color: theme.vars.palette.text.disabled, + ...(ownerState.active && { color: theme.vars.palette.success.main }), + '& .QontoStepIcon-completedIcon': { + zIndex: 1, + fontSize: 18, + color: theme.vars.palette.success.main, + }, + '& .QontoStepIcon-circle': { + width: 8, + height: 8, + borderRadius: '50%', + backgroundColor: 'currentColor', + }, +})); + +function QontoStepIcon(props) { + const { active, completed, className } = props; + + return ( + + {completed ? ( + + ) : ( +
    + )} + + ); +} + +const ColorlibConnector = styled(StepConnector)(({ theme }) => ({ + [`&.${stepConnectorClasses.alternativeLabel}`]: { top: 22 }, + [`&.${stepConnectorClasses.active}`]: { + [`& .${stepConnectorClasses.line}`]: { + ...bgGradient({ + color: `0deg, ${theme.vars.palette.error.light}, ${theme.vars.palette.error.main}`, + }), + }, + }, + [`&.${stepConnectorClasses.completed}`]: { + [`& .${stepConnectorClasses.line}`]: { + ...bgGradient({ + color: `0deg, ${theme.vars.palette.error.light}, ${theme.vars.palette.error.main}`, + }), + }, + }, + [`& .${stepConnectorClasses.line}`]: { + height: 3, + border: 0, + borderRadius: 1, + backgroundColor: theme.vars.palette.divider, + }, +})); + +const ColorlibStepIconRoot = styled('div')(({ theme, ownerState }) => ({ + zIndex: 1, + width: 50, + height: 50, + display: 'flex', + borderRadius: '50%', + alignItems: 'center', + justifyContent: 'center', + color: theme.vars.palette.text.disabled, + backgroundColor: theme.vars.palette.grey[300], + [stylesMode.dark]: { backgroundColor: theme.vars.palette.grey[700] }, + ...(ownerState.active && { + ...bgGradient({ + color: `0deg, ${theme.vars.palette.error.light}, ${theme.vars.palette.error.main}`, + }), + color: theme.vars.palette.common.white, + boxShadow: '0 4px 10px 0 rgba(0,0,0,0.25)', + }), + ...(ownerState.completed && { + color: theme.vars.palette.common.white, + ...bgGradient({ + color: `0deg, ${theme.vars.palette.error.light}, ${theme.vars.palette.error.main}`, + }), + }), +})); + +function ColorlibStepIcon(props) { + const { active, completed, className, icon } = props; + + const icons = { + 1: , + 2: , + 3: , + }; + + return ( + + {icons[String(icon)]} + + ); +} + +function getStepContent(step) { + switch (step) { + case 0: + return 'Select campaign settings...'; + case 1: + return 'What is an ad group anyways?'; + case 2: + return 'This is the bit I really care about!'; + default: + return 'Unknown step'; + } +} + +// ---------------------------------------------------------------------- + +export function CustomizedSteppers() { + const [activeStep, setActiveStep] = useState(0); + + const handleNext = () => { + setActiveStep((prevActiveStep) => prevActiveStep + 1); + }; + + const handleBack = () => { + setActiveStep((prevActiveStep) => prevActiveStep - 1); + }; + + const handleReset = () => { + setActiveStep(0); + }; + + return ( + <> + }> + {STEPS.map((label) => ( + + {label} + + ))} + + + + + }> + {STEPS.map((label) => ( + + {label} + + ))} + + + {activeStep === STEPS.length ? ( + <> + varAlpha(theme.vars.palette.grey['500Channel'], 0.12), + }} + > + All steps completed - you're finished + + + + + ) : ( + <> + varAlpha(theme.vars.palette.grey['500Channel'], 0.12), + }} + > + {getStepContent(activeStep)} + + + + + + + + )} + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/stepper-view/horizontal-linear-stepper.jsx b/front_minimal/src/sections/_examples/mui/stepper-view/horizontal-linear-stepper.jsx new file mode 100644 index 0000000..6887919 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/stepper-view/horizontal-linear-stepper.jsx @@ -0,0 +1,133 @@ +import { useState } from 'react'; + +import Box from '@mui/material/Box'; +import Step from '@mui/material/Step'; +import Stack from '@mui/material/Stack'; +import Paper from '@mui/material/Paper'; +import Button from '@mui/material/Button'; +import Stepper from '@mui/material/Stepper'; +import StepLabel from '@mui/material/StepLabel'; +import Typography from '@mui/material/Typography'; + +import { varAlpha } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +const steps = ['Select campaign settings', 'Create an ad group', 'Create an ad']; + +// ---------------------------------------------------------------------- + +export function HorizontalLinearStepper() { + const [activeStep, setActiveStep] = useState(0); + + const [skipped, setSkipped] = useState(new Set()); + + const isStepOptional = (step) => step === 1; + + const isStepSkipped = (step) => skipped.has(step); + + const handleNext = () => { + let newSkipped = skipped; + if (isStepSkipped(activeStep)) { + newSkipped = new Set(newSkipped.values()); + newSkipped.delete(activeStep); + } + + setActiveStep((prevActiveStep) => prevActiveStep + 1); + setSkipped(newSkipped); + }; + + const handleBack = () => { + setActiveStep((prevActiveStep) => prevActiveStep - 1); + }; + + const handleSkip = () => { + if (!isStepOptional(activeStep)) { + // You probably want to guard against something like this, + // it should never occur unless someone's actively trying to break something. + throw new Error("You can't skip a step that isn't optional."); + } + + setActiveStep((prevActiveStep) => prevActiveStep + 1); + setSkipped((prevSkipped) => { + const newSkipped = new Set(prevSkipped.values()); + newSkipped.add(activeStep); + return newSkipped; + }); + }; + + const handleReset = () => { + setActiveStep(0); + }; + + return ( + + + {steps.map((label, index) => { + const stepProps = {}; + const labelProps = {}; + if (isStepOptional(index)) { + labelProps.optional = Optional; + } + if (isStepSkipped(index)) { + stepProps.completed = false; + } + return ( + + {label} + + ); + })} + + + {activeStep === steps.length ? ( + <> + varAlpha(theme.vars.palette.grey['500Channel'], 0.12), + }} + > + All steps completed - you're finished + + + + + + + + ) : ( + <> + varAlpha(theme.vars.palette.grey['500Channel'], 0.12), + }} + > + Step {activeStep + 1} + + + + + + + {isStepOptional(activeStep) && ( + + )} + + + + )} + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/stepper-view/index.js b/front_minimal/src/sections/_examples/mui/stepper-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/stepper-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/stepper-view/linear-alternative-label-stepper.jsx b/front_minimal/src/sections/_examples/mui/stepper-view/linear-alternative-label-stepper.jsx new file mode 100644 index 0000000..2810d23 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/stepper-view/linear-alternative-label-stepper.jsx @@ -0,0 +1,130 @@ +import { useState } from 'react'; + +import Box from '@mui/material/Box'; +import Step from '@mui/material/Step'; +import Stack from '@mui/material/Stack'; +import Paper from '@mui/material/Paper'; +import Button from '@mui/material/Button'; +import Stepper from '@mui/material/Stepper'; +import StepLabel from '@mui/material/StepLabel'; +import Typography from '@mui/material/Typography'; + +import { varAlpha } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +const steps = ['Select campaign settings', 'Create an ad group', 'Create an ad']; + +// ---------------------------------------------------------------------- + +export function LinearAlternativeLabel() { + const [activeStep, setActiveStep] = useState(0); + + const [skipped, setSkipped] = useState(new Set()); + + const isStepOptional = (step) => step === 1; + + const isStepSkipped = (step) => skipped.has(step); + + const handleNext = () => { + let newSkipped = skipped; + if (isStepSkipped(activeStep)) { + newSkipped = new Set(newSkipped.values()); + newSkipped.delete(activeStep); + } + + setActiveStep((prevActiveStep) => prevActiveStep + 1); + setSkipped(newSkipped); + }; + + const handleBack = () => { + setActiveStep((prevActiveStep) => prevActiveStep - 1); + }; + + const handleSkip = () => { + if (!isStepOptional(activeStep)) { + // You probably want to guard against something like this, + // it should never occur unless someone's actively trying to break something. + throw new Error("You can't skip a step that isn't optional."); + } + + setActiveStep((prevActiveStep) => prevActiveStep + 1); + setSkipped((prevSkipped) => { + const newSkipped = new Set(prevSkipped.values()); + newSkipped.add(activeStep); + return newSkipped; + }); + }; + + const handleReset = () => { + setActiveStep(0); + }; + + return ( + <> + + {steps.map((label, index) => { + const stepProps = {}; + const labelProps = {}; + + if (isStepSkipped(index)) { + stepProps.completed = false; + } + return ( + + {label} + + ); + })} + + + {activeStep === steps.length ? ( + <> + varAlpha(theme.vars.palette.grey['500Channel'], 0.12), + }} + > + All steps completed - you're finished + + + + + + + + ) : ( + <> + varAlpha(theme.vars.palette.grey['500Channel'], 0.12), + }} + > + Step {activeStep + 1} + + + + + + {isStepOptional(activeStep) && ( + + )} + + + + )} + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/stepper-view/vertical-linear-stepper.jsx b/front_minimal/src/sections/_examples/mui/stepper-view/vertical-linear-stepper.jsx new file mode 100644 index 0000000..744a3e7 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/stepper-view/vertical-linear-stepper.jsx @@ -0,0 +1,92 @@ +import { useState } from 'react'; + +import Box from '@mui/material/Box'; +import Step from '@mui/material/Step'; +import Paper from '@mui/material/Paper'; +import Button from '@mui/material/Button'; +import Stepper from '@mui/material/Stepper'; +import StepLabel from '@mui/material/StepLabel'; +import Typography from '@mui/material/Typography'; +import StepContent from '@mui/material/StepContent'; + +import { varAlpha } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +const steps = [ + { + label: 'Select campaign settings', + description: `For each ad campaign that you create, you can control how much + you're willing to spend on clicks and conversions, which networks + and geographical locations you want your ads to show on, and more.`, + }, + { + label: 'Create an ad group', + description: 'An ad group contains one or more ads which target a shared set of keywords.', + }, + { + label: 'Create an ad', + description: `Try out different ad text to see what brings in the most customers, + and learn how to enhance your ads using features like ad extensions. + If you run into any problems with your ads, find out how to tell if + they're running and how to resolve approval issues.`, + }, +]; + +// ---------------------------------------------------------------------- + +export function VerticalLinearStepper() { + const [activeStep, setActiveStep] = useState(0); + + const handleNext = () => { + setActiveStep((prevActiveStep) => prevActiveStep + 1); + }; + + const handleBack = () => { + setActiveStep((prevActiveStep) => prevActiveStep - 1); + }; + + const handleReset = () => { + setActiveStep(0); + }; + + return ( + <> + + {steps.map((step, index) => ( + + Last step : null} + > + {step.label} + + + {step.description} + + + + + + + ))} + + + {activeStep === steps.length && ( + varAlpha(theme.vars.palette.grey['500Channel'], 0.12), + }} + > + All steps completed - you're finished + + + )} + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/stepper-view/view.jsx b/front_minimal/src/sections/_examples/mui/stepper-view/view.jsx new file mode 100644 index 0000000..9b2d764 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/stepper-view/view.jsx @@ -0,0 +1,66 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { CustomizedSteppers } from './customized-steppers'; +import { ScrollToViewTemplate } from '../../component-template'; +import { VerticalLinearStepper } from './vertical-linear-stepper'; +import { HorizontalLinearStepper } from './horizontal-linear-stepper'; +import { LinearAlternativeLabel } from './linear-alternative-label-stepper'; + +// ---------------------------------------------------------------------- + +export function StepperView() { + const DEMO = [ + { + name: 'Horizontal linear stepper', + component: ( + + + + ), + }, + { + name: 'Linear alternative label', + component: ( + + + + ), + }, + { + name: 'Vertical linear stepper', + component: ( + + + + ), + }, + { + name: 'Customized stepper', + component: ( + + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/switch-view/index.js b/front_minimal/src/sections/_examples/mui/switch-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/switch-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/switch-view/view.jsx b/front_minimal/src/sections/_examples/mui/switch-view/view.jsx new file mode 100644 index 0000000..a36df5f --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/switch-view/view.jsx @@ -0,0 +1,108 @@ +'use client'; + +import Switch from '@mui/material/Switch'; +import FormGroup from '@mui/material/FormGroup'; +import FormControl from '@mui/material/FormControl'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const COLORS = ['default', 'primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const PLACEMENTS = ['top', 'start', 'bottom', 'end']; + +// ---------------------------------------------------------------------- + +export function SwitchView() { + const DEMO = [ + { + name: 'Basic', + component: ( + + + + + + + + ), + }, + { + name: 'Sizes', + component: ( + + + } label="Small" /> + } label="Normal" /> + + + ), + }, + { + name: 'Placement', + component: ( + + + {PLACEMENTS.map((placement) => ( + } + sx={{ textTransform: 'capitalize' }} + /> + ))} + + + ), + }, + { + name: 'Colors', + component: ( + + + + {COLORS.map((color) => ( + } + label={color} + sx={{ textTransform: 'capitalize' }} + /> + ))} + + } + label="Disabled" + /> + + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/table-view/basic.jsx b/front_minimal/src/sections/_examples/mui/table-view/basic.jsx new file mode 100644 index 0000000..2ce7b44 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/table-view/basic.jsx @@ -0,0 +1,59 @@ +import Table from '@mui/material/Table'; +import TableRow from '@mui/material/TableRow'; +import TableCell from '@mui/material/TableCell'; +import TableBody from '@mui/material/TableBody'; + +import { Scrollbar } from 'src/components/scrollbar'; +import { TableHeadCustom } from 'src/components/table'; + +// ---------------------------------------------------------------------- + +function createData(name, calories, fat, carbs, protein) { + return { + name, + calories, + fat, + carbs, + protein, + }; +} + +const TABLE_DATA = [ + createData('Frozen yoghurt', 159, 6.0, 24, 4.0), + createData('Ice cream sandwich', 237, 9.0, 37, 4.3), + createData('Eclair', 262, 16.0, 24, 6.0), + createData('Cupcake', 305, 3.7, 67, 4.3), + createData('Gingerbread', 356, 16.0, 49, 3.9), +]; + +const TABLE_HEAD = [ + { id: 'dessert', label: 'Dessert (100g serving)' }, + { id: 'calories', label: 'Calories', align: 'right' }, + { id: 'fat', label: 'Fat (g)', align: 'right' }, + { id: 'carbs', label: 'Carbs (g)', align: 'right' }, + { id: 'protein', label: 'Protein (g)', align: 'right' }, +]; + +// ---------------------------------------------------------------------- + +export function BasicTable() { + return ( + + + + + + {TABLE_DATA.map((row) => ( + + {row.name} + {row.calories} + {row.fat} + {row.carbs} + {row.protein} + + ))} + +
    +
    + ); +} diff --git a/front_minimal/src/sections/_examples/mui/table-view/collapsible.jsx b/front_minimal/src/sections/_examples/mui/table-view/collapsible.jsx new file mode 100644 index 0000000..a986cd4 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/table-view/collapsible.jsx @@ -0,0 +1,127 @@ +import Table from '@mui/material/Table'; +import Paper from '@mui/material/Paper'; +import TableRow from '@mui/material/TableRow'; +import Collapse from '@mui/material/Collapse'; +import TableHead from '@mui/material/TableHead'; +import TableCell from '@mui/material/TableCell'; +import TableBody from '@mui/material/TableBody'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; + +import { createData } from './utils'; + +// ---------------------------------------------------------------------- + +const TABLE_DATA = [ + createData('Frozen yoghurt', 159, 6.0, 24, 4.0, 3.99), + createData('Ice cream sandwich', 237, 9.0, 37, 4.3, 4.99), + createData('Eclair', 262, 16.0, 24, 6.0, 3.79), + createData('Cupcake', 305, 3.7, 67, 4.3, 2.5), + createData('Gingerbread', 356, 16.0, 49, 3.9, 1.5), +]; + +// ---------------------------------------------------------------------- + +export function CollapsibleTable() { + return ( + + + + + + Dessert (100g serving) + Calories + Fat (g) + Carbs (g) + Protein (g) + + + + + {TABLE_DATA.map((row) => ( + + ))} + +
    +
    + ); +} + +function CollapsibleTableRow({ row }) { + const collapsible = useBoolean(); + + return ( + <> + *': { borderBottom: 'unset' } }}> + + + + + + + {row.name} + + {row.calories} + {row.fat} + {row.carbs} + {row.protein} + + + + + + theme.customShadows.z20 }), + }} + > + + History + + + + + Date + Customer + Amount + Total price ($) + + + + + {row.history.map((historyRow) => ( + + + {historyRow.date} + + {historyRow.customerId} + {historyRow.amount} + + {Math.round(historyRow.amount * row.price * 100) / 100} + + + ))} + +
    +
    +
    +
    +
    + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/table-view/grouping-fixed-header.jsx b/front_minimal/src/sections/_examples/mui/table-view/grouping-fixed-header.jsx new file mode 100644 index 0000000..8dfb357 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/table-view/grouping-fixed-header.jsx @@ -0,0 +1,143 @@ +import Table from '@mui/material/Table'; +import TableRow from '@mui/material/TableRow'; +import TableHead from '@mui/material/TableHead'; +import TableCell from '@mui/material/TableCell'; +import TableBody from '@mui/material/TableBody'; + +import { Scrollbar } from 'src/components/scrollbar'; +import { useTable, TablePaginationCustom } from 'src/components/table'; + +// ---------------------------------------------------------------------- + +function createData(name, code, population, size) { + const density = population / size; + return { + name, + code, + population, + size, + density, + }; +} + +const TABLE_DATA = [ + createData('India', 'IN', 1324171354, 3287263), + createData('China', 'CN', 1403500365, 9596961), + createData('Italy', 'IT', 60483973, 301340), + createData('United States', 'US', 327167434, 9833520), + createData('Canada', 'CA', 37602103, 9984670), + createData('Australia', 'AU', 25475400, 7692024), + createData('Germany', 'DE', 83019200, 357578), + createData('Ireland', 'IE', 4857000, 70273), + createData('Mexico', 'MX', 126577691, 1972550), + createData('Japan', 'JP', 126317000, 377973), + createData('France', 'FR', 67022000, 640679), + createData('United Kingdom', 'GB', 67545757, 242495), + createData('Russia', 'RU', 146793744, 17098246), + createData('Nigeria', 'NG', 200962417, 923768), + createData('Brazil', 'BR', 210147125, 8515767), +]; + +const COLUMNS = [ + { id: 'name', label: 'Name', minWidth: 170 }, + { id: 'code', label: 'ISO\u00a0Code', minWidth: 100 }, + { + id: 'population', + label: 'Population', + minWidth: 170, + align: 'right', + format: (value) => value.toLocaleString('en-US'), + }, + { + id: 'size', + label: 'Size\u00a0(km\u00b2)', + minWidth: 170, + align: 'right', + format: (value) => value.toLocaleString('en-US'), + }, + { + id: 'density', + label: 'Density', + minWidth: 170, + align: 'right', + format: (value) => value.toFixed(2), + }, +]; + +// ---------------------------------------------------------------------- + +export function GroupingFixedHeaderTable() { + const table = useTable({ defaultRowsPerPage: 10 }); + + return ( + <> + + + + + theme.vars.palette.background.paper, + }} + > + Country + + theme.vars.palette.background.paper, + }} + > + Details + + + + + {COLUMNS.map((column) => ( + + {column.label} + + ))} + + + + + {TABLE_DATA.slice( + table.page * table.rowsPerPage, + table.page * table.rowsPerPage + table.rowsPerPage + ).map((row) => ( + + {COLUMNS.map((column) => { + const value = row[column.id]; + + return ( + + {column.format && typeof value === 'number' ? column.format(value) : value} + + ); + })} + + ))} + +
    +
    + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/table-view/index.js b/front_minimal/src/sections/_examples/mui/table-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/table-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/table-view/sorting-selecting.jsx b/front_minimal/src/sections/_examples/mui/table-view/sorting-selecting.jsx new file mode 100644 index 0000000..ef9cbe5 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/table-view/sorting-selecting.jsx @@ -0,0 +1,184 @@ +import { useState, useEffect } from 'react'; + +import Box from '@mui/material/Box'; +import Table from '@mui/material/Table'; +import Stack from '@mui/material/Stack'; +import Tooltip from '@mui/material/Tooltip'; +import TableRow from '@mui/material/TableRow'; +import Checkbox from '@mui/material/Checkbox'; +import TableCell from '@mui/material/TableCell'; +import TableBody from '@mui/material/TableBody'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { + useTable, + emptyRows, + getComparator, + TableEmptyRows, + TableHeadCustom, + TableSelectedAction, + TablePaginationCustom, +} from 'src/components/table'; + +function createData(name, calories, fat, carbs, protein) { + return { + name, + calories, + fat, + carbs, + protein, + }; +} + +const TABLE_DATA = [ + createData('Cupcake', 305, 3.7, 67, 4.3), + createData('Donut', 452, 25.0, 51, 4.9), + createData('Eclair', 262, 16.0, 24, 6.0), + createData('Frozen yoghurt', 159, 6.0, 24, 4.0), + createData('Gingerbread', 356, 16.0, 49, 3.9), + createData('Honeycomb', 408, 3.2, 87, 6.5), + createData('Ice cream sandwich', 237, 9.0, 37, 4.3), + createData('Jelly Bean', 375, 0.0, 94, 0.0), + createData('KitKat', 518, 26.0, 65, 7.0), + createData('Lollipop', 392, 0.2, 98, 0.0), + createData('Marshmallow', 318, 0, 81, 2.0), + createData('Nougat', 360, 19.0, 9, 37.0), +]; + +const TABLE_HEAD = [ + { id: 'name', label: 'Dessert (100g serving)', align: 'left' }, + { id: 'calories', label: 'Calories', align: 'center' }, + { id: 'fat', label: 'Fat (g)', align: 'center' }, + { id: 'carbs', label: 'Carbs (g)', align: 'center' }, + { id: 'protein', label: 'Protein (g)', align: 'center' }, +]; + +// ---------------------------------------------------------------------- + +export function SortingSelectingTable() { + const table = useTable({ defaultOrderBy: 'calories' }); + + const [tableData, setTableData] = useState([]); + + useEffect(() => { + setTableData(TABLE_DATA); + }, []); + + const dataFiltered = applyFilter({ + inputData: tableData, + comparator: getComparator(table.order, table.orderBy), + }); + + return ( +
    + + Title + + + + + + + + + + + table.onSelectAllRows( + checked, + tableData.map((row) => row.name) + ) + } + action={ + + + + + + } + /> + + + + + table.onSelectAllRows( + checked, + tableData.map((row) => row.name) + ) + } + /> + + + {dataFiltered + .slice( + table.page * table.rowsPerPage, + table.page * table.rowsPerPage + table.rowsPerPage + ) + .map((row) => ( + table.onSelectRow(row.name)} + selected={table.selected.includes(row.name)} + > + + + + {row.name} + {row.calories} + {row.fat} + {row.carbs} + {row.protein} + + ))} + + + +
    +
    +
    + + +
    + ); +} + +function applyFilter({ inputData, comparator }) { + const stabilizedThis = inputData.map((el, index) => [el, index]); + + stabilizedThis.sort((a, b) => { + const order = comparator(a[0], b[0]); + + if (order !== 0) return order; + + return a[1] - b[1]; + }); + + inputData = stabilizedThis.map((el) => el[0]); + + return inputData; +} diff --git a/front_minimal/src/sections/_examples/mui/table-view/utils.js b/front_minimal/src/sections/_examples/mui/table-view/utils.js new file mode 100644 index 0000000..c438bcc --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/table-view/utils.js @@ -0,0 +1,16 @@ +// ---------------------------------------------------------------------- + +export function createData(name, calories, fat, carbs, protein, price) { + return { + name, + calories, + fat, + carbs, + protein, + price, + history: [ + { date: '2020-01-05', customerId: '11091700', amount: 3 }, + { date: '2020-01-02', customerId: 'Anonymous', amount: 1 }, + ], + }; +} diff --git a/front_minimal/src/sections/_examples/mui/table-view/view.jsx b/front_minimal/src/sections/_examples/mui/table-view/view.jsx new file mode 100644 index 0000000..0869a34 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/table-view/view.jsx @@ -0,0 +1,76 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { BasicTable } from './basic'; +import { CollapsibleTable } from './collapsible'; +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { SortingSelectingTable } from './sorting-selecting'; +import { ScrollToViewTemplate } from '../../component-template'; +import { GroupingFixedHeaderTable } from './grouping-fixed-header'; + +// ---------------------------------------------------------------------- + +const blockProps = { + p: 0, + overflow: 'hidden', + alignItems: 'unset', + flexDirection: 'column', + bgcolor: 'background.paper', +}; + +const DEMO = [ + { + name: 'Basic Table', + component: ( + + + + ), + }, + { + name: 'Sorting & selecting', + component: ( + + + + ), + }, + { + name: 'Grouping & fixed header', + component: ( + + + + ), + }, + { + name: 'Collapsible table', + component: ( + + + + ), + }, +]; + +// ---------------------------------------------------------------------- + +export function TableView() { + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/tabs-view/index.js b/front_minimal/src/sections/_examples/mui/tabs-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/tabs-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/tabs-view/view.jsx b/front_minimal/src/sections/_examples/mui/tabs-view/view.jsx new file mode 100644 index 0000000..ed15b6e --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/tabs-view/view.jsx @@ -0,0 +1,216 @@ +'use client'; + +import { Fragment } from 'react'; + +import Tab from '@mui/material/Tab'; +import Tabs from '@mui/material/Tabs'; +import Paper from '@mui/material/Paper'; + +import { paths } from 'src/routes/paths'; + +import { useTabs } from 'src/hooks/use-tabs'; + +import { Iconify } from 'src/components/iconify'; +import { CustomTabs } from 'src/components/custom-tabs'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const TABS = [ + { value: 'one', icon: , label: 'Item one' }, + { value: 'two', icon: , label: 'Item two' }, + { + value: 'three', + icon: , + label: 'Item three', + disabled: true, + }, + { value: 'four', icon: , label: 'Item four' }, + { + value: 'five', + icon: , + label: 'Item five', + disabled: true, + }, + { value: 'six', icon: , label: 'Item six' }, + { value: 'seven', icon: , label: 'Item seven' }, +]; + +// ---------------------------------------------------------------------- + +export function TabsView() { + const basicTabs = useTabs('one'); + + const customTabs = useTabs('one'); + + const scrollableTabs = useTabs('one'); + + const DEMO = [ + { + name: 'Text', + component: ( + + + {TABS.slice(0, 3).map((tab) => ( + + ))} + + + + {TABS.slice(0, 3).map((tab) => + tab.value === basicTabs.value ? ( + {tab.label} + ) : null + )} + + + ), + }, + { + name: 'Icon', + component: ( + + + {TABS.slice(0, 3).map((tab) => ( + + ))} + + + ), + }, + { + name: 'Top', + component: ( + + + {TABS.slice(0, 3).map((tab) => ( + + ))} + + + ), + }, + { + name: 'Bottom', + component: ( + + + {TABS.slice(0, 3).map((tab) => ( + + ))} + + + ), + }, + { + name: 'Start', + component: ( + + + {TABS.slice(0, 3).map((tab) => ( + + ))} + + + ), + }, + { + name: 'End', + component: ( + + + {TABS.slice(0, 3).map((tab) => ( + + ))} + + + ), + }, + { + name: 'Scrollable', + component: ( + + + {TABS.map((tab) => ( + + ))} + + + ), + }, + { + name: 'Custom', + component: ( + + + {TABS.map((tab) => ( + + ))} + + + + {TABS.map((tab) => + tab.value === basicTabs.value ? ( + {tab.label} + ) : null + )} + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/textfield-view/index.js b/front_minimal/src/sections/_examples/mui/textfield-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/textfield-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/textfield-view/textfield.jsx b/front_minimal/src/sections/_examples/mui/textfield-view/textfield.jsx new file mode 100644 index 0000000..84e4e14 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/textfield-view/textfield.jsx @@ -0,0 +1,286 @@ +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import MenuItem from '@mui/material/MenuItem'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { Iconify } from 'src/components/iconify'; + +import { ComponentBlock } from '../../component-block'; + +// ---------------------------------------------------------------------- + +const CURRENCIES = [ + { value: 'USD', label: '$' }, + { value: 'EUR', label: '€' }, + { value: 'BTC', label: '฿' }, + { value: 'JPY', label: '¥' }, +]; + +// ---------------------------------------------------------------------- + +export function Textfields({ variant }) { + const [currency, setCurrency] = useState('EUR'); + + const [values, setValues] = useState({ + amount: '', + password: '', + weight: '', + weightRange: '', + showPassword: false, + }); + + const handleChangeCurrency = useCallback((event) => { + setCurrency(event.target.value); + }, []); + + const handleChange = (prop) => (event) => { + setValues({ ...values, [prop]: event.target.value }); + }; + + const handleShowPassword = useCallback(() => { + setValues({ ...values, showPassword: !values.showPassword }); + }, [values]); + + const handleMouseDownPassword = useCallback((event) => { + event.preventDefault(); + }, []); + + const blockProps = { + gap: 3, + flexDirection: 'column', + }; + + return ( + + + + + + + + + + + + + + + + ), + }} + /> + + + + + ), + }} + /> + + Kg }} + /> + + Kg }} + /> + + + + + ), + endAdornment: ( + + + {values.showPassword ? ( + + ) : ( + + )} + + + ), + }} + /> + + + + + + + + + + + + + + + + + + + + + + + + + {CURRENCIES.map((option) => ( + + {option.label} + + ))} + + + + {CURRENCIES.map((option) => ( + + ))} + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/textfield-view/view.jsx b/front_minimal/src/sections/_examples/mui/textfield-view/view.jsx new file mode 100644 index 0000000..4eb4f0e --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/textfield-view/view.jsx @@ -0,0 +1,33 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { Textfields } from './textfield'; +import { ComponentHero } from '../../component-hero'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +export function TextfieldView() { + const DEMO = [ + { name: 'Outlined', component: }, + { name: 'Filled', component: }, + { name: 'Standard', component: }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/timeline-view/index.js b/front_minimal/src/sections/_examples/mui/timeline-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/timeline-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/timeline-view/view.jsx b/front_minimal/src/sections/_examples/mui/timeline-view/view.jsx new file mode 100644 index 0000000..a1cb3cf --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/timeline-view/view.jsx @@ -0,0 +1,253 @@ +'use client'; + +import Paper from '@mui/material/Paper'; +import Timeline from '@mui/lab/Timeline'; +import TimelineDot from '@mui/lab/TimelineDot'; +import TimelineItem from '@mui/lab/TimelineItem'; +import Typography from '@mui/material/Typography'; +import TimelineContent from '@mui/lab/TimelineContent'; +import TimelineSeparator from '@mui/lab/TimelineSeparator'; +import TimelineConnector from '@mui/lab/TimelineConnector'; +import TimelineOppositeContent from '@mui/lab/TimelineOppositeContent'; + +import { paths } from 'src/routes/paths'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +const TIMELINES = [ + { + key: 1, + title: 'Default', + des: 'Morbi mattis ullamcorper', + time: '09:30 am', + icon: , + }, + { + key: 2, + title: 'Primary', + des: 'Morbi mattis ullamcorper', + time: '10:00 am', + color: 'primary', + icon: , + }, + { + key: 3, + title: 'Secondary', + des: 'Morbi mattis ullamcorper', + time: '10:00 am', + color: 'secondary', + icon: , + }, + { + key: 4, + title: 'Info', + des: 'Morbi mattis ullamcorper', + time: '10:30 am', + color: 'info', + icon: , + }, + { + key: 5, + title: 'Success', + des: 'Morbi mattis ullamcorper', + time: '11:00 am', + color: 'success', + icon: , + }, + { + key: 6, + title: 'Warning', + des: 'Morbi mattis ullamcorper', + time: '11:30 am', + color: 'warning', + icon: , + }, + { + key: 7, + title: 'Error', + des: 'Morbi mattis ullamcorper', + time: '12:00 am', + color: 'error', + icon: , + }, +]; + +// ---------------------------------------------------------------------- + +export function TimelineView() { + const lastItem = TIMELINES[TIMELINES.length - 1].key; + + const reduceTimeLine = TIMELINES.slice(TIMELINES.length - 3); + + const DEMO = [ + { + name: 'Left', + component: ( + + + {reduceTimeLine.map((item) => ( + + + + {lastItem === item.key ? null : } + + {item.title} + + ))} + + + ), + }, + { + name: 'Right', + component: ( + + + {reduceTimeLine.map((item) => ( + + + + {lastItem === item.key ? null : } + + {item.title} + + ))} + + + ), + }, + { + name: 'Alternating', + component: ( + + + {reduceTimeLine.map((item) => ( + + + + {lastItem === item.key ? null : } + + {item.title} + + ))} + + + ), + }, + { + name: 'Filled', + component: ( + + + {TIMELINES.map((item) => ( + + + + {lastItem === item.key ? null : } + + {item.title} + + ))} + + + ), + }, + { + name: 'Outlined', + component: ( + + + {TIMELINES.map((item) => ( + + + + {lastItem === item.key ? null : } + + {item.title} + + ))} + + + ), + }, + { + name: 'Opposite content', + component: ( + + + {TIMELINES.map((item) => ( + + + {item.time} + + + + {lastItem === item.key ? null : } + + + {item.title} + + + ))} + + + ), + }, + { + name: 'Customized', + component: ( + + + {TIMELINES.map((item) => ( + + + + {item.time} + + + + {item.icon} + + + + varAlpha(theme.vars.palette.grey['500Channel'], 0.12), + }} + > + {item.title} + + {item.des} + + + + + ))} + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/tooltip-view/index.js b/front_minimal/src/sections/_examples/mui/tooltip-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/tooltip-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/tooltip-view/view.jsx b/front_minimal/src/sections/_examples/mui/tooltip-view/view.jsx new file mode 100644 index 0000000..386c613 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/tooltip-view/view.jsx @@ -0,0 +1,204 @@ +'use client'; + +import { m } from 'framer-motion'; + +import Fab from '@mui/material/Fab'; +import Zoom from '@mui/material/Zoom'; +import Fade from '@mui/material/Fade'; +import Button from '@mui/material/Button'; +import { styled } from '@mui/material/styles'; +import IconButton from '@mui/material/IconButton'; +import Tooltip, { tooltipClasses } from '@mui/material/Tooltip'; + +import { paths } from 'src/routes/paths'; + +import { Iconify } from 'src/components/iconify'; +import { varHover } from 'src/components/animate'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +const LONG_TEXT = ` +Aliquam eget finibus ante, non facilisis lectus. Sed vitae dignissim est, vel aliquam tellus. +Praesent non nunc mollis, fermentum neque at, semper arcu. +Nullam eget est sed sem iaculis gravida eget vitae justo. +`; + +// ---------------------------------------------------------------------- + +const CustomWidthTooltip = styled(({ className, ...props }) => ( + +))({ [`& .${tooltipClasses.tooltip}`]: { maxWidth: 500 } }); + +const NoMaxWidthTooltip = styled(({ className, ...props }) => ( + +))({ [`& .${tooltipClasses.tooltip}`]: { maxWidth: 'none' } }); + +// ---------------------------------------------------------------------- + +export function TooltipView() { + const DEMO = [ + { + name: 'Simple', + component: ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ), + }, + { + name: 'Arrow', + component: ( + + + + + + + + ), + }, + { + name: 'Variable width', + component: ( + + + + + + + + + + + + + + ), + }, + { + name: 'Transitions', + component: ( + + + + + + + + + + + + + + ), + }, + { + name: 'Positioned', + component: ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/transfer-list-view/enhanced-transfer-list.jsx b/front_minimal/src/sections/_examples/mui/transfer-list-view/enhanced-transfer-list.jsx new file mode 100644 index 0000000..8a3032b --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/transfer-list-view/enhanced-transfer-list.jsx @@ -0,0 +1,152 @@ +import { useState } from 'react'; + +import List from '@mui/material/List'; +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import Checkbox from '@mui/material/Checkbox'; +import Grid from '@mui/material/Unstable_Grid2'; +import CardHeader from '@mui/material/CardHeader'; +import ListItemText from '@mui/material/ListItemText'; +import ListItemIcon from '@mui/material/ListItemIcon'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +function not(a, b) { + return a.filter((value) => b.indexOf(value) === -1); +} + +function intersection(a, b) { + return a.filter((value) => b.indexOf(value) !== -1); +} + +function union(a, b) { + return [...a, ...not(b, a)]; +} + +// ---------------------------------------------------------------------- + +export function EnhancedTransferList() { + const [checked, setChecked] = useState([]); + + const [left, setLeft] = useState([0, 1, 2, 3]); + + const [right, setRight] = useState([4, 5, 6, 7]); + + const leftChecked = intersection(checked, left); + + const rightChecked = intersection(checked, right); + + const handleToggle = (value) => () => { + const currentIndex = checked.indexOf(value); + + const newChecked = [...checked]; + + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + + setChecked(newChecked); + }; + + const numberOfChecked = (items) => intersection(checked, items).length; + + const handleToggleAll = (items) => () => { + if (numberOfChecked(items) === items.length) { + setChecked(not(checked, items)); + } else { + setChecked(union(checked, items)); + } + }; + + const handleCheckedRight = () => { + setRight(right.concat(leftChecked)); + setLeft(not(left, leftChecked)); + setChecked(not(checked, leftChecked)); + }; + + const handleCheckedLeft = () => { + setLeft(left.concat(rightChecked)); + setRight(not(right, rightChecked)); + setChecked(not(checked, rightChecked)); + }; + + const customList = (title, items) => ( + + + } + title={title} + subheader={`${numberOfChecked(items)}/${items.length} selected`} + sx={{ p: 2 }} + /> + + + + + {items.map((value) => ( + + + + + + + ))} + + + ); + + return ( + + {customList('Choices', left)} + + + + + + + + {customList('Chosen', right)} + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/transfer-list-view/index.js b/front_minimal/src/sections/_examples/mui/transfer-list-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/transfer-list-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/transfer-list-view/simple-transfer-list.jsx b/front_minimal/src/sections/_examples/mui/transfer-list-view/simple-transfer-list.jsx new file mode 100644 index 0000000..6cbe74c --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/transfer-list-view/simple-transfer-list.jsx @@ -0,0 +1,147 @@ +import { useState } from 'react'; + +import List from '@mui/material/List'; +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; +import Checkbox from '@mui/material/Checkbox'; +import Grid from '@mui/material/Unstable_Grid2'; +import ListItemIcon from '@mui/material/ListItemIcon'; +import ListItemText from '@mui/material/ListItemText'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +function not(a, b) { + return a.filter((value) => b.indexOf(value) === -1); +} + +function intersection(a, b) { + return a.filter((value) => b.indexOf(value) !== -1); +} + +// ---------------------------------------------------------------------- + +export function SimpleTransferList() { + const [checked, setChecked] = useState([]); + + const [left, setLeft] = useState([0, 1, 2, 3]); + + const [right, setRight] = useState([4, 5, 6, 7]); + + const leftChecked = intersection(checked, left); + + const rightChecked = intersection(checked, right); + + const handleToggle = (value) => () => { + const currentIndex = checked.indexOf(value); + const newChecked = [...checked]; + if (currentIndex === -1) { + newChecked.push(value); + } else { + newChecked.splice(currentIndex, 1); + } + setChecked(newChecked); + }; + + const handleAllRight = () => { + setRight(right.concat(left)); + setLeft([]); + }; + + const handleCheckedRight = () => { + setRight(right.concat(leftChecked)); + setLeft(not(left, leftChecked)); + setChecked(not(checked, leftChecked)); + }; + + const handleCheckedLeft = () => { + setLeft(left.concat(rightChecked)); + setRight(not(right, rightChecked)); + setChecked(not(checked, rightChecked)); + }; + + const handleAllLeft = () => { + setLeft(left.concat(right)); + setRight([]); + }; + + const customList = (items) => ( + + + {items.map((value) => { + const labelId = `transfer-list-item-${value}-label`; + return ( + + + + + + + ); + })} + + + ); + + return ( + + {customList(left)} + + + + + + + + + {customList(right)} + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/transfer-list-view/view.jsx b/front_minimal/src/sections/_examples/mui/transfer-list-view/view.jsx new file mode 100644 index 0000000..153cfdf --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/transfer-list-view/view.jsx @@ -0,0 +1,48 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { SimpleTransferList } from './simple-transfer-list'; +import { ScrollToViewTemplate } from '../../component-template'; +import { EnhancedTransferList } from './enhanced-transfer-list'; + +// ---------------------------------------------------------------------- + +export function TransferListView() { + const DEMO = [ + { + name: 'Simple', + component: ( + + + + ), + }, + { + name: 'Enhanced', + component: ( + + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/tree-view/basic.jsx b/front_minimal/src/sections/_examples/mui/tree-view/basic.jsx new file mode 100644 index 0000000..d1e072d --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/tree-view/basic.jsx @@ -0,0 +1,51 @@ +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import { RichTreeView } from '@mui/x-tree-view/RichTreeView'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; + +// ---------------------------------------------------------------------- + +const MUI_X_PRODUCTS = [ + { + id: 'grid', + label: 'Data Grid', + children: [ + { id: 'grid-community', label: '@mui/x-data-grid' }, + { id: 'grid-pro', label: '@mui/x-data-grid-pro' }, + { id: 'grid-premium', label: '@mui/x-data-grid-premium' }, + ], + }, + { + id: 'pickers', + label: 'Date and Time Pickers', + children: [ + { id: 'pickers-community', label: '@mui/x-date-pickers' }, + { id: 'pickers-pro', label: '@mui/x-date-pickers-pro' }, + ], + }, +]; + +// ---------------------------------------------------------------------- + +export function BasicRichTree() { + return ( + + ); +} + +// ---------------------------------------------------------------------- + +export function BasicSimpleTree() { + return ( + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/tree-view/custom-icon.jsx b/front_minimal/src/sections/_examples/mui/tree-view/custom-icon.jsx new file mode 100644 index 0000000..3516f61 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/tree-view/custom-icon.jsx @@ -0,0 +1,55 @@ +import SvgIcon from '@mui/material/SvgIcon'; +import { TreeItem } from '@mui/x-tree-view/TreeItem'; +import { SimpleTreeView } from '@mui/x-tree-view/SimpleTreeView'; + +// ---------------------------------------------------------------------- + +const TreeViewCollapseIcon = (props) => ( + + + +); + +const TreeViewExpandIcon = (props) => ( + + + +); + +const TreeViewEndIcon = ({ ...props }) => ( + + + +); + +// ---------------------------------------------------------------------- + +export function CustomIcons() { + return ( + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/tree-view/custom-styling.jsx b/front_minimal/src/sections/_examples/mui/tree-view/custom-styling.jsx new file mode 100644 index 0000000..b7d9dba --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/tree-view/custom-styling.jsx @@ -0,0 +1,74 @@ +import { styled } from '@mui/material/styles'; +import { RichTreeView } from '@mui/x-tree-view/RichTreeView'; +import { TreeItem, treeItemClasses } from '@mui/x-tree-view/TreeItem'; + +import { varAlpha, stylesMode } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +const ITEMS = [ + { + id: '1', + label: 'Main', + children: [ + { id: '2', label: 'Hello' }, + { + id: '3', + label: 'Subtree with children', + children: [ + { id: '6', label: 'Hello' }, + { + id: '7', + label: 'Sub-subtree with children', + children: [ + { id: '9', label: 'Child 1' }, + { id: '10', label: 'Child 2' }, + { id: '11', label: 'Child 3' }, + ], + }, + { id: '8', label: 'Hello' }, + ], + }, + { id: '4', label: 'World' }, + { id: '5', label: 'Something something' }, + ], + }, +]; + +const StyledTreeItem = styled(TreeItem)(({ theme }) => ({ + color: theme.vars.palette.grey[800], + [stylesMode.dark]: { color: theme.vars.palette.grey[200] }, + [`& .${treeItemClasses.content}`]: { + borderRadius: theme.spacing(0.5), + padding: theme.spacing(0.5, 1), + margin: theme.spacing(0.2, 0), + [`& .${treeItemClasses.label}`]: { fontSize: '0.8rem', fontWeight: 500 }, + }, + [`& .${treeItemClasses.iconContainer}`]: { + borderRadius: '50%', + backgroundColor: varAlpha(theme.vars.palette.primary.mainChannel, 0.25), + [stylesMode.dark]: { + color: theme.vars.palette.primary.contrastText, + backgroundColor: theme.vars.palette.primary.dark, + }, + }, + [`& .${treeItemClasses.groupTransition}`]: { + marginLeft: 15, + paddingLeft: 18, + borderLeft: `1px dashed ${varAlpha(theme.vars.palette.text.primaryChannel, 0.4)}`, + }, +})); + +// ---------------------------------------------------------------------- + +export function CustomStyling() { + return ( + + ); +} diff --git a/front_minimal/src/sections/_examples/mui/tree-view/index.js b/front_minimal/src/sections/_examples/mui/tree-view/index.js new file mode 100644 index 0000000..5638cb2 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/tree-view/index.js @@ -0,0 +1 @@ +export * from './view'; diff --git a/front_minimal/src/sections/_examples/mui/tree-view/view.jsx b/front_minimal/src/sections/_examples/mui/tree-view/view.jsx new file mode 100644 index 0000000..19fc4d7 --- /dev/null +++ b/front_minimal/src/sections/_examples/mui/tree-view/view.jsx @@ -0,0 +1,65 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { CustomIcons } from './custom-icon'; +import { CustomStyling } from './custom-styling'; +import { ComponentHero } from '../../component-hero'; +import { ComponentBlock } from '../../component-block'; +import { BasicRichTree, BasicSimpleTree } from './basic'; +import { ScrollToViewTemplate } from '../../component-template'; + +// ---------------------------------------------------------------------- + +export function TreeView() { + const DEMO = [ + { + name: 'Simple tree view', + component: ( + + + + ), + }, + { + name: 'Rich tree view', + component: ( + + + + ), + }, + { + name: 'Custom styling', + component: ( + + + + ), + }, + { + name: 'Custom icon', + component: ( + + + + ), + }, + ]; + + return ( + <> + + + + + + + ); +} diff --git a/front_minimal/src/sections/_examples/view.jsx b/front_minimal/src/sections/_examples/view.jsx new file mode 100644 index 0000000..c17c571 --- /dev/null +++ b/front_minimal/src/sections/_examples/view.jsx @@ -0,0 +1,139 @@ +'use client'; + +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { orderBy } from 'src/utils/helper'; + +import { varFade, MotionContainer } from 'src/components/animate'; + +import { ComponentNav } from './component-nav'; +import { ComponentCard } from './component-card'; +import { ComponentHero } from './component-hero'; +import { muiNav, extraNav, foundationNav } from './config-nav'; + +// ---------------------------------------------------------------------- + +export function ComponentsView() { + return ( + <> + + + + + Components + + + + + + With huge resource pack making deployment easy and expanding more effectively + + + + + + + + + + }> + + + Foundation + + + Colors, typography, shadows… + + + + + {foundationNav.map((item) => ( + + ))} + + + + + + MUI + + + Components from{' '} + + Material UI + + . + + + + + Some advanced components from MUI X will not be included. So you need to + purchase a separate + + license + + . + + + + + + {orderBy(muiNav, ['name'], ['asc']).map((item) => ( + + ))} + + + + + + Extra Components + + + Some custom components / use 3rd party dependencies (chart, map, editor…). + + + + + {orderBy(extraNav, ['name'], ['asc']).map((item) => ( + + ))} + + + + + + + ); +} + +// ---------------------------------------------------------------------- + +function Grid({ children }) { + return ( + + {children} + + ); +} diff --git a/front_minimal/src/sections/about/about-hero.jsx b/front_minimal/src/sections/about/about-hero.jsx new file mode 100644 index 0000000..2c10434 --- /dev/null +++ b/front_minimal/src/sections/about/about-hero.jsx @@ -0,0 +1,60 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { CONFIG } from 'src/config-global'; + +import { varFade, AnimateText, MotionContainer, animateTextClasses } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export function AboutHero() { + return ( + + + + + + + + Let's work together and +
    make awesome site easily +
    +
    +
    +
    +
    + ); +} diff --git a/front_minimal/src/sections/about/about-team.jsx b/front_minimal/src/sections/about/about-team.jsx new file mode 100644 index 0000000..facd54a --- /dev/null +++ b/front_minimal/src/sections/about/about-team.jsx @@ -0,0 +1,111 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { _socials, _carouselsMembers } from 'src/_mock'; + +import { Image } from 'src/components/image'; +import { Iconify, SocialIcon } from 'src/components/iconify'; +import { varFade, MotionViewport } from 'src/components/animate'; +import { Carousel, useCarousel, CarouselArrowFloatButtons } from 'src/components/carousel'; + +// ---------------------------------------------------------------------- + +export function AboutTeam() { + const carousel = useCarousel({ + align: 'start', + slideSpacing: '24px', + slidesToShow: { xs: 1, sm: 2, md: 3, lg: 4 }, + }); + + return ( + + + + Dream team + + + + + + Great team is the key + + + + + + Minimal will provide you support if you have any problems, our support team will reply + within a day and we also have detailed documentation. + + + + + + + + {_carouselsMembers.map((member) => ( + + + + ))} + + + + + + ); +} + +// ---------------------------------------------------------------------- + +function MemberCard({ member }) { + return ( + + + {member.name} + + + + {member.role} + + + + {member.name} + + + + {_socials.map((social) => ( + + + + ))} + + + ); +} diff --git a/front_minimal/src/sections/about/about-testimonials.jsx b/front_minimal/src/sections/about/about-testimonials.jsx new file mode 100644 index 0000000..f1d7a25 --- /dev/null +++ b/front_minimal/src/sections/about/about-testimonials.jsx @@ -0,0 +1,175 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Masonry from '@mui/lab/Masonry'; +import Stack from '@mui/material/Stack'; +import Rating from '@mui/material/Rating'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Container from '@mui/material/Container'; +import Grid from '@mui/material/Unstable_Grid2'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +import { fDate } from 'src/utils/format-time'; + +import { _testimonials } from 'src/_mock'; +import { CONFIG } from 'src/config-global'; +import { bgBlur, varAlpha, bgGradient, hideScrollY } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { varFade, MotionViewport } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export function AboutTestimonials() { + const theme = useTheme(); + + const mdUp = useResponsive('up', 'md'); + + const renderLink = ( + + ); + + const renderDescription = ( + + + + Testimonials + + + + + + Who love
    + my work +
    +
    + + + + Our goal is to create a product and service that you’re satisfied with and use it every + day. This is why we’re constantly working on our services to make it better every day and + really listen to what our users has to say. + + + + {!mdUp && ( + + {renderLink} + + )} +
    + ); + + const renderContent = ( + + + {_testimonials.map((testimonial) => ( + + + + ))} + + + ); + + return ( + + + + + {renderDescription} + + + + {renderContent} + + + + {mdUp && ( + + {renderLink} + + )} + + + ); +} + +function TestimonialCard({ testimonial, sx, ...other }) { + const theme = useTheme(); + + const { name, ratingNumber, postedDate, content, avatarUrl } = testimonial; + + return ( + + + + {content} + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/about/about-vision.jsx b/front_minimal/src/sections/about/about-vision.jsx new file mode 100644 index 0000000..c8b85fa --- /dev/null +++ b/front_minimal/src/sections/about/about-vision.jsx @@ -0,0 +1,108 @@ +import { m } from 'framer-motion'; + +import Fab from '@mui/material/Fab'; +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Container from '@mui/material/Container'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha } from 'src/theme/styles'; + +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; +import { varFade, MotionViewport } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export function AboutVision() { + const theme = useTheme(); + + const renderImg = ( + about-vision + ); + + const renderLogos = ( + + {['ibm', 'lya', 'spotify', 'netflix', 'hbo', 'amazon'].map((logo) => ( + + ))} + + ); + + return ( + + + + {renderImg} + + {renderLogos} + + + + + + + + + Our vision offering the best product nulla vehicula tortor scelerisque ultrices + malesuada. + + + + + ); +} diff --git a/front_minimal/src/sections/about/about-what.jsx b/front_minimal/src/sections/about/about-what.jsx new file mode 100644 index 0000000..ee8a038 --- /dev/null +++ b/front_minimal/src/sections/about/about-what.jsx @@ -0,0 +1,139 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import Grid from '@mui/material/Unstable_Grid2'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; +import LinearProgress from '@mui/material/LinearProgress'; + +import { fPercent } from 'src/utils/format-number'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, stylesMode } from 'src/theme/styles'; + +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; +import { varFade, MotionViewport } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export const SKILLS = [...Array(3)].map((_, index) => ({ + label: ['Development', 'Design', 'Marketing'][index], + value: [20, 40, 60][index], +})); + +// ---------------------------------------------------------------------- + +export function AboutWhat() { + const theme = useTheme(); + + return ( + + + + + + Our office small + + + + + + Our office large + + + + + + + + What is Minimal? + + + + + + Our theme is the most advanced and user-friendly theme you will find on the market, we + have documentation and video to help set your site really easily, pre-installed demos + you can import in one click and everything from the theme options to page content can + be edited from the front-end. This is the theme you are looking for. + + + + + {SKILLS.map((progress, index) => ( + + + + {progress.label} + + + + {fPercent(progress.value)} + + + + + + ))} + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/about/view/about-view.jsx b/front_minimal/src/sections/about/view/about-view.jsx new file mode 100644 index 0000000..35f7f1e --- /dev/null +++ b/front_minimal/src/sections/about/view/about-view.jsx @@ -0,0 +1,25 @@ +'use client'; + +import { AboutHero } from '../about-hero'; +import { AboutWhat } from '../about-what'; +import { AboutTeam } from '../about-team'; +import { AboutVision } from '../about-vision'; +import { AboutTestimonials } from '../about-testimonials'; + +// ---------------------------------------------------------------------- + +export function AboutView() { + return ( + <> + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/about/view/index.js b/front_minimal/src/sections/about/view/index.js new file mode 100644 index 0000000..dbce7c9 --- /dev/null +++ b/front_minimal/src/sections/about/view/index.js @@ -0,0 +1 @@ +export * from './about-view'; diff --git a/front_minimal/src/sections/account/account-billing-address.jsx b/front_minimal/src/sections/account/account-billing-address.jsx new file mode 100644 index 0000000..864a197 --- /dev/null +++ b/front_minimal/src/sections/account/account-billing-address.jsx @@ -0,0 +1,125 @@ +import { useState, useCallback } from 'react'; + +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import CardHeader from '@mui/material/CardHeader'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +import { AddressItem, AddressNewForm } from '../address'; + +// ---------------------------------------------------------------------- + +export function AccountBillingAddress({ addressBook }) { + const [addressId, setAddressId] = useState(''); + + const popover = usePopover(); + + const addressForm = useBoolean(); + + const handleAddNewAddress = useCallback((address) => { + console.info('ADDRESS', address); + }, []); + + const handleSelectedId = useCallback( + (event, id) => { + popover.onOpen(event); + setAddressId(id); + }, + [popover] + ); + + const handleClose = useCallback(() => { + popover.onClose(); + setAddressId(''); + }, [popover]); + + return ( + <> + + } + onClick={addressForm.onTrue} + > + Address + + } + /> + + + {addressBook.map((address) => ( + { + handleSelectedId(event, `${address.id}`); + }} + sx={{ position: 'absolute', top: 8, right: 8 }} + > + + + } + sx={{ p: 2.5, borderRadius: 1 }} + /> + ))} + + + + + + { + handleClose(); + console.info('SET AS PRIMARY', addressId); + }} + > + + Set as primary + + + { + handleClose(); + console.info('EDIT', addressId); + }} + > + + Edit + + + { + handleClose(); + console.info('DELETE', addressId); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + + + ); +} diff --git a/front_minimal/src/sections/account/account-billing-history.jsx b/front_minimal/src/sections/account/account-billing-history.jsx new file mode 100644 index 0000000..6bb9610 --- /dev/null +++ b/front_minimal/src/sections/account/account-billing-history.jsx @@ -0,0 +1,72 @@ +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { fDate } from 'src/utils/format-time'; +import { fCurrency } from 'src/utils/format-number'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function AccountBillingHistory({ invoices }) { + const showMore = useBoolean(); + + return ( + + + + + {(showMore.value ? invoices : invoices.slice(0, 8)).map((invoice) => ( + + + + + {fCurrency(invoice.price)} + + + + PDF + + + ))} + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/account/account-billing-payment.jsx b/front_minimal/src/sections/account/account-billing-payment.jsx new file mode 100644 index 0000000..af337cb --- /dev/null +++ b/front_minimal/src/sections/account/account-billing-payment.jsx @@ -0,0 +1,51 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; +import CardHeader from '@mui/material/CardHeader'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; + +import { PaymentCardItem } from '../payment/payment-card-item'; +import { PaymentNewCardDialog } from '../payment/payment-new-card-dialog'; + +// ---------------------------------------------------------------------- + +export function AccountBillingPayment({ cards }) { + const newCard = useBoolean(); + + return ( + <> + + } + onClick={newCard.onTrue} + > + New Card + + } + /> + + + {cards.map((card) => ( + + ))} + + + + + + ); +} diff --git a/front_minimal/src/sections/account/account-billing-plan.jsx b/front_minimal/src/sections/account/account-billing-plan.jsx new file mode 100644 index 0000000..ca5680c --- /dev/null +++ b/front_minimal/src/sections/account/account-billing-plan.jsx @@ -0,0 +1,212 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Paper from '@mui/material/Paper'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import Grid from '@mui/material/Unstable_Grid2'; +import CardHeader from '@mui/material/CardHeader'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { PlanFreeIcon, PlanStarterIcon, PlanPremiumIcon } from 'src/assets/icons'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; + +import { AddressListDialog } from '../address'; +import { PaymentCardListDialog } from '../payment/payment-card-list-dialog'; + +// ---------------------------------------------------------------------- + +export function AccountBillingPlan({ cardList, addressBook, plans }) { + const openAddress = useBoolean(); + + const openCards = useBoolean(); + + const primaryAddress = addressBook.filter((address) => address.primary)[0]; + + const primaryCard = cardList.filter((card) => card.primary)[0]; + + const [selectedPlan, setSelectedPlan] = useState(''); + + const [selectedAddress, setSelectedAddress] = useState(primaryAddress); + + const [selectedCard, setSelectedCard] = useState(primaryCard); + + const handleSelectPlan = useCallback( + (newValue) => { + const currentPlan = plans.filter((plan) => plan.primary)[0].subscription; + if (currentPlan !== newValue) { + setSelectedPlan(newValue); + } + }, + [plans] + ); + + const handleSelectAddress = useCallback((newValue) => { + setSelectedAddress(newValue); + }, []); + + const handleSelectCard = useCallback((newValue) => { + setSelectedCard(newValue); + }, []); + + const renderPlans = plans.map((plan) => ( + + handleSelectPlan(plan.subscription)} + sx={{ + p: 2.5, + cursor: 'pointer', + position: 'relative', + ...(plan.primary && { opacity: 0.48, cursor: 'default' }), + ...(plan.subscription === selectedPlan && { + boxShadow: (theme) => `0 0 0 2px ${theme.vars.palette.text.primary}`, + }), + }} + > + {plan.primary && ( + + )} + + {plan.subscription === 'basic' && } + {plan.subscription === 'starter' && } + {plan.subscription === 'premium' && } + + + {plan.subscription} + + + + {plan.price || 'Free'} + + {!!plan.price && ( + + /mo + + )} + + + + )); + + return ( + <> + + + + + {renderPlans} + + + + + + Plan + + + {selectedPlan || '-'} + + + + + + Billing name + + + + + + + + + Billing address + + + {selectedAddress?.fullAddress} + + + + + + Billing phone number + + + {selectedAddress?.phoneNumber} + + + + + + Payment method + + + + + + + + + + + + + + + + selectedCard?.id === selectedId} + onSelect={handleSelectCard} + /> + + selectedAddress?.id === selectedId} + onSelect={handleSelectAddress} + action={ + + } + /> + + ); +} diff --git a/front_minimal/src/sections/account/account-billing.jsx b/front_minimal/src/sections/account/account-billing.jsx new file mode 100644 index 0000000..e120a10 --- /dev/null +++ b/front_minimal/src/sections/account/account-billing.jsx @@ -0,0 +1,26 @@ +import Grid from '@mui/material/Unstable_Grid2'; + +import { AccountBillingPlan } from './account-billing-plan'; +import { AccountBillingPayment } from './account-billing-payment'; +import { AccountBillingHistory } from './account-billing-history'; +import { AccountBillingAddress } from './account-billing-address'; + +// ---------------------------------------------------------------------- + +export function AccountBilling({ cards, plans, invoices, addressBook }) { + return ( + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/account/account-change-password.jsx b/front_minimal/src/sections/account/account-change-password.jsx new file mode 100644 index 0000000..8c19e06 --- /dev/null +++ b/front_minimal/src/sections/account/account-change-password.jsx @@ -0,0 +1,125 @@ +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +export const ChangePassWordSchema = zod + .object({ + oldPassword: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), + newPassword: zod.string().min(1, { message: 'New password is required!' }), + confirmNewPassword: zod.string().min(1, { message: 'Confirm password is required!' }), + }) + .refine((data) => data.oldPassword !== data.newPassword, { + message: 'New password must be different than old password', + path: ['newPassword'], + }) + .refine((data) => data.newPassword === data.confirmNewPassword, { + message: 'Passwords do not match!', + path: ['confirmNewPassword'], + }); + +// ---------------------------------------------------------------------- + +export function AccountChangePassword() { + const password = useBoolean(); + + const defaultValues = { oldPassword: '', newPassword: '', confirmNewPassword: '' }; + + const methods = useForm({ + mode: 'all', + resolver: zodResolver(ChangePassWordSchema), + defaultValues, + }); + + const { + reset, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + reset(); + toast.success('Update success!'); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + return ( +
    + + + + + + + ), + }} + /> + + + + + + + ), + }} + helperText={ + + Password must be minimum + 6+ + + } + /> + + + + + + + ), + }} + /> + + + Save changes + + +
    + ); +} diff --git a/front_minimal/src/sections/account/account-general.jsx b/front_minimal/src/sections/account/account-general.jsx new file mode 100644 index 0000000..1326812 --- /dev/null +++ b/front_minimal/src/sections/account/account-general.jsx @@ -0,0 +1,163 @@ +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; +import { isValidPhoneNumber } from 'react-phone-number-input/input'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Grid from '@mui/material/Unstable_Grid2'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { fData } from 'src/utils/format-number'; + +import { toast } from 'src/components/snackbar'; +import { Form, Field, schemaHelper } from 'src/components/hook-form'; + +import { useMockedUser } from 'src/auth/hooks'; + +// ---------------------------------------------------------------------- + +export const UpdateUserSchema = zod.object({ + displayName: zod.string().min(1, { message: 'Name is required!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + photoURL: schemaHelper.file({ + message: { required_error: 'Avatar is required!' }, + }), + phoneNumber: schemaHelper.phoneNumber({ isValidPhoneNumber }), + country: schemaHelper.objectOrNull({ + message: { required_error: 'Country is required!' }, + }), + address: zod.string().min(1, { message: 'Address is required!' }), + state: zod.string().min(1, { message: 'State is required!' }), + city: zod.string().min(1, { message: 'City is required!' }), + zipCode: zod.string().min(1, { message: 'Zip code is required!' }), + about: zod.string().min(1, { message: 'About is required!' }), + // Not required + isPublic: zod.boolean(), +}); + +export function AccountGeneral() { + const { user } = useMockedUser(); + + const defaultValues = { + displayName: user?.displayName || '', + email: user?.email || '', + photoURL: user?.photoURL || null, + phoneNumber: user?.phoneNumber || '', + country: user?.country || '', + address: user?.address || '', + state: user?.state || '', + city: user?.city || '', + zipCode: user?.zipCode || '', + about: user?.about || '', + isPublic: user?.isPublic || false, + }; + + const methods = useForm({ + mode: 'all', + resolver: zodResolver(UpdateUserSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + toast.success('Update success!'); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + return ( +
    + + + + + Allowed *.jpeg, *.jpg, *.png, *.gif +
    max size of {fData(3145728)} + + } + /> + + + + +
    +
    + + + + + + + + + + + + + + + + + + + + + Save changes + + + + +
    +
    + ); +} diff --git a/front_minimal/src/sections/account/account-notifications.jsx b/front_minimal/src/sections/account/account-notifications.jsx new file mode 100644 index 0000000..3eaaf18 --- /dev/null +++ b/front_minimal/src/sections/account/account-notifications.jsx @@ -0,0 +1,117 @@ +import { useForm, Controller } from 'react-hook-form'; + +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Switch from '@mui/material/Switch'; +import Grid from '@mui/material/Unstable_Grid2'; +import LoadingButton from '@mui/lab/LoadingButton'; +import ListItemText from '@mui/material/ListItemText'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { toast } from 'src/components/snackbar'; +import { Form } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +const NOTIFICATIONS = [ + { + subheader: 'Activity', + caption: 'Donec mi odio, faucibus at, scelerisque quis', + items: [ + { id: 'activity_comments', label: 'Email me when someone comments onmy article' }, + { id: 'activity_answers', label: 'Email me when someone answers on my form' }, + { id: 'activityFollows', label: 'Email me hen someone follows me' }, + ], + }, + { + subheader: 'Application', + caption: 'Donec mi odio, faucibus at, scelerisque quis', + items: [ + { id: 'application_news', label: 'News and announcements' }, + { id: 'application_product', label: 'Weekly product updates' }, + { id: 'application_blog', label: 'Weekly blog digest' }, + ], + }, +]; + +// ---------------------------------------------------------------------- + +export function AccountNotifications() { + const methods = useForm({ + defaultValues: { selected: ['activity_comments', 'application_product'] }, + }); + + const { + watch, + control, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const values = watch(); + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + toast.success('Update success!'); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const getSelected = (selectedItems, item) => + selectedItems.includes(item) + ? selectedItems.filter((value) => value !== item) + : [...selectedItems, item]; + + return ( +
    + + {NOTIFICATIONS.map((notification) => ( + + + + + + + + ( + <> + {notification.items.map((item) => ( + field.onChange(getSelected(values.selected, item.id))} + /> + } + sx={{ m: 0, width: 1, justifyContent: 'space-between' }} + /> + ))} + + )} + /> + + + + ))} + + + Save changes + + +
    + ); +} diff --git a/front_minimal/src/sections/account/account-social-links.jsx b/front_minimal/src/sections/account/account-social-links.jsx new file mode 100644 index 0000000..31c21e6 --- /dev/null +++ b/front_minimal/src/sections/account/account-social-links.jsx @@ -0,0 +1,61 @@ +import { useForm } from 'react-hook-form'; + +import Card from '@mui/material/Card'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { toast } from 'src/components/snackbar'; +import { SocialIcon } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export function AccountSocialLinks({ socialLinks }) { + const defaultValues = { + facebook: socialLinks.facebook || '', + instagram: socialLinks.instagram || '', + linkedin: socialLinks.linkedin || '', + twitter: socialLinks.twitter || '', + }; + + const methods = useForm({ defaultValues }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + toast.success('Update success!'); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + return ( +
    + + {Object.keys(socialLinks).map((link) => ( + + + + ), + }} + /> + ))} + + + Save changes + + +
    + ); +} diff --git a/front_minimal/src/sections/account/view/index.js b/front_minimal/src/sections/account/view/index.js new file mode 100644 index 0000000..31c1242 --- /dev/null +++ b/front_minimal/src/sections/account/view/index.js @@ -0,0 +1 @@ +export * from './user-account-view'; diff --git a/front_minimal/src/sections/account/view/user-account-view.jsx b/front_minimal/src/sections/account/view/user-account-view.jsx new file mode 100644 index 0000000..26c3b8e --- /dev/null +++ b/front_minimal/src/sections/account/view/user-account-view.jsx @@ -0,0 +1,77 @@ +'use client'; + +import Tab from '@mui/material/Tab'; +import Tabs from '@mui/material/Tabs'; + +import { paths } from 'src/routes/paths'; + +import { useTabs } from 'src/hooks/use-tabs'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { _userAbout, _userPlans, _userPayment, _userInvoices, _userAddressBook } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { AccountGeneral } from '../account-general'; +import { AccountBilling } from '../account-billing'; +import { AccountSocialLinks } from '../account-social-links'; +import { AccountNotifications } from '../account-notifications'; +import { AccountChangePassword } from '../account-change-password'; + +// ---------------------------------------------------------------------- + +const TABS = [ + { value: 'general', label: 'General', icon: }, + { value: 'billing', label: 'Billing', icon: }, + { + value: 'notifications', + label: 'Notifications', + icon: , + }, + { value: 'social', label: 'Social links', icon: }, + { value: 'security', label: 'Security', icon: }, +]; + +// ---------------------------------------------------------------------- + +export function AccountView() { + const tabs = useTabs('general'); + + return ( + + + + + {TABS.map((tab) => ( + + ))} + + + {tabs.value === 'general' && } + + {tabs.value === 'billing' && ( + + )} + + {tabs.value === 'notifications' && } + + {tabs.value === 'social' && } + + {tabs.value === 'security' && } + + ); +} diff --git a/front_minimal/src/sections/address/address-item.jsx b/front_minimal/src/sections/address/address-item.jsx new file mode 100644 index 0000000..a49d6c4 --- /dev/null +++ b/front_minimal/src/sections/address/address-item.jsx @@ -0,0 +1,51 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Paper from '@mui/material/Paper'; +import Typography from '@mui/material/Typography'; + +import { Label } from 'src/components/label'; + +// ---------------------------------------------------------------------- + +export function AddressItem({ address, action, sx, ...other }) { + return ( + + + + + {address.name} + + ({address.addressType}) + + + + {address.primary && ( + + )} + + + + {address.fullAddress} + + + + {address.phoneNumber} + + + + {action && action} + + ); +} diff --git a/front_minimal/src/sections/address/address-list-dialog.jsx b/front_minimal/src/sections/address/address-list-dialog.jsx new file mode 100644 index 0000000..c576428 --- /dev/null +++ b/front_minimal/src/sections/address/address-list-dialog.jsx @@ -0,0 +1,139 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Dialog from '@mui/material/Dialog'; +import TextField from '@mui/material/TextField'; +import ButtonBase from '@mui/material/ButtonBase'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { SearchNotFound } from 'src/components/search-not-found'; + +// ---------------------------------------------------------------------- + +export function AddressListDialog({ + list, + open, + action, + onClose, + selected, + onSelect, + title = 'Address book', +}) { + const [searchAddress, setSearchAddress] = useState(''); + + const dataFiltered = applyFilter({ inputData: list, query: searchAddress }); + + const notFound = !dataFiltered.length && !!searchAddress; + + const handleSearchAddress = useCallback((event) => { + setSearchAddress(event.target.value); + }, []); + + const handleSelectAddress = useCallback( + (address) => { + onSelect(address); + setSearchAddress(''); + onClose(); + }, + [onClose, onSelect] + ); + + const renderList = ( + + {dataFiltered.map((address) => ( + handleSelectAddress(address)} + sx={{ + py: 1, + my: 0.5, + px: 1.5, + gap: 0.5, + width: 1, + borderRadius: 1, + display: 'flex', + flexDirection: 'column', + alignItems: 'flex-start', + ...(selected(`${address.id}`) && { + bgcolor: 'action.selected', + }), + }} + > + + {address.name} + + {address.primary && } + + + {address.company && ( + {address.company} + )} + + + {address.fullAddress} + + + {address.phoneNumber && ( + + {address.phoneNumber} + + )} + + ))} + + ); + + return ( + + + {title} + + {action && action} + + + + + + + ), + }} + /> + + + {notFound ? ( + + ) : ( + renderList + )} + + ); +} + +function applyFilter({ inputData, query }) { + if (query) { + return inputData.filter( + (address) => + address.name.toLowerCase().indexOf(query.toLowerCase()) !== -1 || + address.fullAddress.toLowerCase().indexOf(query.toLowerCase()) !== -1 || + `${address.company}`.toLowerCase().indexOf(query.toLowerCase()) !== -1 + ); + } + + return inputData; +} diff --git a/front_minimal/src/sections/address/address-new-form.jsx b/front_minimal/src/sections/address/address-new-form.jsx new file mode 100644 index 0000000..884f458 --- /dev/null +++ b/front_minimal/src/sections/address/address-new-form.jsx @@ -0,0 +1,139 @@ +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; +import { isValidPhoneNumber } from 'react-phone-number-input/input'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import LoadingButton from '@mui/lab/LoadingButton'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; + +import { Form, Field, schemaHelper } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const NewAddressSchema = zod.object({ + city: zod.string().min(1, { message: 'City is required!' }), + state: zod.string().min(1, { message: 'State is required!' }), + name: zod.string().min(1, { message: 'Name is required!' }), + address: zod.string().min(1, { message: 'Address is required!' }), + zipCode: zod.string().min(1, { message: 'Zip code is required!' }), + phoneNumber: schemaHelper.phoneNumber({ isValidPhoneNumber }), + country: schemaHelper.objectOrNull({ + message: { required_error: 'Country is required!' }, + }), + // Not required + primary: zod.boolean(), + addressType: zod.string(), +}); + +export function AddressNewForm({ open, onClose, onCreate }) { + const defaultValues = { + name: '', + city: '', + state: '', + address: '', + zipCode: '', + country: '', + primary: true, + phoneNumber: '', + addressType: 'Home', + }; + + const methods = useForm({ + mode: 'all', + resolver: zodResolver(NewAddressSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + onCreate({ + name: data.name, + phoneNumber: data.phoneNumber, + fullAddress: `${data.address}, ${data.city}, ${data.state}, ${data.country}, ${data.zipCode}`, + addressType: data.addressType, + primary: data.primary, + }); + onClose(); + } catch (error) { + console.error(error); + } + }); + + return ( + +
    + New address + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Deliver to this address + + +
    +
    + ); +} diff --git a/front_minimal/src/sections/address/index.js b/front_minimal/src/sections/address/index.js new file mode 100644 index 0000000..dc39835 --- /dev/null +++ b/front_minimal/src/sections/address/index.js @@ -0,0 +1,5 @@ +export * from './address-item'; + +export * from './address-new-form'; + +export * from './address-list-dialog'; diff --git a/front_minimal/src/sections/auth-demo/centered/centered-reset-password-view.jsx b/front_minimal/src/sections/auth-demo/centered/centered-reset-password-view.jsx new file mode 100644 index 0000000..cf45b08 --- /dev/null +++ b/front_minimal/src/sections/auth-demo/centered/centered-reset-password-view.jsx @@ -0,0 +1,110 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { PasswordIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const ResetPasswordSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), +}); + +// ---------------------------------------------------------------------- + +export function CenteredResetPasswordView() { + const defaultValues = { email: '' }; + + const methods = useForm({ + resolver: zodResolver(ResetPasswordSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + <> + + + + Forgot your password? + + + {`Please enter the email address associated with your account and we'll email you a link to reset your password.`} + + + + ); + + const renderForm = ( + + + + + Send request + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth-demo/centered/centered-sign-in-view.jsx b/front_minimal/src/sections/auth-demo/centered/centered-sign-in-view.jsx new file mode 100644 index 0000000..622e26e --- /dev/null +++ b/front_minimal/src/sections/auth-demo/centered/centered-sign-in-view.jsx @@ -0,0 +1,170 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { AnimateLogo2 } from 'src/components/animate'; +import { Form, Field } from 'src/components/hook-form'; +import { Iconify, SocialIcon } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export const SignInSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function CenteredSignInView() { + const password = useBoolean(); + + const defaultValues = { email: '', password: '' }; + + const methods = useForm({ + resolver: zodResolver(SignInSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderLogo = ; + + const renderHead = ( + + Sign in to your account + + + + {`Don't have an account?`} + + + + Get started + + + + ); + + const renderForm = ( + + + + + + Forgot password? + + + + + + + + ), + }} + /> + + + + Sign in + + + ); + + const renderSignInWithSocials = ( + <> + + OR + + + + + + + + + + + + + + + + + ); + + return ( + <> + {renderLogo} + + {renderHead} + +
    + {renderForm} +
    + + {renderSignInWithSocials} + + ); +} diff --git a/front_minimal/src/sections/auth-demo/centered/centered-sign-up-view.jsx b/front_minimal/src/sections/auth-demo/centered/centered-sign-up-view.jsx new file mode 100644 index 0000000..8b980e9 --- /dev/null +++ b/front_minimal/src/sections/auth-demo/centered/centered-sign-up-view.jsx @@ -0,0 +1,194 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { AnimateLogo2 } from 'src/components/animate'; +import { Form, Field } from 'src/components/hook-form'; +import { Iconify, SocialIcon } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export const SignUpSchema = zod.object({ + firstName: zod.string().min(1, { message: 'First name is required!' }), + lastName: zod.string().min(1, { message: 'Last name is required!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function CenteredSignUpView() { + const password = useBoolean(); + + const defaultValues = { + firstName: '', + lastName: '', + email: '', + password: '', + }; + + const methods = useForm({ + resolver: zodResolver(SignUpSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderLogo = ; + + const renderHead = ( + + Get started absolutely free + + + + Already have an account? + + + + Sign in + + + + ); + + const renderForm = ( + + + + + + + + + + + + + + ), + }} + /> + + + Create account + + + ); + + const renderTerms = ( + + {'By signing up, I agree to '} + + Terms of service + + {' and '} + + Privacy policy + + . + + ); + + const renderSignInWithSocials = ( + <> + + OR + + + + + + + + + + + + + + + + + ); + + return ( + <> + {renderLogo} + + {renderHead} + +
    + {renderForm} +
    + + {renderTerms} + + {renderSignInWithSocials} + + ); +} diff --git a/front_minimal/src/sections/auth-demo/centered/centered-update-password-view.jsx b/front_minimal/src/sections/auth-demo/centered/centered-update-password-view.jsx new file mode 100644 index 0000000..7cc3a5c --- /dev/null +++ b/front_minimal/src/sections/auth-demo/centered/centered-update-password-view.jsx @@ -0,0 +1,173 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { SentIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +export const UpdatePasswordSchema = zod + .object({ + code: zod + .string() + .min(1, { message: 'Code is required!' }) + .min(6, { message: 'Code must be at least 6 characters!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), + confirmPassword: zod.string().min(1, { message: 'Confirm password is required!' }), + }) + .refine((data) => data.password === data.confirmPassword, { + message: 'Passwords do not match!', + path: ['confirmPassword'], + }); + +// ---------------------------------------------------------------------- + +export function CenteredUpdatePasswordView() { + const password = useBoolean(); + + const defaultValues = { + code: '', + email: '', + password: '', + confirmPassword: '', + }; + + const methods = useForm({ + resolver: zodResolver(UpdatePasswordSchema), + defaultValues, + }); + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + <> + + + + Request sent successfully! + + + {`We've sent a 6-digit confirmation email to your email. \nPlease enter the code in below box to verify your email.`} + + + + ); + + const renderForm = ( + + + + + + + + + + + ), + }} + /> + + + + + + + ), + }} + /> + + + Update password + + + + {`Don’t have a code? `} + + Resend code + + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth-demo/centered/centered-verify-view.jsx b/front_minimal/src/sections/auth-demo/centered/centered-verify-view.jsx new file mode 100644 index 0000000..e568a1e --- /dev/null +++ b/front_minimal/src/sections/auth-demo/centered/centered-verify-view.jsx @@ -0,0 +1,120 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { EmailInboxIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +export const VerifySchema = zod.object({ + code: zod + .string() + .min(1, { message: 'Code is required!' }) + .min(6, { message: 'Code must be at least 6 characters!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), +}); + +// ---------------------------------------------------------------------- + +export function CenteredVerifyView() { + const defaultValues = { code: '', email: '' }; + + const methods = useForm({ + resolver: zodResolver(VerifySchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + <> + + + + Please check your email! + + + {`We've emailed a 6-digit confirmation code. \nPlease enter the code in the box below to verify your email.`} + + + + ); + + const renderForm = ( + + + + + + + Verify + + + + {`Don’t have a code? `} + + Resend code + + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth-demo/centered/index.js b/front_minimal/src/sections/auth-demo/centered/index.js new file mode 100644 index 0000000..65ce0b4 --- /dev/null +++ b/front_minimal/src/sections/auth-demo/centered/index.js @@ -0,0 +1,9 @@ +export * from './centered-verify-view'; + +export * from './centered-sign-in-view'; + +export * from './centered-sign-up-view'; + +export * from './centered-reset-password-view'; + +export * from './centered-update-password-view'; diff --git a/front_minimal/src/sections/auth-demo/split/index.js b/front_minimal/src/sections/auth-demo/split/index.js new file mode 100644 index 0000000..9c5d914 --- /dev/null +++ b/front_minimal/src/sections/auth-demo/split/index.js @@ -0,0 +1,9 @@ +export * from './split-verify-view'; + +export * from './split-sign-in-view'; + +export * from './split-sign-up-view'; + +export * from './split-reset-password-view'; + +export * from './split-update-password-view'; diff --git a/front_minimal/src/sections/auth-demo/split/split-reset-password-view.jsx b/front_minimal/src/sections/auth-demo/split/split-reset-password-view.jsx new file mode 100644 index 0000000..01bc19a --- /dev/null +++ b/front_minimal/src/sections/auth-demo/split/split-reset-password-view.jsx @@ -0,0 +1,110 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { PasswordIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const ResetPasswordSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), +}); + +// ---------------------------------------------------------------------- + +export function SplitResetPasswordView() { + const defaultValues = { email: '' }; + + const methods = useForm({ + resolver: zodResolver(ResetPasswordSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + <> + + + + Forgot your password? + + + {`Please enter the email address associated with your account and we'll email you a link to reset your password.`} + + + + ); + + const renderForm = ( + + + + + Send request + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth-demo/split/split-sign-in-view.jsx b/front_minimal/src/sections/auth-demo/split/split-sign-in-view.jsx new file mode 100644 index 0000000..5b71de1 --- /dev/null +++ b/front_minimal/src/sections/auth-demo/split/split-sign-in-view.jsx @@ -0,0 +1,165 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Form, Field } from 'src/components/hook-form'; +import { Iconify, SocialIcon } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export const SignInSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function SplitSignInView() { + const password = useBoolean(); + + const defaultValues = { email: '', password: '' }; + + const methods = useForm({ + resolver: zodResolver(SignInSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + + Sign in to your account + + + + {`Don't have an account?`} + + + + Get started + + + + ); + + const renderForm = ( + + + + + + Forgot password? + + + + + + + + ), + }} + /> + + + + Sign in + + + ); + + const renderSignInWithSocials = ( + <> + + OR + + + + + + + + + + + + + + + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + {renderSignInWithSocials} + + ); +} diff --git a/front_minimal/src/sections/auth-demo/split/split-sign-up-view.jsx b/front_minimal/src/sections/auth-demo/split/split-sign-up-view.jsx new file mode 100644 index 0000000..d52c012 --- /dev/null +++ b/front_minimal/src/sections/auth-demo/split/split-sign-up-view.jsx @@ -0,0 +1,189 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Form, Field } from 'src/components/hook-form'; +import { Iconify, SocialIcon } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export const SignUpSchema = zod.object({ + firstName: zod.string().min(1, { message: 'First name is required!' }), + lastName: zod.string().min(1, { message: 'Last name is required!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function SplitSignUpView() { + const password = useBoolean(); + + const defaultValues = { + firstName: '', + lastName: '', + email: '', + password: '', + }; + + const methods = useForm({ + resolver: zodResolver(SignUpSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + + Get started absolutely free + + + + Already have an account? + + + + Sign in + + + + ); + + const renderForm = ( + + + + + + + + + + + + + + ), + }} + /> + + + Create account + + + ); + + const renderTerms = ( + + {'By signing up, I agree to '} + + Terms of service + + {' and '} + + Privacy policy + + . + + ); + + const renderSignInWithSocials = ( + <> + + OR + + + + + + + + + + + + + + + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + {renderTerms} + + {renderSignInWithSocials} + + ); +} diff --git a/front_minimal/src/sections/auth-demo/split/split-update-password-view.jsx b/front_minimal/src/sections/auth-demo/split/split-update-password-view.jsx new file mode 100644 index 0000000..47e5f1c --- /dev/null +++ b/front_minimal/src/sections/auth-demo/split/split-update-password-view.jsx @@ -0,0 +1,174 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { SentIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +export const UpdatePasswordSchema = zod + .object({ + code: zod + .string() + .min(1, { message: 'Code is required!' }) + .min(6, { message: 'Code must be at least 6 characters!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), + confirmPassword: zod.string().min(1, { message: 'Confirm password is required!' }), + }) + .refine((data) => data.password === data.confirmPassword, { + message: 'Passwords do not match!', + path: ['confirmPassword'], + }); + +// ---------------------------------------------------------------------- + +export function SplitUpdatePasswordView() { + const password = useBoolean(); + + const defaultValues = { + code: '', + email: '', + password: '', + confirmPassword: '', + }; + + const methods = useForm({ + resolver: zodResolver(UpdatePasswordSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + <> + + + + Request sent successfully! + + + {`We've sent a 6-digit confirmation email to your email. \nPlease enter the code in below box to verify your email.`} + + + + ); + + const renderForm = ( + + + + + + + + + + + ), + }} + /> + + + + + + + ), + }} + /> + + + Update password + + + + {`Don’t have a code? `} + + Resend code + + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth-demo/split/split-verify-view.jsx b/front_minimal/src/sections/auth-demo/split/split-verify-view.jsx new file mode 100644 index 0000000..26fe9e0 --- /dev/null +++ b/front_minimal/src/sections/auth-demo/split/split-verify-view.jsx @@ -0,0 +1,122 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { EmailInboxIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const VerifySchema = zod.object({ + code: zod + .string() + .min(1, { message: 'Code is required!' }) + .min(6, { message: 'Code must be at least 6 characters!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), +}); + +// ---------------------------------------------------------------------- + +export function SplitVerifyView() { + const defaultValues = { code: '', email: '' }; + + const methods = useForm({ + resolver: zodResolver(VerifySchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + <> + + + + Please check your email! + + + {`We've emailed a 6-digit confirmation code. \nPlease enter the code in the box below to verify your email.`} + + + + ); + + const renderForm = ( + + + + + + + Verify + + + + {`Don’t have a code? `} + + Resend code + + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth/amplify/amplify-reset-password-view.jsx b/front_minimal/src/sections/auth/amplify/amplify-reset-password-view.jsx new file mode 100644 index 0000000..1805bce --- /dev/null +++ b/front_minimal/src/sections/auth/amplify/amplify-reset-password-view.jsx @@ -0,0 +1,121 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { PasswordIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { resetPassword } from 'src/auth/context/amplify'; + +// ---------------------------------------------------------------------- + +export const ResetPasswordSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), +}); + +// ---------------------------------------------------------------------- + +export function AmplifyResetPasswordView() { + const router = useRouter(); + + const defaultValues = { + email: '', + }; + + const methods = useForm({ + resolver: zodResolver(ResetPasswordSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await resetPassword({ username: data.email }); + + const searchParams = new URLSearchParams({ email: data.email }).toString(); + + const href = `${paths.auth.amplify.updatePassword}?${searchParams}`; + router.push(href); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + <> + + + + Forgot your password? + + + {`Please enter the email address associated with your account and we'll email you a link to reset your password.`} + + + + ); + + const renderForm = ( + + + + + Send request + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth/amplify/amplify-sign-in-view.jsx b/front_minimal/src/sections/auth/amplify/amplify-sign-in-view.jsx new file mode 100644 index 0000000..691b3d1 --- /dev/null +++ b/front_minimal/src/sections/auth/amplify/amplify-sign-in-view.jsx @@ -0,0 +1,157 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useState } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Alert from '@mui/material/Alert'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { useAuthContext } from 'src/auth/hooks'; +import { signInWithPassword } from 'src/auth/context/amplify'; + +// ---------------------------------------------------------------------- + +export const SignInSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function AmplifySignInView() { + const router = useRouter(); + + const password = useBoolean(); + + const [errorMsg, setErrorMsg] = useState(''); + + const { checkUserSession } = useAuthContext(); + + const defaultValues = { + email: '', + password: '', + }; + + const methods = useForm({ + resolver: zodResolver(SignInSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await signInWithPassword({ username: data.email, password: data.password }); + await checkUserSession?.(); + + router.refresh(); + } catch (error) { + console.error(error); + setErrorMsg(error instanceof Error ? error.message : error); + } + }); + + const renderHead = ( + + Sign in to your account + + + + {`Don't have an account?`} + + + + Get started + + + + ); + + const renderForm = ( + + + + + + Forgot password? + + + + + + + + ), + }} + /> + + + + Sign in + + + ); + + return ( + <> + {renderHead} + + {!!errorMsg && ( + + {errorMsg} + + )} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth/amplify/amplify-sign-up-view.jsx b/front_minimal/src/sections/auth/amplify/amplify-sign-up-view.jsx new file mode 100644 index 0000000..22f8e0c --- /dev/null +++ b/front_minimal/src/sections/auth/amplify/amplify-sign-up-view.jsx @@ -0,0 +1,183 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useState } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Alert from '@mui/material/Alert'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { signUp } from 'src/auth/context/amplify'; + +// ---------------------------------------------------------------------- + +export const SignUpSchema = zod.object({ + firstName: zod.string().min(1, { message: 'First name is required!' }), + lastName: zod.string().min(1, { message: 'Last name is required!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function AmplifySignUpView() { + const [errorMsg, setErrorMsg] = useState(''); + + const router = useRouter(); + + const password = useBoolean(); + + const defaultValues = { + firstName: '', + lastName: '', + email: '', + password: '', + }; + + const methods = useForm({ + resolver: zodResolver(SignUpSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await signUp({ + username: data.email, + password: data.password, + firstName: data.firstName, + lastName: data.lastName, + }); + + const searchParams = new URLSearchParams({ email: data.email }).toString(); + + const href = `${paths.auth.amplify.verify}?${searchParams}`; + + router.push(href); + } catch (error) { + console.error(error); + setErrorMsg(error instanceof Error ? error.message : error); + } + }); + + const renderHead = ( + + Get started absolutely free + + + + Already have an account? + + + + Sign in + + + + ); + + const renderForm = ( + + + + + + + + + + + + + + ), + }} + /> + + + Create account + + + ); + + const renderTerms = ( + + {'By signing up, I agree to '} + + Terms of service + + {' and '} + + Privacy policy + + . + + ); + + return ( + <> + {renderHead} + + {!!errorMsg && ( + + {errorMsg} + + )} + +
    + {renderForm} +
    + + {renderTerms} + + ); +} diff --git a/front_minimal/src/sections/auth/amplify/amplify-update-password-view.jsx b/front_minimal/src/sections/auth/amplify/amplify-update-password-view.jsx new file mode 100644 index 0000000..236fb1f --- /dev/null +++ b/front_minimal/src/sections/auth/amplify/amplify-update-password-view.jsx @@ -0,0 +1,212 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useCallback } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; +import { useRouter, useSearchParams } from 'src/routes/hooks'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useCountdownSeconds } from 'src/hooks/use-countdown'; + +import { SentIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { resetPassword, updatePassword } from 'src/auth/context/amplify'; + +export const UpdatePasswordSchema = zod + .object({ + code: zod + .string() + .min(1, { message: 'Code is required!' }) + .min(6, { message: 'Code must be at least 6 characters!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), + confirmPassword: zod.string().min(1, { message: 'Confirm password is required!' }), + }) + .refine((data) => data.password === data.confirmPassword, { + message: 'Passwords do not match!', + path: ['confirmPassword'], + }); + +// ---------------------------------------------------------------------- + +export function AmplifyUpdatePasswordView() { + const router = useRouter(); + + const searchParams = useSearchParams(); + + const email = searchParams.get('email'); + + const password = useBoolean(); + + const { countdown, counting, startCountdown } = useCountdownSeconds(60); + + const defaultValues = { + code: '', + email: email || '', + password: '', + confirmPassword: '', + }; + + const methods = useForm({ + resolver: zodResolver(UpdatePasswordSchema), + defaultValues, + }); + + const { + watch, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const values = watch(); + + const onSubmit = handleSubmit(async (data) => { + try { + await updatePassword({ + username: data.email, + confirmationCode: data.code, + newPassword: data.password, + }); + + router.push(paths.auth.amplify.signIn); + } catch (error) { + console.error(error); + } + }); + + const handleResendCode = useCallback(async () => { + try { + startCountdown(); + await resetPassword({ username: values.email }); + } catch (error) { + console.error(error); + } + }, [startCountdown, values.email]); + + const renderHead = ( + <> + + + + Request sent successfully! + + + {`We've sent a 6-digit confirmation email to your email. \nPlease enter the code in below box to verify your email.`} + + + + ); + + const renderForm = ( + + + + + + + + + + + ), + }} + /> + + + + + + + ), + }} + /> + + + Update password + + + + {`Don’t have a code? `} + + Resend code {counting && `(${countdown}s)`} + + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth/amplify/amplify-verify-view.jsx b/front_minimal/src/sections/auth/amplify/amplify-verify-view.jsx new file mode 100644 index 0000000..f6e4c35 --- /dev/null +++ b/front_minimal/src/sections/auth/amplify/amplify-verify-view.jsx @@ -0,0 +1,156 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useCallback } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; +import { useRouter, useSearchParams } from 'src/routes/hooks'; + +import { useCountdownSeconds } from 'src/hooks/use-countdown'; + +import { EmailInboxIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { confirmSignUp, resendSignUpCode } from 'src/auth/context/amplify'; + +// ---------------------------------------------------------------------- + +export const VerifySchema = zod.object({ + code: zod + .string() + .min(1, { message: 'Code is required!' }) + .min(6, { message: 'Code must be at least 6 characters!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), +}); + +// ---------------------------------------------------------------------- + +export function AmplifyVerifyView() { + const router = useRouter(); + + const searchParams = useSearchParams(); + + const email = searchParams.get('email'); + + const { countdown, counting, startCountdown } = useCountdownSeconds(60); + + const defaultValues = { code: '', email: email || '' }; + + const methods = useForm({ + resolver: zodResolver(VerifySchema), + defaultValues, + }); + + const { + watch, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const values = watch(); + + const onSubmit = handleSubmit(async (data) => { + try { + await confirmSignUp({ username: data.email, confirmationCode: data.code }); + router.push(paths.auth.amplify.signIn); + } catch (error) { + console.error(error); + } + }); + + const handleResendCode = useCallback(async () => { + try { + startCountdown(); + await resendSignUpCode?.({ username: values.email }); + } catch (error) { + console.error(error); + } + }, [startCountdown, values.email]); + + const renderHead = ( + <> + + + + Please check your email! + + + {`We've emailed a 6-digit confirmation code. \nPlease enter the code in the box below to verify your email.`} + + + + ); + + const renderForm = ( + + + + + + + Verify + + + + {`Don’t have a code? `} + + Resend code {counting && `(${countdown}s)`} + + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth/amplify/index.js b/front_minimal/src/sections/auth/amplify/index.js new file mode 100644 index 0000000..61a7d7b --- /dev/null +++ b/front_minimal/src/sections/auth/amplify/index.js @@ -0,0 +1,9 @@ +export * from './amplify-verify-view'; + +export * from './amplify-sign-in-view'; + +export * from './amplify-sign-up-view'; + +export * from './amplify-reset-password-view'; + +export * from './amplify-update-password-view'; diff --git a/front_minimal/src/sections/auth/auth0/auth0-sign-in-view.jsx b/front_minimal/src/sections/auth/auth0/auth0-sign-in-view.jsx new file mode 100644 index 0000000..899e0e8 --- /dev/null +++ b/front_minimal/src/sections/auth/auth0/auth0-sign-in-view.jsx @@ -0,0 +1,110 @@ +'use client'; + +import { useCallback } from 'react'; +import { useAuth0 } from '@auth0/auth0-react'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import Typography from '@mui/material/Typography'; + +import { useSearchParams } from 'src/routes/hooks'; + +import { CONFIG } from 'src/config-global'; + +// ---------------------------------------------------------------------- + +export function Auth0SignInView() { + const { loginWithPopup, loginWithRedirect } = useAuth0(); + + const searchParams = useSearchParams(); + + const returnTo = searchParams.get('returnTo'); + + const handleSignInWithPopup = useCallback(async () => { + try { + await loginWithPopup(); + } catch (error) { + console.error(error); + } + }, [loginWithPopup]); + + const handleSignUpWithPopup = useCallback(async () => { + try { + await loginWithPopup({ authorizationParams: { screen_hint: 'signup' } }); + } catch (error) { + console.error(error); + } + }, [loginWithPopup]); + + const handleSignInWithRedirect = useCallback(async () => { + try { + await loginWithRedirect({ appState: { returnTo: returnTo || CONFIG.auth.redirectPath } }); + } catch (error) { + console.error(error); + } + }, [loginWithRedirect, returnTo]); + + const handleSignUpWithRedirect = useCallback(async () => { + try { + await loginWithRedirect({ + appState: { returnTo: returnTo || CONFIG.auth.redirectPath }, + authorizationParams: { screen_hint: 'signup' }, + }); + } catch (error) { + console.error(error); + } + }, [loginWithRedirect, returnTo]); + + return ( + <> + + Sign in to your account + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/auth/auth0/index.js b/front_minimal/src/sections/auth/auth0/index.js new file mode 100644 index 0000000..2c9bb76 --- /dev/null +++ b/front_minimal/src/sections/auth/auth0/index.js @@ -0,0 +1 @@ +export * from './auth0-sign-in-view'; diff --git a/front_minimal/src/sections/auth/firebase/firebase-reset-password-view.jsx b/front_minimal/src/sections/auth/firebase/firebase-reset-password-view.jsx new file mode 100644 index 0000000..ea9d5eb --- /dev/null +++ b/front_minimal/src/sections/auth/firebase/firebase-reset-password-view.jsx @@ -0,0 +1,121 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { PasswordIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { sendPasswordResetEmail } from 'src/auth/context/firebase'; + +// ---------------------------------------------------------------------- + +export const ResetPasswordSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), +}); + +// ---------------------------------------------------------------------- + +export function FirebaseResetPasswordView() { + const router = useRouter(); + + const defaultValues = { + email: '', + }; + + const methods = useForm({ + resolver: zodResolver(ResetPasswordSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await sendPasswordResetEmail({ email: data.email }); + + const searchParams = new URLSearchParams({ email: data.email }).toString(); + + const href = `${paths.auth.firebase.verify}?${searchParams}`; + router.push(href); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + <> + + + + Forgot your password? + + + {`Please enter the email address associated with your account and we'll email you a link to reset your password.`} + + + + ); + + const renderForm = ( + + + + + Send request + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth/firebase/firebase-sign-in-view.jsx b/front_minimal/src/sections/auth/firebase/firebase-sign-in-view.jsx new file mode 100644 index 0000000..cf2554d --- /dev/null +++ b/front_minimal/src/sections/auth/firebase/firebase-sign-in-view.jsx @@ -0,0 +1,218 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useState } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Alert from '@mui/material/Alert'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Form, Field } from 'src/components/hook-form'; +import { Iconify, SocialIcon } from 'src/components/iconify'; + +import { useAuthContext } from 'src/auth/hooks'; +import { + signInWithGoogle, + signInWithGithub, + signInWithTwitter, + signInWithPassword, +} from 'src/auth/context/firebase'; + +// ---------------------------------------------------------------------- + +export const SignInSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function FirebaseSignInView() { + const router = useRouter(); + + const { checkUserSession } = useAuthContext(); + + const [errorMsg, setErrorMsg] = useState(''); + + const password = useBoolean(); + + const defaultValues = { + email: '', + password: '', + }; + + const methods = useForm({ + resolver: zodResolver(SignInSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await signInWithPassword({ email: data.email, password: data.password }); + await checkUserSession?.(); + + router.refresh(); + } catch (error) { + console.error(error); + setErrorMsg(error instanceof Error ? error.message : error); + } + }); + + const handleSignInWithGoogle = async () => { + try { + await signInWithGoogle(); + } catch (error) { + console.error(error); + } + }; + + const handleSignInWithGithub = async () => { + try { + await signInWithGithub(); + } catch (error) { + console.error(error); + } + }; + + const handleSignInWithTwitter = async () => { + try { + await signInWithTwitter(); + } catch (error) { + console.error(error); + } + }; + + const renderHead = ( + + Sign in to your account + + + + {`Don't have an account?`} + + + + Get started + + + + ); + + const renderForm = ( + + + + + + Forgot password? + + + + + + + + ), + }} + /> + + + + Sign in + + + ); + + const renderSignInWithSocials = ( + <> + + OR + + + + + + + + + + + + + + + + + ); + + return ( + <> + {renderHead} + + {!!errorMsg && ( + + {errorMsg} + + )} + +
    + {renderForm} +
    + + {renderSignInWithSocials} + + ); +} diff --git a/front_minimal/src/sections/auth/firebase/firebase-sign-up-view.jsx b/front_minimal/src/sections/auth/firebase/firebase-sign-up-view.jsx new file mode 100644 index 0000000..bd17700 --- /dev/null +++ b/front_minimal/src/sections/auth/firebase/firebase-sign-up-view.jsx @@ -0,0 +1,244 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useState } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Alert from '@mui/material/Alert'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Form, Field } from 'src/components/hook-form'; +import { Iconify, SocialIcon } from 'src/components/iconify'; + +import { + signUp, + signInWithGithub, + signInWithGoogle, + signInWithTwitter, +} from 'src/auth/context/firebase'; + +// ---------------------------------------------------------------------- + +export const SignUpSchema = zod.object({ + firstName: zod.string().min(1, { message: 'First name is required!' }), + lastName: zod.string().min(1, { message: 'Last name is required!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function FirebaseSignUpView() { + const [errorMsg, setErrorMsg] = useState(''); + + const router = useRouter(); + + const password = useBoolean(); + + const defaultValues = { + firstName: '', + lastName: '', + email: '', + password: '', + }; + + const methods = useForm({ + resolver: zodResolver(SignUpSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await signUp({ + email: data.email, + password: data.password, + firstName: data.firstName, + lastName: data.lastName, + }); + + const searchParams = new URLSearchParams({ email: data.email }).toString(); + + const href = `${paths.auth.firebase.verify}?${searchParams}`; + + router.push(href); + } catch (error) { + console.error(error); + setErrorMsg(error instanceof Error ? error.message : error); + } + }); + + const handleSignInWithGoogle = async () => { + try { + await signInWithGoogle(); + } catch (error) { + console.error(error); + } + }; + + const handleSignInWithGithub = async () => { + try { + await signInWithGithub(); + } catch (error) { + console.error(error); + } + }; + + const handleSignInWithTwitter = async () => { + try { + await signInWithTwitter(); + } catch (error) { + console.error(error); + } + }; + + const renderHead = ( + + Get started absolutely free + + + + Already have an account? + + + + Sign in + + + + ); + + const renderForm = ( + + + + + + + + + + + + + + ), + }} + /> + + + Create account + + + ); + + const renderTerms = ( + + {'By signing up, I agree to '} + + Terms of service + + {' and '} + + Privacy policy + + . + + ); + + const renderSignInWithSocials = ( + <> + + OR + + + + + + + + + + + + + + + + + ); + + return ( + <> + {renderHead} + + {!!errorMsg && ( + + {errorMsg} + + )} + +
    + {renderForm} +
    + + {renderTerms} + + {renderSignInWithSocials} + + ); +} diff --git a/front_minimal/src/sections/auth/firebase/firebase-verify-view.jsx b/front_minimal/src/sections/auth/firebase/firebase-verify-view.jsx new file mode 100644 index 0000000..56a822a --- /dev/null +++ b/front_minimal/src/sections/auth/firebase/firebase-verify-view.jsx @@ -0,0 +1,47 @@ +'use client'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { EmailInboxIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function FirebaseVerifyView() { + const renderHead = ( + <> + + + + Please check your email! + + + {`We have sent a confirmation link to your email. \nPlease check your inbox or spam folder.`} + + + + ); + + return ( + <> + {renderHead} + + + + ); +} diff --git a/front_minimal/src/sections/auth/firebase/index.js b/front_minimal/src/sections/auth/firebase/index.js new file mode 100644 index 0000000..bbce399 --- /dev/null +++ b/front_minimal/src/sections/auth/firebase/index.js @@ -0,0 +1,7 @@ +export * from './firebase-verify-view'; + +export * from './firebase-sign-in-view'; + +export * from './firebase-sign-up-view'; + +export * from './firebase-reset-password-view'; diff --git a/front_minimal/src/sections/auth/jwt/index.js b/front_minimal/src/sections/auth/jwt/index.js new file mode 100644 index 0000000..0e2428a --- /dev/null +++ b/front_minimal/src/sections/auth/jwt/index.js @@ -0,0 +1,3 @@ +export * from './jwt-sign-in-view'; + +export * from './jwt-sign-up-view'; diff --git a/front_minimal/src/sections/auth/jwt/jwt-sign-in-view.jsx b/front_minimal/src/sections/auth/jwt/jwt-sign-in-view.jsx new file mode 100644 index 0000000..cc3b80a --- /dev/null +++ b/front_minimal/src/sections/auth/jwt/jwt-sign-in-view.jsx @@ -0,0 +1,163 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useState } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Alert from '@mui/material/Alert'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { useAuthContext } from 'src/auth/hooks'; +import { signInWithPassword } from 'src/auth/context/jwt'; + +// ---------------------------------------------------------------------- + +export const SignInSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function JwtSignInView() { + const router = useRouter(); + + const { checkUserSession } = useAuthContext(); + + const [errorMsg, setErrorMsg] = useState(''); + + const password = useBoolean(); + + const defaultValues = { + email: 'demo@minimals.cc', + password: '@demo1', + }; + + const methods = useForm({ + resolver: zodResolver(SignInSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await signInWithPassword({ email: data.email, password: data.password }); + await checkUserSession?.(); + + router.refresh(); + } catch (error) { + console.error(error); + setErrorMsg(error instanceof Error ? error.message : error); + } + }); + + const renderHead = ( + + Sign in to your account + + + + {`Don't have an account?`} + + + + Get started + + + + ); + + const renderForm = ( + + + + + + Forgot password? + + + + + + + + ), + }} + /> + + + + Sign in + + + ); + + return ( + <> + {renderHead} + + + Use {defaultValues.email} + {' with password '} + {defaultValues.password} + + + {!!errorMsg && ( + + {errorMsg} + + )} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth/jwt/jwt-sign-up-view.jsx b/front_minimal/src/sections/auth/jwt/jwt-sign-up-view.jsx new file mode 100644 index 0000000..e5167aa --- /dev/null +++ b/front_minimal/src/sections/auth/jwt/jwt-sign-up-view.jsx @@ -0,0 +1,183 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useState } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Alert from '@mui/material/Alert'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { signUp } from 'src/auth/context/jwt'; +import { useAuthContext } from 'src/auth/hooks'; + +// ---------------------------------------------------------------------- + +export const SignUpSchema = zod.object({ + firstName: zod.string().min(1, { message: 'First name is required!' }), + lastName: zod.string().min(1, { message: 'Last name is required!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function JwtSignUpView() { + const { checkUserSession } = useAuthContext(); + + const router = useRouter(); + + const password = useBoolean(); + + const [errorMsg, setErrorMsg] = useState(''); + + const defaultValues = { + firstName: 'Hello', + lastName: 'Friend', + email: 'hello@gmail.com', + password: '@demo1', + }; + + const methods = useForm({ + resolver: zodResolver(SignUpSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await signUp({ + email: data.email, + password: data.password, + firstName: data.firstName, + lastName: data.lastName, + }); + await checkUserSession?.(); + + router.refresh(); + } catch (error) { + console.error(error); + setErrorMsg(error instanceof Error ? error.message : error); + } + }); + + const renderHead = ( + + Get started absolutely free + + + + Already have an account? + + + + Sign in + + + + ); + + const renderForm = ( + + + + + + + + + + + + + + ), + }} + /> + + + Create account + + + ); + + const renderTerms = ( + + {'By signing up, I agree to '} + + Terms of service + + {' and '} + + Privacy policy + + . + + ); + + return ( + <> + {renderHead} + + {!!errorMsg && ( + + {errorMsg} + + )} + +
    + {renderForm} +
    + + {renderTerms} + + ); +} diff --git a/front_minimal/src/sections/auth/supabase/index.js b/front_minimal/src/sections/auth/supabase/index.js new file mode 100644 index 0000000..0cb4cc2 --- /dev/null +++ b/front_minimal/src/sections/auth/supabase/index.js @@ -0,0 +1,9 @@ +export * from './supabase-verify-view'; + +export * from './supabase-sign-in-view'; + +export * from './supabase-sign-up-view'; + +export * from './supabase-reset-password-view'; + +export * from './supabase-update-password-view'; diff --git a/front_minimal/src/sections/auth/supabase/supabase-reset-password-view.jsx b/front_minimal/src/sections/auth/supabase/supabase-reset-password-view.jsx new file mode 100644 index 0000000..338af03 --- /dev/null +++ b/front_minimal/src/sections/auth/supabase/supabase-reset-password-view.jsx @@ -0,0 +1,118 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { PasswordIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { resetPassword } from 'src/auth/context/supabase'; + +// ---------------------------------------------------------------------- + +export const ResetPasswordSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), +}); + +// ---------------------------------------------------------------------- + +export function SupabaseResetPasswordView() { + const router = useRouter(); + + const defaultValues = { + email: '', + }; + + const methods = useForm({ + resolver: zodResolver(ResetPasswordSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await resetPassword({ email: data.email }); + + router.push(paths.auth.supabase.verify); + } catch (error) { + console.error(error); + } + }); + + const renderHead = ( + <> + + + + Forgot your password? + + + {`Please enter the email address associated with your account and we'll email you a link to reset your password.`} + + + + ); + + const renderForm = ( + + + + + Send request + + + + + Return to sign in + + + ); + + return ( + <> + {renderHead} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth/supabase/supabase-sign-in-view.jsx b/front_minimal/src/sections/auth/supabase/supabase-sign-in-view.jsx new file mode 100644 index 0000000..36bdcf7 --- /dev/null +++ b/front_minimal/src/sections/auth/supabase/supabase-sign-in-view.jsx @@ -0,0 +1,157 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useState } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Alert from '@mui/material/Alert'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { useAuthContext } from 'src/auth/hooks'; +import { signInWithPassword } from 'src/auth/context/supabase'; + +// ---------------------------------------------------------------------- + +export const SignInSchema = zod.object({ + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function SupabaseSignInView() { + const router = useRouter(); + + const { checkUserSession } = useAuthContext(); + + const [errorMsg, setErrorMsg] = useState(''); + + const password = useBoolean(); + + const defaultValues = { + email: '', + password: '', + }; + + const methods = useForm({ + resolver: zodResolver(SignInSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await signInWithPassword({ email: data.email, password: data.password }); + await checkUserSession?.(); + + router.refresh(); + } catch (error) { + console.error(error); + setErrorMsg(error instanceof Error ? error.message : error); + } + }); + + const renderHead = ( + + Sign in to your account + + + + {`Don't have an account?`} + + + + Get started + + + + ); + + const renderForm = ( + + + + + + Forgot password? + + + + + + + + ), + }} + /> + + + + Sign in + + + ); + + return ( + <> + {renderHead} + + {!!errorMsg && ( + + {errorMsg} + + )} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth/supabase/supabase-sign-up-view.jsx b/front_minimal/src/sections/auth/supabase/supabase-sign-up-view.jsx new file mode 100644 index 0000000..9f92a6b --- /dev/null +++ b/front_minimal/src/sections/auth/supabase/supabase-sign-up-view.jsx @@ -0,0 +1,179 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useState } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Link from '@mui/material/Link'; +import Alert from '@mui/material/Alert'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { signUp } from 'src/auth/context/supabase'; + +// ---------------------------------------------------------------------- + +export const SignUpSchema = zod.object({ + firstName: zod.string().min(1, { message: 'First name is required!' }), + lastName: zod.string().min(1, { message: 'Last name is required!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), +}); + +// ---------------------------------------------------------------------- + +export function SupabaseSignUpView() { + const [errorMsg, setErrorMsg] = useState(''); + + const router = useRouter(); + + const password = useBoolean(); + + const defaultValues = { + firstName: '', + lastName: '', + email: '', + password: '', + }; + + const methods = useForm({ + resolver: zodResolver(SignUpSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await signUp({ + email: data.email, + password: data.password, + firstName: data.firstName, + lastName: data.lastName, + }); + + router.push(paths.auth.supabase.verify); + } catch (error) { + console.error(error); + setErrorMsg(error instanceof Error ? error.message : error); + } + }); + + const renderHead = ( + + Get started absolutely free + + + + Already have an account? + + + + Sign in + + + + ); + + const renderForm = ( + + + + + + + + + + + + + + ), + }} + /> + + + Create account + + + ); + + const renderTerms = ( + + {'By signing up, I agree to '} + + Terms of service + + {' and '} + + Privacy policy + + . + + ); + + return ( + <> + {renderHead} + + {!!errorMsg && ( + + {errorMsg} + + )} + +
    + {renderForm} +
    + + {renderTerms} + + ); +} diff --git a/front_minimal/src/sections/auth/supabase/supabase-update-password-view.jsx b/front_minimal/src/sections/auth/supabase/supabase-update-password-view.jsx new file mode 100644 index 0000000..fdc32a7 --- /dev/null +++ b/front_minimal/src/sections/auth/supabase/supabase-update-password-view.jsx @@ -0,0 +1,149 @@ +'use client'; + +import { z as zod } from 'zod'; +import { useState } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Alert from '@mui/material/Alert'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import IconButton from '@mui/material/IconButton'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { NewPasswordIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +import { updatePassword } from 'src/auth/context/supabase'; + +export const UpdatePasswordSchema = zod + .object({ + password: zod + .string() + .min(1, { message: 'Password is required!' }) + .min(6, { message: 'Password must be at least 6 characters!' }), + confirmPassword: zod.string().min(1, { message: 'Confirm password is required!' }), + }) + .refine((data) => data.password === data.confirmPassword, { + message: 'Passwords do not match!', + path: ['confirmPassword'], + }); + +// ---------------------------------------------------------------------- + +export function SupabaseUpdatePasswordView() { + const router = useRouter(); + + const [errorMsg, setErrorMsg] = useState(''); + + const password = useBoolean(); + + const defaultValues = { password: '', confirmPassword: '' }; + + const methods = useForm({ + resolver: zodResolver(UpdatePasswordSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await updatePassword({ password: data.password }); + + router.push(paths.dashboard.root); + } catch (error) { + console.error(error); + setErrorMsg(error instanceof Error ? error.message : error); + } + }); + + const renderHead = ( + <> + + + + Update password + + + Successful updates enable access using the new password. + + + + ); + + const renderForm = ( + + + + + + + ), + }} + /> + + + + + + + ), + }} + /> + + + Update password + + + ); + + return ( + <> + {renderHead} + + {!!errorMsg && ( + + {errorMsg} + + )} + +
    + {renderForm} +
    + + ); +} diff --git a/front_minimal/src/sections/auth/supabase/supabase-verify-view.jsx b/front_minimal/src/sections/auth/supabase/supabase-verify-view.jsx new file mode 100644 index 0000000..246104c --- /dev/null +++ b/front_minimal/src/sections/auth/supabase/supabase-verify-view.jsx @@ -0,0 +1,47 @@ +'use client'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { EmailInboxIcon } from 'src/assets/icons'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function SupabaseVerifyView() { + const renderHead = ( + <> + + + + Please check your email! + + + {`We have sent a confirmation link to your email. \nPlease check your inbox or spam folder.`} + + + + ); + + return ( + <> + {renderHead} + + + + ); +} diff --git a/front_minimal/src/sections/blank/view.jsx b/front_minimal/src/sections/blank/view.jsx new file mode 100644 index 0000000..e9b39ae --- /dev/null +++ b/front_minimal/src/sections/blank/view.jsx @@ -0,0 +1,28 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Typography from '@mui/material/Typography'; + +import { varAlpha } from 'src/theme/styles'; +import { DashboardContent } from 'src/layouts/dashboard'; + +// ---------------------------------------------------------------------- + +export function BlankView({ title = 'Blank' }) { + return ( + + {title} + + varAlpha(theme.vars.palette.grey['500Channel'], 0.04), + border: (theme) => `dashed 1px ${theme.vars.palette.divider}`, + }} + /> + + ); +} diff --git a/front_minimal/src/sections/blog/post-comment-form.jsx b/front_minimal/src/sections/blog/post-comment-form.jsx new file mode 100644 index 0000000..3dd66e4 --- /dev/null +++ b/front_minimal/src/sections/blog/post-comment-form.jsx @@ -0,0 +1,76 @@ +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const CommentSchema = zod.object({ + comment: zod.string().min(1, { message: 'Comment is required!' }), +}); + +// ---------------------------------------------------------------------- + +export function PostCommentForm() { + const defaultValues = { comment: '' }; + + const methods = useForm({ + resolver: zodResolver(CommentSchema), + defaultValues, + }); + + const { + reset, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + reset(); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + return ( +
    + + + + + + + + + + + + + + + + + + + + Post comment + + + +
    + ); +} diff --git a/front_minimal/src/sections/blog/post-comment-item.jsx b/front_minimal/src/sections/blog/post-comment-item.jsx new file mode 100644 index 0000000..aff1124 --- /dev/null +++ b/front_minimal/src/sections/blog/post-comment-item.jsx @@ -0,0 +1,71 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { fDate } from 'src/utils/format-time'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function PostCommentItem({ name, avatarUrl, message, tagUser, postedAt, hasReply }) { + const reply = useBoolean(); + + return ( + + + + `solid 1px ${theme.vars.palette.divider}` }} + > + + {name} + + + + {fDate(postedAt)} + + + + {tagUser && ( + + @{tagUser} + + )} + {message} + + + {reply.value && ( + + + + )} + + + {!hasReply && ( + + )} + + ); +} diff --git a/front_minimal/src/sections/blog/post-comment-list.jsx b/front_minimal/src/sections/blog/post-comment-list.jsx new file mode 100644 index 0000000..16d7f22 --- /dev/null +++ b/front_minimal/src/sections/blog/post-comment-list.jsx @@ -0,0 +1,45 @@ +import Box from '@mui/material/Box'; +import Pagination from '@mui/material/Pagination'; + +import { PostCommentItem } from './post-comment-item'; + +// ---------------------------------------------------------------------- + +export function PostCommentList({ comments = [] }) { + return ( + <> + {comments.map((comment) => { + const hasReply = !!comment.replyComment.length; + + return ( + + + {hasReply && + comment.replyComment.map((reply) => { + const userReply = comment.users.find((user) => user.id === reply.userId); + + return ( + + ); + })} + + ); + })} + + + + ); +} diff --git a/front_minimal/src/sections/blog/post-details-hero.jsx b/front_minimal/src/sections/blog/post-details-hero.jsx new file mode 100644 index 0000000..adaea8b --- /dev/null +++ b/front_minimal/src/sections/blog/post-details-hero.jsx @@ -0,0 +1,104 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Container from '@mui/material/Container'; +import SpeedDial from '@mui/material/SpeedDial'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; +import SpeedDialAction from '@mui/material/SpeedDialAction'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +import { fDate } from 'src/utils/format-time'; + +import { _socials } from 'src/_mock'; +import { varAlpha, bgGradient } from 'src/theme/styles'; + +import { Iconify, SocialIcon } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function PostDetailsHero({ title, author, coverUrl, createdAt }) { + const theme = useTheme(); + + const smUp = useResponsive('up', 'sm'); + + return ( + + + + {title} + + + + {author && createdAt && ( + + + + + + )} + + } + FabProps={{ size: 'medium' }} + sx={{ position: 'absolute', bottom: { xs: 32, md: 64 }, right: { xs: 16, md: 24 } }} + > + {_socials.map((action) => ( + } + tooltipTitle={action.name} + tooltipPlacement="top" + FabProps={{ color: 'default' }} + /> + ))} + + + + + ); +} diff --git a/front_minimal/src/sections/blog/post-details-preview.jsx b/front_minimal/src/sections/blog/post-details-preview.jsx new file mode 100644 index 0000000..e8d1018 --- /dev/null +++ b/front_minimal/src/sections/blog/post-details-preview.jsx @@ -0,0 +1,82 @@ +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import Divider from '@mui/material/Divider'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import DialogActions from '@mui/material/DialogActions'; + +import { Markdown } from 'src/components/markdown'; +import { Scrollbar } from 'src/components/scrollbar'; +import { EmptyContent } from 'src/components/empty-content'; + +import { PostDetailsHero } from './post-details-hero'; + +// ---------------------------------------------------------------------- + +export function PostDetailsPreview({ + open, + title, + content, + isValid, + onClose, + coverUrl, + onSubmit, + description, + isSubmitting, +}) { + let previewUrl = ''; + + if (coverUrl) { + if (typeof coverUrl === 'string') { + previewUrl = coverUrl; + } else { + previewUrl = URL.createObjectURL(coverUrl); + } + } + + const hasHero = title || previewUrl; + + const hasContent = title || description || content || previewUrl; + + return ( + + + + Preview + + + + + + Post + + + + + + {hasContent ? ( + + {(hasHero || previewUrl) && } + + + {description} + {content} + + + + ) : ( + + )} + + ); +} diff --git a/front_minimal/src/sections/blog/post-details-toolbar.jsx b/front_minimal/src/sections/blog/post-details-toolbar.jsx new file mode 100644 index 0000000..5a3d9d0 --- /dev/null +++ b/front_minimal/src/sections/blog/post-details-toolbar.jsx @@ -0,0 +1,94 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Tooltip from '@mui/material/Tooltip'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { RouterLink } from 'src/routes/components'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function PostDetailsToolbar({ + publish, + backLink, + editLink, + liveLink, + publishOptions, + onChangePublish, + sx, + ...other +}) { + const popover = usePopover(); + + return ( + <> + + + + + + {publish === 'published' && ( + + + + + + )} + + + + + + + + } + onClick={popover.onOpen} + sx={{ textTransform: 'capitalize' }} + > + {publish} + + + + + + {publishOptions.map((option) => ( + { + popover.onClose(); + onChangePublish(option.value); + }} + > + {option.value === 'published' && } + {option.value === 'draft' && } + {option.label} + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/blog/post-item-horizontal.jsx b/front_minimal/src/sections/blog/post-item-horizontal.jsx new file mode 100644 index 0000000..33457a4 --- /dev/null +++ b/front_minimal/src/sections/blog/post-item-horizontal.jsx @@ -0,0 +1,167 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import { useTheme } from '@mui/material/styles'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { fDate } from 'src/utils/format-time'; +import { fShortenNumber } from 'src/utils/format-number'; + +import { maxLine } from 'src/theme/styles'; + +import { Label } from 'src/components/label'; +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function PostItemHorizontal({ post }) { + const theme = useTheme(); + + const popover = usePopover(); + + const router = useRouter(); + + const { + title, + author, + publish, + coverUrl, + createdAt, + totalViews, + totalShares, + totalComments, + description, + } = post; + + return ( + <> + + + + + + + {fDate(createdAt)} + + + + + + {title} + + + + {description} + + + + + + + + + + + + {fShortenNumber(totalComments)} + + + + + {fShortenNumber(totalViews)} + + + + + {fShortenNumber(totalShares)} + + + + + + + + {title} + + + + + + { + popover.onClose(); + router.push(paths.dashboard.post.details(title)); + }} + > + + View + + + { + popover.onClose(); + router.push(paths.dashboard.post.edit(title)); + }} + > + + Edit + + + { + popover.onClose(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + ); +} diff --git a/front_minimal/src/sections/blog/post-item.jsx b/front_minimal/src/sections/blog/post-item.jsx new file mode 100644 index 0000000..6d96d0d --- /dev/null +++ b/front_minimal/src/sections/blog/post-item.jsx @@ -0,0 +1,182 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; +import CardContent from '@mui/material/CardContent'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { fDate } from 'src/utils/format-time'; +import { fShortenNumber } from 'src/utils/format-number'; + +import { maxLine, varAlpha } from 'src/theme/styles'; +import { AvatarShape } from 'src/assets/illustrations'; + +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function PostItem({ post }) { + const theme = useTheme(); + + const linkTo = paths.post.details(post.title); + + return ( + + + + + + + {post.title} + + + + + {fDate(post.createdAt)} + + + + {post.title} + + + + + + ); +} + +// ---------------------------------------------------------------------- + +export function PostItemLatest({ post, index }) { + const theme = useTheme(); + + const linkTo = paths.post.details(post.title); + + const postSmall = index === 1 || index === 2; + + return ( + + + + {post.title} + + + + {fDate(post.createdAt)} + + + + {post.title} + + + + + + ); +} + +// ---------------------------------------------------------------------- + +export function InfoBlock({ totalComments, totalViews, totalShares, sx }) { + return ( + + + + {fShortenNumber(totalComments)} + + + + + {fShortenNumber(totalViews)} + + + + + {fShortenNumber(totalShares)} + + + ); +} diff --git a/front_minimal/src/sections/blog/post-list-horizontal.jsx b/front_minimal/src/sections/blog/post-list-horizontal.jsx new file mode 100644 index 0000000..3de190a --- /dev/null +++ b/front_minimal/src/sections/blog/post-list-horizontal.jsx @@ -0,0 +1,35 @@ +import Box from '@mui/material/Box'; +import Pagination, { paginationClasses } from '@mui/material/Pagination'; + +import { PostItemSkeleton } from './post-skeleton'; +import { PostItemHorizontal } from './post-item-horizontal'; + +// ---------------------------------------------------------------------- + +export function PostListHorizontal({ posts, loading }) { + const renderLoading = ; + + const renderList = posts.map((post) => ); + + return ( + <> + + {loading ? renderLoading : renderList} + + + {posts.length > 8 && ( + + )} + + ); +} diff --git a/front_minimal/src/sections/blog/post-list.jsx b/front_minimal/src/sections/blog/post-list.jsx new file mode 100644 index 0000000..67c5e5a --- /dev/null +++ b/front_minimal/src/sections/blog/post-list.jsx @@ -0,0 +1,70 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Grid from '@mui/material/Unstable_Grid2'; + +import { Iconify } from 'src/components/iconify'; + +import { PostItemSkeleton } from './post-skeleton'; +import { PostItem, PostItemLatest } from './post-item'; + +// ---------------------------------------------------------------------- + +export function PostList({ posts, loading }) { + const renderLoading = ( + + + + ); + + const renderList = ( + + {posts.slice(0, 3).map((post, index) => ( + + + + ))} + + {posts.slice(0, 3).map((post) => ( + + + + ))} + + {posts.slice(3, posts.length).map((post) => ( + + + + ))} + + ); + + return ( + <> + {loading ? renderLoading : renderList} + + {posts.length > 8 && ( + + + + )} + + ); +} diff --git a/front_minimal/src/sections/blog/post-new-edit-form.jsx b/front_minimal/src/sections/blog/post-new-edit-form.jsx new file mode 100644 index 0000000..b5d87ae --- /dev/null +++ b/front_minimal/src/sections/blog/post-new-edit-form.jsx @@ -0,0 +1,256 @@ +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; +import { useMemo, useEffect, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Chip from '@mui/material/Chip'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Switch from '@mui/material/Switch'; +import Divider from '@mui/material/Divider'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { _tags } from 'src/_mock'; + +import { toast } from 'src/components/snackbar'; +import { Form, Field, schemaHelper } from 'src/components/hook-form'; + +import { PostDetailsPreview } from './post-details-preview'; + +// ---------------------------------------------------------------------- + +export const NewPostSchema = zod.object({ + title: zod.string().min(1, { message: 'Title is required!' }), + description: zod.string().min(1, { message: 'Description is required!' }), + content: schemaHelper.editor().min(100, { message: 'Content must be at least 100 characters' }), + coverUrl: schemaHelper.file({ message: { required_error: 'Cover is required!' } }), + tags: zod.string().array().min(2, { message: 'Must have at least 2 items!' }), + metaKeywords: zod.string().array().nonempty({ message: 'Meta keywords is required!' }), + // Not required + metaTitle: zod.string(), + metaDescription: zod.string(), +}); + +// ---------------------------------------------------------------------- + +export function PostNewEditForm({ currentPost }) { + const router = useRouter(); + + const preview = useBoolean(); + + const defaultValues = useMemo( + () => ({ + title: currentPost?.title || '', + description: currentPost?.description || '', + content: currentPost?.content || '', + coverUrl: currentPost?.coverUrl || null, + tags: currentPost?.tags || [], + metaKeywords: currentPost?.metaKeywords || [], + metaTitle: currentPost?.metaTitle || '', + metaDescription: currentPost?.metaDescription || '', + }), + [currentPost] + ); + + const methods = useForm({ + mode: 'all', + resolver: zodResolver(NewPostSchema), + defaultValues, + }); + + const { + reset, + watch, + setValue, + handleSubmit, + formState: { isSubmitting, isValid }, + } = methods; + + const values = watch(); + + useEffect(() => { + if (currentPost) { + reset(defaultValues); + } + }, [currentPost, defaultValues, reset]); + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + reset(); + preview.onFalse(); + toast.success(currentPost ? 'Update success!' : 'Create success!'); + router.push(paths.dashboard.post.root); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const handleRemoveFile = useCallback(() => { + setValue('coverUrl', null); + }, [setValue]); + + const renderDetails = ( + + + + + + + + + + + + Content + + + + + Cover + + + + + ); + + const renderProperties = ( + + + + + + + option)} + getOptionLabel={(option) => option} + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + /> + + + + + + option)} + getOptionLabel={(option) => option} + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + /> + + } + label="Enable comments" + /> +
    +
    + ); + + const renderActions = ( + + } + label="Publish" + sx={{ pl: 3, flexGrow: 1 }} + /> + +
    + + + + {!currentPost ? 'Create post' : 'Save changes'} + +
    +
    + ); + + return ( +
    + + {renderDetails} + + {renderProperties} + + {renderActions} + + + + + ); +} diff --git a/front_minimal/src/sections/blog/post-search.jsx b/front_minimal/src/sections/blog/post-search.jsx new file mode 100644 index 0000000..b7469d4 --- /dev/null +++ b/front_minimal/src/sections/blog/post-search.jsx @@ -0,0 +1,109 @@ +import parse from 'autosuggest-highlight/parse'; +import match from 'autosuggest-highlight/match'; + +import Link from '@mui/material/Link'; +import Avatar from '@mui/material/Avatar'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; +import Autocomplete, { autocompleteClasses } from '@mui/material/Autocomplete'; + +import { useRouter } from 'src/routes/hooks'; + +import { Iconify } from 'src/components/iconify'; +import { SearchNotFound } from 'src/components/search-not-found'; + +// ---------------------------------------------------------------------- + +export function PostSearch({ query, results, onSearch, hrefItem, loading }) { + const router = useRouter(); + + const handleClick = (title) => { + router.push(hrefItem(title)); + }; + + const handleKeyUp = (event) => { + if (query) { + if (event.key === 'Enter') { + handleClick(query); + } + } + }; + + return ( + onSearch(newValue)} + getOptionLabel={(option) => option.title} + noOptionsText={} + isOptionEqualToValue={(option, value) => option.id === value.id} + slotProps={{ + popper: { placement: 'bottom-start', sx: { minWidth: 320 } }, + paper: { sx: { [` .${autocompleteClasses.option}`]: { pl: 0.75 } } }, + }} + renderInput={(params) => ( + + + + ), + endAdornment: ( + <> + {loading ? : null} + {params.InputProps.endAdornment} + + ), + }} + /> + )} + renderOption={(props, post, { inputValue }) => { + const matches = match(post.title, inputValue); + const parts = parse(post.title, matches); + + return ( +
  • + + + handleClick(post.title)}> + {parts.map((part, index) => ( + + {part.text} + + ))} + +
  • + ); + }} + /> + ); +} diff --git a/front_minimal/src/sections/blog/post-skeleton.jsx b/front_minimal/src/sections/blog/post-skeleton.jsx new file mode 100644 index 0000000..339abc3 --- /dev/null +++ b/front_minimal/src/sections/blog/post-skeleton.jsx @@ -0,0 +1,88 @@ +import Stack from '@mui/material/Stack'; +import Skeleton from '@mui/material/Skeleton'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +// ---------------------------------------------------------------------- + +export function PostItemSkeleton({ sx, amount = 16, variant = 'vertical', ...other }) { + const smUp = useResponsive('up', 'sm'); + + if (variant === 'horizontal') { + return [...Array(amount)].map((_, index) => ( + `solid 1px ${theme.vars.palette.divider}`, + ...sx, + }} + {...other} + > + + + + + + + + + + + + {smUp && ( + + + + )} + + )); + } + + return [...Array(amount)].map((_, index) => ( + `solid 1px ${theme.vars.palette.divider}`, + ...sx, + }} + {...other} + > + + + + + + + + + + + + + )); +} + +// ---------------------------------------------------------------------- + +export function PostDetailsSkeleton({ ...other }) { + return ( + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/blog/post-sort.jsx b/front_minimal/src/sections/blog/post-sort.jsx new file mode 100644 index 0000000..d6913f5 --- /dev/null +++ b/front_minimal/src/sections/blog/post-sort.jsx @@ -0,0 +1,51 @@ +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function PostSort({ sort, sortOptions, onSort }) { + const popover = usePopover(); + + return ( + <> + + + + + {sortOptions.map((option) => ( + { + popover.onClose(); + onSort(option.value); + }} + > + {option.label} + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/blog/view/index.js b/front_minimal/src/sections/blog/view/index.js new file mode 100644 index 0000000..63ac8fe --- /dev/null +++ b/front_minimal/src/sections/blog/view/index.js @@ -0,0 +1,11 @@ +export * from './post-list-view'; + +export * from './post-edit-view'; + +export * from './post-create-view'; + +export * from './post-details-view'; + +export * from './post-list-home-view'; + +export * from './post-details-home-view'; diff --git a/front_minimal/src/sections/blog/view/post-create-view.jsx b/front_minimal/src/sections/blog/view/post-create-view.jsx new file mode 100644 index 0000000..8a7cbe3 --- /dev/null +++ b/front_minimal/src/sections/blog/view/post-create-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { PostNewEditForm } from '../post-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function PostCreateView() { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/blog/view/post-details-home-view.jsx b/front_minimal/src/sections/blog/view/post-details-home-view.jsx new file mode 100644 index 0000000..31f43e0 --- /dev/null +++ b/front_minimal/src/sections/blog/view/post-details-home-view.jsx @@ -0,0 +1,130 @@ +'use client'; + +import Chip from '@mui/material/Chip'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import Checkbox from '@mui/material/Checkbox'; +import Container from '@mui/material/Container'; +import Grid from '@mui/material/Unstable_Grid2'; +import Typography from '@mui/material/Typography'; +import AvatarGroup from '@mui/material/AvatarGroup'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; + +import { fShortenNumber } from 'src/utils/format-number'; + +import { Iconify } from 'src/components/iconify'; +import { Markdown } from 'src/components/markdown'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { PostItem } from '../post-item'; +import { PostCommentList } from '../post-comment-list'; +import { PostCommentForm } from '../post-comment-form'; +import { PostDetailsHero } from '../post-details-hero'; + +// ---------------------------------------------------------------------- + +export function PostDetailsHomeView({ post, latestPosts }) { + return ( + <> + + + `solid 1px ${theme.vars.palette.divider}` }} + > + + + + + + {post?.description} + + + + `dashed 1px ${theme.vars.palette.divider}`, + borderBottom: (theme) => `dashed 1px ${theme.vars.palette.divider}`, + }} + > + + {post?.tags.map((tag) => ( + + ))} + + + + } + checkedIcon={} + inputProps={{ id: 'favorite-checkbox', 'aria-label': 'Favorite checkbox' }} + /> + } + label={fShortenNumber(post?.totalFavorites)} + sx={{ mr: 1 }} + /> + + + {post?.favoritePerson.map((person) => ( + + ))} + + + + + + Comments + + + ({post?.comments.length}) + + + + + + + + + + + + {!!latestPosts?.length && ( + + + Recent Posts + + + + {latestPosts?.slice(latestPosts.length - 4).map((latestPost) => ( + + + + ))} + + + )} + + ); +} diff --git a/front_minimal/src/sections/blog/view/post-details-view.jsx b/front_minimal/src/sections/blog/view/post-details-view.jsx new file mode 100644 index 0000000..58f5858 --- /dev/null +++ b/front_minimal/src/sections/blog/view/post-details-view.jsx @@ -0,0 +1,127 @@ +'use client'; + +import { useState, useEffect, useCallback } from 'react'; + +import Chip from '@mui/material/Chip'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import Checkbox from '@mui/material/Checkbox'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; +import FormControlLabel from '@mui/material/FormControlLabel'; +import AvatarGroup, { avatarGroupClasses } from '@mui/material/AvatarGroup'; + +import { paths } from 'src/routes/paths'; + +import { fShortenNumber } from 'src/utils/format-number'; + +import { POST_PUBLISH_OPTIONS } from 'src/_mock'; +import { DashboardContent } from 'src/layouts/dashboard'; + +import { Iconify } from 'src/components/iconify'; +import { Markdown } from 'src/components/markdown'; + +import { PostDetailsHero } from '../post-details-hero'; +import { PostCommentList } from '../post-comment-list'; +import { PostCommentForm } from '../post-comment-form'; +import { PostDetailsToolbar } from '../post-details-toolbar'; + +// ---------------------------------------------------------------------- + +export function PostDetailsView({ post }) { + const [publish, setPublish] = useState(''); + + const handleChangePublish = useCallback((newValue) => { + setPublish(newValue); + }, []); + + useEffect(() => { + if (post) { + setPublish(post?.publish); + } + }, [post]); + + return ( + + + + + + + + + {post?.description} + + + + `dashed 1px ${theme.vars.palette.divider}`, + borderBottom: (theme) => `dashed 1px ${theme.vars.palette.divider}`, + }} + > + + {post?.tags.map((tag) => ( + + ))} + + + + } + checkedIcon={} + inputProps={{ id: 'favorite-checkbox', 'aria-label': 'Favorite checkbox' }} + /> + } + label={fShortenNumber(post?.totalFavorites)} + sx={{ mr: 1 }} + /> + + + {post?.favoritePerson.map((person) => ( + + ))} + + + + + + Comments + + + ({post?.comments.length}) + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/blog/view/post-edit-view.jsx b/front_minimal/src/sections/blog/view/post-edit-view.jsx new file mode 100644 index 0000000..e65b881 --- /dev/null +++ b/front_minimal/src/sections/blog/view/post-edit-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { PostNewEditForm } from '../post-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function PostEditView({ post }) { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/blog/view/post-list-home-view.jsx b/front_minimal/src/sections/blog/view/post-list-home-view.jsx new file mode 100644 index 0000000..6c05068 --- /dev/null +++ b/front_minimal/src/sections/blog/view/post-list-home-view.jsx @@ -0,0 +1,86 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; + +import { useDebounce } from 'src/hooks/use-debounce'; + +import { orderBy } from 'src/utils/helper'; + +import { POST_SORT_OPTIONS } from 'src/_mock'; +import { useSearchPosts } from 'src/actions/blog'; + +import { PostList } from '../post-list'; +import { PostSort } from '../post-sort'; +import { PostSearch } from '../post-search'; + +// ---------------------------------------------------------------------- + +export function PostListHomeView({ posts }) { + const [sortBy, setSortBy] = useState('latest'); + + const [searchQuery, setSearchQuery] = useState(''); + + const debouncedQuery = useDebounce(searchQuery); + + const { searchResults, searchLoading } = useSearchPosts(debouncedQuery); + + const dataFiltered = applyFilter({ inputData: posts, sortBy }); + + const handleSortBy = useCallback((newValue) => { + setSortBy(newValue); + }, []); + + const handleSearch = useCallback((inputValue) => { + setSearchQuery(inputValue); + }, []); + + return ( + + + Blog + + + + paths.post.details(title)} + /> + + + + + + + ); +} + +const applyFilter = ({ inputData, sortBy }) => { + if (sortBy === 'latest') { + return orderBy(inputData, ['createdAt'], ['desc']); + } + + if (sortBy === 'oldest') { + return orderBy(inputData, ['createdAt'], ['asc']); + } + + if (sortBy === 'popular') { + return orderBy(inputData, ['totalViews'], ['desc']); + } + + return inputData; +}; diff --git a/front_minimal/src/sections/blog/view/post-list-view.jsx b/front_minimal/src/sections/blog/view/post-list-view.jsx new file mode 100644 index 0000000..684caf2 --- /dev/null +++ b/front_minimal/src/sections/blog/view/post-list-view.jsx @@ -0,0 +1,155 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Tab from '@mui/material/Tab'; +import Tabs from '@mui/material/Tabs'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { useDebounce } from 'src/hooks/use-debounce'; +import { useSetState } from 'src/hooks/use-set-state'; + +import { orderBy } from 'src/utils/helper'; + +import { POST_SORT_OPTIONS } from 'src/_mock'; +import { DashboardContent } from 'src/layouts/dashboard'; +import { useGetPosts, useSearchPosts } from 'src/actions/blog'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { PostSort } from '../post-sort'; +import { PostSearch } from '../post-search'; +import { PostListHorizontal } from '../post-list-horizontal'; + +// ---------------------------------------------------------------------- + +export function PostListView() { + const [sortBy, setSortBy] = useState('latest'); + + const [searchQuery, setSearchQuery] = useState(''); + + const debouncedQuery = useDebounce(searchQuery); + + const { posts, postsLoading } = useGetPosts(); + + const { searchResults, searchLoading } = useSearchPosts(debouncedQuery); + + const filters = useSetState({ publish: 'all' }); + + const dataFiltered = applyFilter({ inputData: posts, filters: filters.state, sortBy }); + + const handleSortBy = useCallback((newValue) => { + setSortBy(newValue); + }, []); + + const handleSearch = useCallback((inputValue) => { + setSearchQuery(inputValue); + }, []); + + const handleFilterPublish = useCallback( + (event, newValue) => { + filters.setState({ publish: newValue }); + }, + [filters] + ); + + return ( + + } + > + New post + + } + sx={{ mb: { xs: 3, md: 5 } }} + /> + + + paths.dashboard.post.details(title)} + /> + + + + + + {['all', 'published', 'draft'].map((tab) => ( + + {tab === 'all' && posts.length} + + {tab === 'published' && posts.filter((post) => post.publish === 'published').length} + + {tab === 'draft' && posts.filter((post) => post.publish === 'draft').length} + + } + sx={{ textTransform: 'capitalize' }} + /> + ))} + + + + + ); +} + +const applyFilter = ({ inputData, filters, sortBy }) => { + const { publish } = filters; + + if (sortBy === 'latest') { + inputData = orderBy(inputData, ['createdAt'], ['desc']); + } + + if (sortBy === 'oldest') { + inputData = orderBy(inputData, ['createdAt'], ['asc']); + } + + if (sortBy === 'popular') { + inputData = orderBy(inputData, ['totalViews'], ['desc']); + } + + if (publish !== 'all') { + inputData = inputData.filter((post) => post.publish === publish); + } + + return inputData; +}; diff --git a/front_minimal/src/sections/calendar/calendar-filters-result.jsx b/front_minimal/src/sections/calendar/calendar-filters-result.jsx new file mode 100644 index 0000000..68033ad --- /dev/null +++ b/front_minimal/src/sections/calendar/calendar-filters-result.jsx @@ -0,0 +1,65 @@ +import { useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Chip from '@mui/material/Chip'; + +import { fDateRangeShortLabel } from 'src/utils/format-time'; + +import { varAlpha } from 'src/theme/styles'; + +import { chipProps, FiltersBlock, FiltersResult } from 'src/components/filters-result'; + +// ---------------------------------------------------------------------- + +export function CalendarFiltersResult({ filters, totalResults, sx }) { + const handleRemoveColor = useCallback( + (inputValue) => { + const newValue = filters.state.colors.filter((item) => item !== inputValue); + + filters.setState({ colors: newValue }); + }, + [filters] + ); + + const handleRemoveDate = useCallback(() => { + filters.setState({ startDate: null, endDate: null }); + }, [filters]); + + return ( + + + {filters.state.colors.map((item) => ( + + `solid 1px ${varAlpha(theme.vars.palette.common.whiteChannel, 0.24)}`, + }} + /> + } + onDelete={() => handleRemoveColor(item)} + /> + ))} + + + + + + + ); +} diff --git a/front_minimal/src/sections/calendar/calendar-filters.jsx b/front_minimal/src/sections/calendar/calendar-filters.jsx new file mode 100644 index 0000000..2b63d0f --- /dev/null +++ b/front_minimal/src/sections/calendar/calendar-filters.jsx @@ -0,0 +1,140 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Badge from '@mui/material/Badge'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import Tooltip from '@mui/material/Tooltip'; +import Drawer from '@mui/material/Drawer'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import ListItemButton from '@mui/material/ListItemButton'; +import { DatePicker } from '@mui/x-date-pickers/DatePicker'; + +import { fDateTime } from 'src/utils/format-time'; +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { ColorPicker } from 'src/components/color-utils'; + +// ---------------------------------------------------------------------- + +export function CalendarFilters({ + open, + onClose, + filters, + onFilters, + canReset, + onResetFilters, + dateError, + events, + onClickEvent, +}) { + + // Статичные пресеты: Красный (Отмена), Фиолетовый (Запланировано), Зеленый (Завершено) + const colorOptions = ['#FF4842', '#7635dc', '#00AB55', '#1890FF']; + + const renderHead = ( + + + Фильтры + + + + + + + + + + + + + + + ); + + const renderColors = ( + + По цвету (статусу) + onFilters('colors', color)} + /> + + ); + + const renderDateRange = ( + + Диапазон дат + onFilters('startDate', newValue)} + slotProps={{ textField: { fullWidth: true } }} + /> + onFilters('endDate', newValue)} + slotProps={{ + textField: { + fullWidth: true, + error: dateError, + helperText: dateError && 'Дата окончания не может быть раньше начала', + }, + }} + /> + + ); + + const renderEvents = ( + + + События ({events.length}) + + + + {events.map((event) => ( + onClickEvent(event.id)} + sx={{ py: 1.5, px: 2.5, borderBottom: (theme) => `dashed 1px ${theme.palette.divider}` }} + > + + + {event.title} + + {fDateTime(event.start)} + + + + ))} + + + ); + + return ( + + {renderHead} + + {renderColors} + {renderDateRange} + + {renderEvents} + + ); +} diff --git a/front_minimal/src/sections/calendar/calendar-form.jsx b/front_minimal/src/sections/calendar/calendar-form.jsx new file mode 100644 index 0000000..2f0c074 --- /dev/null +++ b/front_minimal/src/sections/calendar/calendar-form.jsx @@ -0,0 +1,284 @@ +import { z as zod } from 'zod'; +import { useForm, Controller } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; +import { useMemo, useCallback } from 'react'; +import dayjs from 'dayjs'; +import 'dayjs/locale/ru'; + +// ---------------------------------------------------------------------- + +dayjs.locale('ru'); + +// ---------------------------------------------------------------------- + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import Avatar from '@mui/material/Avatar'; +import Tooltip from '@mui/material/Tooltip'; +import MenuItem from '@mui/material/MenuItem'; +import Switch from '@mui/material/Switch'; +import FormControlLabel from '@mui/material/FormControlLabel'; +import IconButton from '@mui/material/IconButton'; +import LoadingButton from '@mui/lab/LoadingButton'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { useGetStudents, useGetSubjects } from 'src/actions/calendar'; +import { fIsAfter } from 'src/utils/format-time'; +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +const DURATION_OPTIONS = [ + { value: 30, label: '30 минут' }, + { value: 45, label: '45 минут' }, + { value: 60, label: '1 час' }, + { value: 90, label: '1.5 часа' }, + { value: 120, label: '2 часа' }, +]; + +export function CalendarForm({ + currentEvent, + range, + open, + onClose, + onCreateEvent, + onUpdateEvent, + onDeleteEvent, +}) { + const { students } = useGetStudents(); + const { subjects } = useGetSubjects(); + + const EventSchema = zod.object({ + client: zod.union([zod.string(), zod.number()]).refine((val) => !!val, 'Выберите ученика'), + subject: zod.union([zod.string(), zod.number()]).refine((val) => !!val, 'Выберите предмет'), + description: zod.string().max(5000).optional(), + start_time: zod.any().refine((val) => val !== null, 'Выберите начало занятия'), + duration: zod.number().min(1, 'Выберите длительность'), + price: zod.coerce.number().min(0, 'Цена не может быть отрицательной'), + is_recurring: zod.boolean().optional(), + }); + + const defaultValues = useMemo(() => { + const start = currentEvent?.start || range?.start || new Date(); + return { + client: currentEvent?.extendedProps?.client?.id || '', + subject: currentEvent?.extendedProps?.mentor_subject?.id || '', + description: currentEvent?.description || '', + start_time: dayjs(start), + duration: 60, + price: 1500, + is_recurring: false, + }; + }, [currentEvent, range]); + + const methods = useForm({ + resolver: zodResolver(EventSchema), + defaultValues, + }); + + const { + reset, + watch, + control, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const values = watch(); + + const onSubmit = handleSubmit(async (data) => { + try { + const startTime = dayjs(data.start_time); + const endTime = startTime.add(data.duration, 'minute'); + + // Формируем динамический title: Предмет - Преподаватель - Ученик #ID + const selectedSubject = subjects.find(s => s.id === data.subject); + const selectedStudent = students.find(s => s.id === data.client); + + const subjectName = selectedSubject?.name || selectedSubject?.subject_name || 'Урок'; + + const studentFullName = selectedStudent?.user ? `${selectedStudent.user.last_name} ${selectedStudent.user.first_name}` : (selectedStudent?.full_name || 'Ученик'); + + const mentorFullName = currentEvent?.extendedProps?.mentor ? `${currentEvent.extendedProps.mentor.last_name} ${currentEvent.extendedProps.mentor.first_name}` : 'Ментор'; + + const lessonNumber = currentEvent?.id ? ` №${currentEvent.id}` : ''; + + const displayTitle = `${subjectName} ${mentorFullName} - ${studentFullName}${lessonNumber}`.trim(); + + const payload = { + title: displayTitle, // Добавляем обязательное поле title + client: data.client, + subject: data.subject, + description: data.description, + start_time: startTime.toISOString(), + end_time: endTime.toISOString(), + price: data.price, + is_recurring: data.is_recurring, + }; + + if (currentEvent?.id) { + await onUpdateEvent({ ...payload, id: currentEvent.id }); + } else { + await onCreateEvent(payload); + } + onClose(); + reset(); + } catch (error) { + console.error(error); + } + }); + + const onDelete = useCallback(async () => { + try { + await onDeleteEvent(`${currentEvent?.id}`); + onClose(); + reset(); + } catch (error) { + console.error(error); + } + }, [currentEvent?.id, onDeleteEvent, onClose, reset]); + + return ( + +
    + + {currentEvent?.id ? 'Редактировать занятие' : 'Создать занятие'} + + + + + + + Выберите ученика + {students.map((student) => { + const studentName = student.user?.full_name || + student.full_name || + (student.user?.first_name ? `${student.user.first_name} ${student.user.last_name || ''}` : '') || + student.email || + `ID: ${student.id}`; + + const studentAvatar = student.user?.avatar || student.avatar; + const letter = studentName.charAt(0).toUpperCase(); + + return ( + + + + {letter} + + {studentName} + + + ); + })} + + + + Выберите предмет + {subjects.map((sub) => ( + + {sub.name || sub.subject_name || sub.title || `Предмет ID: ${sub.id}`} + + ))} + + + + + + + + + {DURATION_OPTIONS.map((option) => ( + + {option.label} + + ))} + + + ₽ + ), + }} + /> + + + } + /> + } + label="Постоянное занятие (повторяется еженедельно)" + sx={{ ml: 0 }} + /> + + + + + {currentEvent?.id && ( + + + + + + )} + + + + + + + {currentEvent?.id ? 'Сохранить изменения' : 'Создать'} + + +
    +
    + ); +} diff --git a/front_minimal/src/sections/calendar/calendar-toolbar.jsx b/front_minimal/src/sections/calendar/calendar-toolbar.jsx new file mode 100644 index 0000000..44e3f01 --- /dev/null +++ b/front_minimal/src/sections/calendar/calendar-toolbar.jsx @@ -0,0 +1,124 @@ +import Stack from '@mui/material/Stack'; +import Badge from '@mui/material/Badge'; +import Button from '@mui/material/Button'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LinearProgress from '@mui/material/LinearProgress'; + +import dayjs from 'dayjs'; // Импортируем dayjs напрямую для точного форматирования +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +const VIEW_OPTIONS = [ + { value: 'dayGridMonth', label: 'Месяц', icon: 'mingcute:calendar-month-line' }, + { value: 'timeGridWeek', label: 'Неделя', icon: 'mingcute:calendar-week-line' }, + { value: 'timeGridDay', label: 'День', icon: 'mingcute:calendar-day-line' }, + { value: 'listWeek', label: 'Повестка', icon: 'fluent:calendar-agenda-24-regular' }, +]; + +// ---------------------------------------------------------------------- + +export function CalendarToolbar({ + date, + view, + loading, + onToday, + canReset, + onNextDate, + onPrevDate, + onChangeView, + onOpenFilters, +}) { + const popover = usePopover(); + + const selectedItem = VIEW_OPTIONS.filter((item) => item.value === view)[0]; + + return ( + <> + + + + + + + + + + {dayjs(date).locale('ru').format('MMMM YYYY')} + + + + + + + + + + + + + + + + + + {loading && ( + + )} + + + + + {VIEW_OPTIONS.map((viewOption) => ( + { + popover.onClose(); + onChangeView(viewOption.value); + }} + > + + {viewOption.label} + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/calendar/hooks/use-calendar.js b/front_minimal/src/sections/calendar/hooks/use-calendar.js new file mode 100644 index 0000000..a9a8430 --- /dev/null +++ b/front_minimal/src/sections/calendar/hooks/use-calendar.js @@ -0,0 +1,164 @@ +import { useRef, useState, useCallback } from 'react'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +// ---------------------------------------------------------------------- + +export function useCalendar() { + const calendarRef = useRef(null); + + const calendarEl = calendarRef.current; + + const smUp = useResponsive('up', 'sm'); + + const [date, setDate] = useState(new Date()); + + const [openForm, setOpenForm] = useState(false); + + const [selectEventId, setSelectEventId] = useState(''); + + const [selectedRange, setSelectedRange] = useState(null); + + const [view, setView] = useState(smUp ? 'dayGridMonth' : 'listWeek'); + + const onOpenForm = useCallback(() => { + setOpenForm(true); + }, []); + + const onCloseForm = useCallback(() => { + setOpenForm(false); + setSelectedRange(null); + setSelectEventId(''); + }, []); + + const onInitialView = useCallback(() => { + if (calendarEl) { + const calendarApi = calendarEl.getApi(); + + const newView = smUp ? 'dayGridMonth' : 'listWeek'; + calendarApi.changeView(newView); + setView(newView); + } + }, [calendarEl, smUp]); + + const onChangeView = useCallback( + (newView) => { + if (calendarEl) { + const calendarApi = calendarEl.getApi(); + + calendarApi.changeView(newView); + setView(newView); + } + }, + [calendarEl] + ); + + const onDateToday = useCallback(() => { + if (calendarEl) { + const calendarApi = calendarEl.getApi(); + + calendarApi.today(); + setDate(calendarApi.getDate()); + } + }, [calendarEl]); + + const onDatePrev = useCallback(() => { + if (calendarEl) { + const calendarApi = calendarEl.getApi(); + + calendarApi.prev(); + setDate(calendarApi.getDate()); + } + }, [calendarEl]); + + const onDateNext = useCallback(() => { + if (calendarEl) { + const calendarApi = calendarEl.getApi(); + + calendarApi.next(); + setDate(calendarApi.getDate()); + } + }, [calendarEl]); + + const onSelectRange = useCallback( + (arg) => { + if (calendarEl) { + const calendarApi = calendarEl.getApi(); + + calendarApi.unselect(); + } + + onOpenForm(); + setSelectedRange({ start: arg.startStr, end: arg.endStr }); + }, + [calendarEl, onOpenForm] + ); + + const onClickEvent = useCallback( + (arg) => { + const { event } = arg; + + onOpenForm(); + setSelectEventId(event.id); + }, + [onOpenForm] + ); + + const onResizeEvent = useCallback((arg, updateEvent) => { + const { event } = arg; + + updateEvent({ + id: event.id, + allDay: event.allDay, + start: event.startStr, + end: event.endStr, + }); + }, []); + + const onDropEvent = useCallback((arg, updateEvent) => { + const { event } = arg; + + updateEvent({ + id: event.id, + allDay: event.allDay, + start: event.startStr, + end: event.endStr, + }); + }, []); + + const onClickEventInFilters = useCallback( + (eventId) => { + if (eventId) { + onOpenForm(); + setSelectEventId(eventId); + } + }, + [onOpenForm] + ); + + return { + calendarRef, + // + view, + date, + // + onDatePrev, + onDateNext, + onDateToday, + onDropEvent, + onClickEvent, + onChangeView, + onSelectRange, + onResizeEvent, + onInitialView, + // + openForm, + onOpenForm, + onCloseForm, + // + selectEventId, + selectedRange, + // + onClickEventInFilters, + }; +} diff --git a/front_minimal/src/sections/calendar/hooks/use-event.js b/front_minimal/src/sections/calendar/hooks/use-event.js new file mode 100644 index 0000000..b36e6c7 --- /dev/null +++ b/front_minimal/src/sections/calendar/hooks/use-event.js @@ -0,0 +1,33 @@ +import dayjs from 'dayjs'; +import { useMemo } from 'react'; + +import { CALENDAR_COLOR_OPTIONS } from 'src/_mock/_calendar'; + +// ---------------------------------------------------------------------- + +export function useEvent(events, selectEventId, selectedRange, openForm) { + const currentEvent = events.find((event) => event.id === selectEventId); + + const defaultValues = useMemo( + () => ({ + id: '', + title: '', + description: '', + color: CALENDAR_COLOR_OPTIONS[1], + allDay: false, + start: selectedRange ? selectedRange.start : dayjs(new Date()).format(), + end: selectedRange ? selectedRange.end : dayjs(new Date()).format(), + }), + [selectedRange] + ); + + if (!openForm) { + return undefined; + } + + if (currentEvent || selectedRange) { + return { ...defaultValues, ...currentEvent }; + } + + return defaultValues; +} diff --git a/front_minimal/src/sections/calendar/styles.jsx b/front_minimal/src/sections/calendar/styles.jsx new file mode 100644 index 0000000..e5553b5 --- /dev/null +++ b/front_minimal/src/sections/calendar/styles.jsx @@ -0,0 +1,145 @@ +import { styled } from '@mui/material/styles'; + +import { varAlpha } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +export const StyledCalendar = styled('div')(({ theme }) => ({ + width: 'calc(100% + 2px)', + marginLeft: -1, + marginBottom: -1, + + '& .fc': { + '--fc-border-color': varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + '--fc-now-indicator-color': theme.vars.palette.error.main, + '--fc-today-bg-color': varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + '--fc-page-bg-color': theme.vars.palette.background.default, + '--fc-neutral-bg-color': theme.vars.palette.background.neutral, + '--fc-list-event-hover-bg-color': theme.vars.palette.action.hover, + '--fc-highlight-color': theme.vars.palette.action.hover, + }, + + '& .fc .fc-license-message': { display: 'none' }, + '& .fc a': { color: theme.vars.palette.text.primary }, + + // Table Head + '& .fc .fc-col-header ': { + boxShadow: `inset 0 -1px 0 ${theme.vars.palette.divider}`, + '& th': { borderColor: 'transparent' }, + '& .fc-col-header-cell-cushion': { ...theme.typography.subtitle2, padding: '13px 0' }, + }, + + // List Empty + '& .fc .fc-list-empty': { + ...theme.typography.h6, + backgroundColor: 'transparent', + color: theme.vars.palette.text.secondary, + }, + + // Event + '& .fc .fc-event': { + borderColor: 'transparent', + backgroundColor: 'transparent', + }, + '& .fc .fc-event .fc-event-main': { + padding: '2px 4px', + borderRadius: 6, + color: theme.vars.palette.common.white, + backgroundColor: 'inherit', + '&::before': { + top: 0, + left: 0, + width: '100%', + content: "''", + opacity: 0.24, + height: '100%', + borderRadius: 6, + position: 'absolute', + backgroundColor: 'currentColor', + transition: theme.transitions.create(['opacity']), + }, + '&:hover': { + '&::before': { + opacity: 0.32, + }, + }, + }, + '& .fc .fc-event .fc-event-main-frame': { + fontSize: 13, + lineHeight: '20px', + color: '#FFFFFF', // Всегда белый текст + filter: 'brightness(1)', // Убираем затемнение, чтобы текст был чистым + }, + '& .fc .fc-daygrid-event .fc-event-title': { + overflow: 'hidden', + whiteSpace: 'nowrap', + color: '#FFFFFF', // Белый текст + textOverflow: 'ellipsis', + }, + '& .fc .fc-event .fc-event-time': { + overflow: 'unset', + color: '#FFFFFF', // Белый текст + fontWeight: theme.typography.fontWeightBold, + }, + + // Popover + '& .fc .fc-popover': { + border: 0, + overflow: 'hidden', + boxShadow: theme.customShadows.dropdown, + borderRadius: theme.shape.borderRadius * 1.5, + backgroundColor: theme.vars.palette.background.paper, + }, + '& .fc .fc-popover-header': { + ...theme.typography.subtitle2, + padding: theme.spacing(1), + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + }, + '& .fc .fc-popover-close': { + opacity: 0.48, + transition: theme.transitions.create(['opacity']), + '&:hover': { opacity: 1 }, + }, + '& .fc .fc-more-popover .fc-popover-body': { padding: theme.spacing(1) }, + '& .fc .fc-popover-body': { + '& .fc-daygrid-event.fc-event-start, & .fc-daygrid-event.fc-event-end': { margin: '2px 0' }, + }, + + // Month View + '& .fc .fc-day-other .fc-daygrid-day-top': { + opacity: 1, + '& .fc-daygrid-day-number': { color: theme.vars.palette.text.disabled }, + }, + '& .fc .fc-daygrid-day-number': { ...theme.typography.body2, padding: theme.spacing(1, 1, 0) }, + '& .fc .fc-daygrid-event': { marginTop: 4 }, + '& .fc .fc-daygrid-event.fc-event-start, & .fc .fc-daygrid-event.fc-event-end': { + marginLeft: 4, + marginRight: 4, + }, + '& .fc .fc-daygrid-more-link': { + ...theme.typography.caption, + color: theme.vars.palette.text.secondary, + '&:hover': { + backgroundColor: 'unset', + textDecoration: 'underline', + color: theme.vars.palette.text.primary, + fontWeight: theme.typography.fontWeightMedium, + }, + }, + + // Week & Day View + '& .fc .fc-timegrid-axis-cushion': { + ...theme.typography.body2, + color: theme.vars.palette.text.secondary, + }, + '& .fc .fc-timegrid-slot-label-cushion': { ...theme.typography.body2 }, + + // Agenda View + '& .fc-direction-ltr .fc-list-day-text, .fc-direction-rtl .fc-list-day-side-text, .fc-direction-ltr .fc-list-day-side-text, .fc-direction-rtl .fc-list-day-text': + { ...theme.typography.subtitle2 }, + '& .fc .fc-list-event': { + ...theme.typography.body2, + '& .fc-list-event-time': { color: theme.vars.palette.text.secondary }, + }, + '& .fc .fc-list-table': { '& th, td': { borderColor: 'transparent' } }, +})); diff --git a/front_minimal/src/sections/calendar/view/calendar-view.jsx b/front_minimal/src/sections/calendar/view/calendar-view.jsx new file mode 100644 index 0000000..e14f0c2 --- /dev/null +++ b/front_minimal/src/sections/calendar/view/calendar-view.jsx @@ -0,0 +1,200 @@ +'use client'; + +import FullCalendar from '@fullcalendar/react'; +import dayGridPlugin from '@fullcalendar/daygrid'; +import timeGridPlugin from '@fullcalendar/timegrid'; +import interactionPlugin from '@fullcalendar/interaction'; +import listPlugin from '@fullcalendar/list'; +import timelinePlugin from '@fullcalendar/timeline'; +import ruLocale from '@fullcalendar/core/locales/ru'; + +import { useState, useEffect, useCallback } from 'react'; + +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; +import { useBoolean } from 'src/hooks/use-boolean'; +import { useGetEvents, updateEvent, createEvent, deleteEvent } from 'src/actions/calendar'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; +import { useSettingsContext } from 'src/components/settings'; + +import { CalendarForm } from '../calendar-form'; +import { StyledCalendar } from '../styles'; +import { CalendarToolbar } from '../calendar-toolbar'; +import { CalendarFilters } from '../calendar-filters'; +import { useCalendar } from '../hooks/use-calendar'; + +// ---------------------------------------------------------------------- + +export function CalendarView() { + const settings = useSettingsContext(); + + const { events, eventsLoading } = useGetEvents(); + + const { + calendarRef, + view, + date, + onDatePrev, + onDateNext, + onDateToday, + onChangeView, + onSelectRange, + onClickEvent, + onResizeEvent, + onDropEvent, + onInitialView, + openForm, + onOpenForm, + onCloseForm, + selectEventId, + selectedRange, + onClickEventInFilters, + } = useCalendar(); + + const openFilters = useBoolean(); + + const [filters, setFilters] = useState({ + colors: [], + startDate: null, + endDate: null, + }); + + const dateError = filters.startDate && filters.endDate ? filters.startDate > filters.endDate : false; + + useEffect(() => { + onInitialView(); + }, [onInitialView]); + + const handleFilters = useCallback((name, value) => { + setFilters((prevState) => ({ + ...prevState, + [name]: value, + })); + }, []); + + const handleResetFilters = useCallback(() => { + setFilters({ + colors: [], + startDate: null, + endDate: null, + }); + }, []); + + const dataPrepared = events.filter((event) => { + const { colors, startDate, endDate } = filters; + + if (colors.length && !colors.includes(event.color)) { + return false; + } + + if (startDate && endDate) { + const eventStart = new Date(event.start); + const eventEnd = new Date(event.end); + return eventStart >= startDate && eventEnd <= endDate; + } + + return true; + }); + + return ( + <> + + + + Расписание + + + + + + + + + + + + + + + + event.id === selectEventId)} + range={selectedRange} + open={openForm} + onClose={onCloseForm} + onCreateEvent={createEvent} + onUpdateEvent={updateEvent} + onDeleteEvent={deleteEvent} + /> + + + + ); +} diff --git a/front_minimal/src/sections/calendar/view/index.js b/front_minimal/src/sections/calendar/view/index.js new file mode 100644 index 0000000..31ec58d --- /dev/null +++ b/front_minimal/src/sections/calendar/view/index.js @@ -0,0 +1 @@ +export * from './calendar-view'; diff --git a/front_minimal/src/sections/chat/chat-header-compose.jsx b/front_minimal/src/sections/chat/chat-header-compose.jsx new file mode 100644 index 0000000..10954cb --- /dev/null +++ b/front_minimal/src/sections/chat/chat-header-compose.jsx @@ -0,0 +1,104 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Chip from '@mui/material/Chip'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import Autocomplete from '@mui/material/Autocomplete'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { SearchNotFound } from 'src/components/search-not-found'; + +// ---------------------------------------------------------------------- + +export function ChatHeaderCompose({ contacts, onAddRecipients }) { + const [searchRecipients, setSearchRecipients] = useState(''); + + const handleAddRecipients = useCallback( + (selected) => { + setSearchRecipients(''); + onAddRecipients(selected); + }, + [onAddRecipients] + ); + + return ( + <> + + To: + + + } + onChange={(event, newValue) => handleAddRecipients(newValue)} + onInputChange={(event, newValue) => setSearchRecipients(newValue)} + options={contacts} + getOptionLabel={(recipient) => recipient.name} + isOptionEqualToValue={(option, value) => option.id === value.id} + renderInput={(params) => } + renderOption={(props, recipient, { selected }) => ( +
  • + + + varAlpha(theme.vars.palette.grey['900Channel'], 0.8), + transition: (theme) => + theme.transitions.create(['opacity'], { + easing: theme.transitions.easing.easeInOut, + duration: theme.transitions.duration.shorter, + }), + ...(selected && { opacity: 1, color: 'primary.main' }), + }} + > + + + + + {recipient.name} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((recipient, index) => ( + } + size="small" + variant="soft" + /> + )) + } + /> + + ); +} diff --git a/front_minimal/src/sections/chat/chat-header-detail.jsx b/front_minimal/src/sections/chat/chat-header-detail.jsx new file mode 100644 index 0000000..97cb2b4 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-header-detail.jsx @@ -0,0 +1,146 @@ +import { useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Badge from '@mui/material/Badge'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import ListItemText from '@mui/material/ListItemText'; +import AvatarGroup, { avatarGroupClasses } from '@mui/material/AvatarGroup'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +import { fToNow } from 'src/utils/format-time'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +import { ChatHeaderSkeleton } from './chat-skeleton'; + +// ---------------------------------------------------------------------- + +export function ChatHeaderDetail({ collapseNav, participants, loading }) { + const popover = usePopover(); + + const lgUp = useResponsive('up', 'lg'); + + const group = participants.length > 1; + + const singleParticipant = participants[0]; + + const { collapseDesktop, onCollapseDesktop, onOpenMobile } = collapseNav; + + const handleToggleNav = useCallback(() => { + if (lgUp) { + onCollapseDesktop(); + } else { + onOpenMobile(); + } + // eslint-disable-next-line react-hooks/exhaustive-deps + }, [lgUp]); + + const renderGroup = ( + + {participants.map((participant) => ( + + ))} + + ); + + const renderSingle = ( + + + + + + + + ); + + if (loading) { + return ; + } + + return ( + <> + {group ? renderGroup : renderSingle} + + + + + + + + + + + + + + + + + + + + + + { + popover.onClose(); + }} + > + + Hide notifications + + + { + popover.onClose(); + }} + > + + Block + + + { + popover.onClose(); + }} + > + + Report + + + + + { + popover.onClose(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + ); +} diff --git a/front_minimal/src/sections/chat/chat-message-input.jsx b/front_minimal/src/sections/chat/chat-message-input.jsx new file mode 100644 index 0000000..b9491f5 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-message-input.jsx @@ -0,0 +1,146 @@ +import { useRef, useMemo, useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import InputBase from '@mui/material/InputBase'; +import IconButton from '@mui/material/IconButton'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { uuidv4 } from 'src/utils/uuidv4'; +import { fSub, today } from 'src/utils/format-time'; + +import { sendMessage, createConversation } from 'src/actions/chat'; + +import { Iconify } from 'src/components/iconify'; + +import { useMockedUser } from 'src/auth/hooks'; + +// ---------------------------------------------------------------------- + +export function ChatMessageInput({ + disabled, + recipients, + onAddRecipients, + selectedConversationId, +}) { + const router = useRouter(); + + const { user } = useMockedUser(); + + const fileRef = useRef(null); + + const [message, setMessage] = useState(''); + + const myContact = useMemo( + () => ({ + id: `${user?.id}`, + role: `${user?.role}`, + email: `${user?.email}`, + address: `${user?.address}`, + name: `${user?.displayName}`, + lastActivity: today(), + avatarUrl: `${user?.photoURL}`, + phoneNumber: `${user?.phoneNumber}`, + status: 'online', + }), + [user] + ); + + const messageData = useMemo( + () => ({ + id: uuidv4(), + attachments: [], + body: message, + contentType: 'text', + createdAt: fSub({ minutes: 1 }), + senderId: myContact.id, + }), + [message, myContact.id] + ); + + const conversationData = useMemo( + () => ({ + id: uuidv4(), + messages: [messageData], + participants: [...recipients, myContact], + type: recipients.length > 1 ? 'GROUP' : 'ONE_TO_ONE', + unreadCount: 0, + }), + [messageData, myContact, recipients] + ); + + const handleAttach = useCallback(() => { + if (fileRef.current) { + fileRef.current.click(); + } + }, []); + + const handleChangeMessage = useCallback((event) => { + setMessage(event.target.value); + }, []); + + const handleSendMessage = useCallback( + async (event) => { + try { + if (event.key === 'Enter') { + if (message) { + if (selectedConversationId) { + await sendMessage(selectedConversationId, messageData); + } else { + const res = await createConversation(conversationData); + + router.push(`${paths.dashboard.chat}?id=${res.conversation.id}`); + + onAddRecipients([]); + } + } + setMessage(''); + } + } catch (error) { + console.error(error); + } + }, + [conversationData, message, messageData, onAddRecipients, router, selectedConversationId] + ); + + return ( + <> + + + + } + endAdornment={ + + + + + + + + + + + + } + sx={{ + px: 1, + height: 56, + flexShrink: 0, + borderTop: (theme) => `solid 1px ${theme.vars.palette.divider}`, + }} + /> + + + + ); +} diff --git a/front_minimal/src/sections/chat/chat-message-item.jsx b/front_minimal/src/sections/chat/chat-message-item.jsx new file mode 100644 index 0000000..8139238 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-message-item.jsx @@ -0,0 +1,124 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { fToNow } from 'src/utils/format-time'; + +import { Iconify } from 'src/components/iconify'; + +import { useMockedUser } from 'src/auth/hooks'; + +import { useMessage } from './hooks/use-message'; + +// ---------------------------------------------------------------------- + +export function ChatMessageItem({ message, participants, onOpenLightbox }) { + const { user } = useMockedUser(); + + const { me, senderDetails, hasImage } = useMessage({ + message, + participants, + currentUserId: `${user?.id}`, + }); + + const { firstName, avatarUrl } = senderDetails; + + const { body, createdAt } = message; + + const renderInfo = ( + + {!me && `${firstName}, `} + + {fToNow(createdAt)} + + ); + + const renderBody = ( + + {hasImage ? ( + onOpenLightbox(body)} + sx={{ + width: 400, + height: 'auto', + borderRadius: 1.5, + cursor: 'pointer', + objectFit: 'cover', + aspectRatio: '16/11', + '&:hover': { opacity: 0.9 }, + }} + /> + ) : ( + body + )} + + ); + + const renderActions = ( + + theme.transitions.create(['opacity'], { duration: theme.transitions.duration.shorter }), + ...(me && { right: 0, left: 'unset' }), + }} + > + + + + + + + + + + + + + ); + + return ( + + {!me && } + + + {renderInfo} + + + {renderBody} + {renderActions} + + + + ); +} diff --git a/front_minimal/src/sections/chat/chat-message-list.jsx b/front_minimal/src/sections/chat/chat-message-list.jsx new file mode 100644 index 0000000..c4b0a39 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-message-list.jsx @@ -0,0 +1,60 @@ +import Stack from '@mui/material/Stack'; +import LinearProgress from '@mui/material/LinearProgress'; + +import { Scrollbar } from 'src/components/scrollbar'; +import { Lightbox, useLightBox } from 'src/components/lightbox'; + +import { ChatMessageItem } from './chat-message-item'; +import { useMessagesScroll } from './hooks/use-messages-scroll'; + +// ---------------------------------------------------------------------- + +export function ChatMessageList({ messages = [], participants, loading }) { + const { messagesEndRef } = useMessagesScroll(messages); + + const slides = messages + .filter((message) => message.contentType === 'image') + .map((message) => ({ src: message.body })); + + const lightbox = useLightBox(slides); + + if (loading) { + return ( + + + + ); + } + + return ( + <> + + {messages.map((message) => ( + lightbox.onOpen(message.body)} + /> + ))} + + + + + ); +} diff --git a/front_minimal/src/sections/chat/chat-nav-account.jsx b/front_minimal/src/sections/chat/chat-nav-account.jsx new file mode 100644 index 0000000..b5891f5 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-nav-account.jsx @@ -0,0 +1,123 @@ +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Select from '@mui/material/Select'; +import Divider from '@mui/material/Divider'; +import Tooltip from '@mui/material/Tooltip'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import InputBase from '@mui/material/InputBase'; +import IconButton from '@mui/material/IconButton'; +import FormControl from '@mui/material/FormControl'; +import ListItemText from '@mui/material/ListItemText'; +import { svgIconClasses } from '@mui/material/SvgIcon'; +import Badge, { badgeClasses } from '@mui/material/Badge'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +import { useMockedUser } from 'src/auth/hooks'; + +// ---------------------------------------------------------------------- + +export function ChatNavAccount() { + const { user } = useMockedUser(); + + const popover = usePopover(); + + const [status, setStatus] = useState('online'); + + const handleChangeStatus = useCallback((event) => { + setStatus(event.target.value); + }, []); + + return ( + <> + + + {user?.displayName?.charAt(0).toUpperCase()} + + + + + + + + + + + + + + + + + + + + + + + + + + + + Profile + + + + + Settings + + + + + ); +} diff --git a/front_minimal/src/sections/chat/chat-nav-item.jsx b/front_minimal/src/sections/chat/chat-nav-item.jsx new file mode 100644 index 0000000..4f56b85 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-nav-item.jsx @@ -0,0 +1,133 @@ +import { useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Badge from '@mui/material/Badge'; +import Avatar from '@mui/material/Avatar'; +import Typography from '@mui/material/Typography'; +import AvatarGroup from '@mui/material/AvatarGroup'; +import ListItemText from '@mui/material/ListItemText'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +import { fToNow } from 'src/utils/format-time'; + +import { clickConversation } from 'src/actions/chat'; + +import { useMockedUser } from 'src/auth/hooks'; + +import { useNavItem } from './hooks/use-nav-item'; + +// ---------------------------------------------------------------------- + +export function ChatNavItem({ selected, collapse, conversation, onCloseMobile }) { + const { user } = useMockedUser(); + + const mdUp = useResponsive('up', 'md'); + + const router = useRouter(); + + const { group, displayName, displayText, participants, lastActivity, hasOnlineInGroup } = + useNavItem({ conversation, currentUserId: `${user?.id}` }); + + const singleParticipant = participants[0]; + + const { name, avatarUrl, status } = singleParticipant; + + const handleClickConversation = useCallback(async () => { + try { + if (!mdUp) { + onCloseMobile(); + } + + await clickConversation(conversation.id); + + router.push(`${paths.dashboard.chat}?id=${conversation.id}`); + } catch (error) { + console.error(error); + } + }, [conversation.id, mdUp, onCloseMobile, router]); + + const renderGroup = ( + + + {participants.slice(0, 2).map((participant) => ( + + ))} + + + ); + + const renderSingle = ( + + + + ); + + return ( + + + + {group ? renderGroup : renderSingle} + + + {!collapse && ( + <> + + + + + {fToNow(lastActivity)} + + + {!!conversation.unreadCount && ( + + )} + + + )} + + + ); +} diff --git a/front_minimal/src/sections/chat/chat-nav-search-results.jsx b/front_minimal/src/sections/chat/chat-nav-search-results.jsx new file mode 100644 index 0000000..332fb25 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-nav-search-results.jsx @@ -0,0 +1,54 @@ +import Box from '@mui/material/Box'; +import Avatar from '@mui/material/Avatar'; +import Typography from '@mui/material/Typography'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { SearchNotFound } from 'src/components/search-not-found'; + +// ---------------------------------------------------------------------- + +export function ChatNavSearchResults({ query, results, onClickResult }) { + const totalResults = results.length; + + const notFound = !totalResults && !!query; + + const renderNotFound = ( + + ); + + const renderResults = ( + + ); + + return ( + <> + + Contacts ({totalResults}) + + + {notFound ? renderNotFound : renderResults} + + ); +} diff --git a/front_minimal/src/sections/chat/chat-nav.jsx b/front_minimal/src/sections/chat/chat-nav.jsx new file mode 100644 index 0000000..3f92383 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-nav.jsx @@ -0,0 +1,213 @@ +import { useState, useEffect, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Drawer from '@mui/material/Drawer'; +import { useTheme } from '@mui/material/styles'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import InputAdornment from '@mui/material/InputAdornment'; +import ClickAwayListener from '@mui/material/ClickAwayListener'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; + +import { ToggleButton } from './styles'; +import { ChatNavItem } from './chat-nav-item'; +import { ChatNavAccount } from './chat-nav-account'; +import { ChatNavItemSkeleton } from './chat-skeleton'; +import { ChatNavSearchResults } from './chat-nav-search-results'; + +// ---------------------------------------------------------------------- + +const NAV_WIDTH = 320; + +const NAV_COLLAPSE_WIDTH = 96; + +// ---------------------------------------------------------------------- + +export function ChatNav({ loading, contacts, conversations, collapseNav, selectedConversationId }) { + const theme = useTheme(); + + const router = useRouter(); + + const mdUp = useResponsive('up', 'md'); + + const { + openMobile, + onOpenMobile, + onCloseMobile, + onCloseDesktop, + collapseDesktop, + onCollapseDesktop, + } = collapseNav; + + const [searchContacts, setSearchContacts] = useState({ query: '', results: [] }); + + useEffect(() => { + if (!mdUp) { + onCloseDesktop(); + } + }, [onCloseDesktop, mdUp]); + + const handleToggleNav = useCallback(() => { + if (mdUp) { + onCollapseDesktop(); + } else { + onCloseMobile(); + } + }, [mdUp, onCloseMobile, onCollapseDesktop]); + + const handleClickCompose = useCallback(() => { + if (!mdUp) { + onCloseMobile(); + } + router.push(paths.dashboard.chat); + }, [mdUp, onCloseMobile, router]); + + const handleSearchContacts = useCallback( + (inputValue) => { + setSearchContacts((prevState) => ({ ...prevState, query: inputValue })); + + if (inputValue) { + const results = contacts.filter((contact) => + contact.name.toLowerCase().includes(inputValue) + ); + + setSearchContacts((prevState) => ({ ...prevState, results })); + } + }, + [contacts] + ); + + const handleClickAwaySearch = useCallback(() => { + setSearchContacts({ query: '', results: [] }); + }, []); + + const handleClickResult = useCallback( + (result) => { + handleClickAwaySearch(); + + router.push(`${paths.dashboard.chat}?id=${result.id}`); + }, + [handleClickAwaySearch, router] + ); + + const renderLoading = ; + + const renderList = ( + + ); + + const renderListResults = ( + + ); + + const renderSearchInput = ( + + handleSearchContacts(event.target.value)} + placeholder="Search contacts..." + InputProps={{ + startAdornment: ( + + + + ), + }} + sx={{ mt: 2.5 }} + /> + + ); + + const renderContent = ( + <> + + {!collapseDesktop && ( + <> + + + + )} + + + + + + {!collapseDesktop && ( + + + + )} + + + {!collapseDesktop && renderSearchInput} + + {loading ? ( + renderLoading + ) : ( + + {searchContacts.query && !!conversations.allIds.length ? renderListResults : renderList} + + )} + + ); + + return ( + <> + + + + + + {renderContent} + + + + {renderContent} + + + ); +} diff --git a/front_minimal/src/sections/chat/chat-room-attachments.jsx b/front_minimal/src/sections/chat/chat-room-attachments.jsx new file mode 100644 index 0000000..33766d9 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-room-attachments.jsx @@ -0,0 +1,64 @@ +import Stack from '@mui/material/Stack'; +import Collapse from '@mui/material/Collapse'; +import ListItemText from '@mui/material/ListItemText'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { fDateTime } from 'src/utils/format-time'; + +import { FileThumbnail } from 'src/components/file-thumbnail'; + +import { CollapseButton } from './styles'; + +// ---------------------------------------------------------------------- + +export function ChatRoomAttachments({ attachments }) { + const collapse = useBoolean(true); + + const totalAttachments = attachments.length; + + const renderList = attachments.map((attachment, index) => ( + + console.info('DOWNLOAD')} + slotProps={{ icon: { width: 24, height: 24 } }} + sx={{ width: 40, height: 40, bgcolor: 'background.neutral' }} + /> + + + + )); + + return ( + <> + + {`Attachments (${totalAttachments})`} + + + {!!totalAttachments && ( + + + {renderList} + + + )} + + ); +} diff --git a/front_minimal/src/sections/chat/chat-room-group.jsx b/front_minimal/src/sections/chat/chat-room-group.jsx new file mode 100644 index 0000000..c90e04e --- /dev/null +++ b/front_minimal/src/sections/chat/chat-room-group.jsx @@ -0,0 +1,71 @@ +import { useState, useCallback } from 'react'; + +import Badge from '@mui/material/Badge'; +import Avatar from '@mui/material/Avatar'; +import Collapse from '@mui/material/Collapse'; +import ListItemText from '@mui/material/ListItemText'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { CollapseButton } from './styles'; +import { ChatRoomParticipantDialog } from './chat-room-participant-dialog'; + +// ---------------------------------------------------------------------- + +export function ChatRoomGroup({ participants }) { + const collapse = useBoolean(true); + + const [selected, setSelected] = useState(null); + + const handleOpen = useCallback((participant) => { + setSelected(participant); + }, []); + + const handleClose = useCallback(() => { + setSelected(null); + }, []); + + const totalParticipants = participants.length; + + const renderList = ( + <> + {participants.map((participant) => ( + handleOpen(participant)}> + + + + + + + ))} + + ); + + return ( + <> + + {`In room (${totalParticipants})`} + + + {renderList} + + {selected && ( + + )} + + ); +} diff --git a/front_minimal/src/sections/chat/chat-room-participant-dialog.jsx b/front_minimal/src/sections/chat/chat-room-participant-dialog.jsx new file mode 100644 index 0000000..e5ac674 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-room-participant-dialog.jsx @@ -0,0 +1,105 @@ +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Dialog from '@mui/material/Dialog'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import DialogContent from '@mui/material/DialogContent'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function ChatRoomParticipantDialog({ participant, open, onClose }) { + return ( + + + + + + + + + + + {participant.role} + + + {participant.name} + + + + {participant.address} + + + + varAlpha(theme.vars.palette.error.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.error.mainChannel, 0.16), + }, + }} + > + + + + varAlpha(theme.vars.palette.info.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.info.mainChannel, 0.16), + }, + }} + > + + + + varAlpha(theme.vars.palette.primary.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.primary.mainChannel, 0.16), + }, + }} + > + + + + varAlpha(theme.vars.palette.secondary.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.secondary.mainChannel, 0.16), + }, + }} + > + + + + + + + ); +} diff --git a/front_minimal/src/sections/chat/chat-room-single.jsx b/front_minimal/src/sections/chat/chat-room-single.jsx new file mode 100644 index 0000000..9b4b05c --- /dev/null +++ b/front_minimal/src/sections/chat/chat-room-single.jsx @@ -0,0 +1,62 @@ +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Collapse from '@mui/material/Collapse'; +import Typography from '@mui/material/Typography'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; + +import { CollapseButton } from './styles'; + +// ---------------------------------------------------------------------- + +export function ChatRoomSingle({ participant }) { + const collapse = useBoolean(true); + + const renderInfo = ( + + + {participant?.name} + + {participant?.role} + + + ); + + const renderContact = ( + + {[ + { icon: 'mingcute:location-fill', value: participant?.address }, + { icon: 'solar:phone-bold', value: participant?.phoneNumber }, + { icon: 'fluent:mail-24-filled', value: participant?.email }, + ].map((item) => ( + + + {item.value} + + ))} + + ); + + return ( + <> + {renderInfo} + + + Information + + + {renderContact} + + ); +} diff --git a/front_minimal/src/sections/chat/chat-room.jsx b/front_minimal/src/sections/chat/chat-room.jsx new file mode 100644 index 0000000..1a080f1 --- /dev/null +++ b/front_minimal/src/sections/chat/chat-room.jsx @@ -0,0 +1,72 @@ +import Stack from '@mui/material/Stack'; +import Drawer from '@mui/material/Drawer'; +import { useTheme } from '@mui/material/styles'; + +import { Scrollbar } from 'src/components/scrollbar'; + +import { ChatRoomGroup } from './chat-room-group'; +import { ChatRoomSkeleton } from './chat-skeleton'; +import { ChatRoomSingle } from './chat-room-single'; +import { ChatRoomAttachments } from './chat-room-attachments'; + +// ---------------------------------------------------------------------- + +const NAV_WIDTH = 280; + +const NAV_DRAWER_WIDTH = 320; + +export function ChatRoom({ collapseNav, participants, messages, loading }) { + const theme = useTheme(); + + const { collapseDesktop, openMobile, onCloseMobile } = collapseNav; + + const group = participants.length > 1; + + const attachments = messages.map((msg) => msg.attachments).flat(1) || []; + + const renderContent = loading ? ( + + ) : ( + +
    + {group ? ( + + ) : ( + + )} + + +
    +
    + ); + + return ( + <> + + {!collapseDesktop && renderContent} + + + + {renderContent} + + + ); +} diff --git a/front_minimal/src/sections/chat/chat-skeleton.jsx b/front_minimal/src/sections/chat/chat-skeleton.jsx new file mode 100644 index 0000000..bb4422c --- /dev/null +++ b/front_minimal/src/sections/chat/chat-skeleton.jsx @@ -0,0 +1,57 @@ +import Stack from '@mui/material/Stack'; +import Skeleton from '@mui/material/Skeleton'; +import CircularProgress from '@mui/material/CircularProgress'; + +// ---------------------------------------------------------------------- + +export function ChatNavItemSkeleton({ sx, amount = 6, ...other }) { + return [...Array(amount)].map((_, index) => ( + + + + + + + + + )); +} + +// ---------------------------------------------------------------------- + +export function ChatHeaderSkeleton({ sx, ...other }) { + return ( + + + + + + + + + + + ); +} + +// ---------------------------------------------------------------------- + +export function ChatRoomSkeleton({ sx, ...other }) { + return ( + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/chat/hooks/use-collapse-nav.js b/front_minimal/src/sections/chat/hooks/use-collapse-nav.js new file mode 100644 index 0000000..b795724 --- /dev/null +++ b/front_minimal/src/sections/chat/hooks/use-collapse-nav.js @@ -0,0 +1,35 @@ +import { useState, useCallback } from 'react'; + +// ---------------------------------------------------------------------- + +export function useCollapseNav() { + const [openMobile, setOpenMobile] = useState(false); + + const [collapseDesktop, setCollapseDesktop] = useState(false); + + const onCollapseDesktop = useCallback(() => { + setCollapseDesktop((prev) => !prev); + }, []); + + const onCloseDesktop = useCallback(() => { + setCollapseDesktop(false); + }, []); + + const onOpenMobile = useCallback(() => { + setOpenMobile(true); + }, []); + + const onCloseMobile = useCallback(() => { + setOpenMobile(false); + }, []); + + return { + collapseDesktop, + onCloseDesktop, + onCollapseDesktop, + // + openMobile, + onOpenMobile, + onCloseMobile, + }; +} diff --git a/front_minimal/src/sections/chat/hooks/use-message.js b/front_minimal/src/sections/chat/hooks/use-message.js new file mode 100644 index 0000000..ba89123 --- /dev/null +++ b/front_minimal/src/sections/chat/hooks/use-message.js @@ -0,0 +1,16 @@ +// ---------------------------------------------------------------------- + +export function useMessage({ message, participants, currentUserId }) { + const sender = participants.find((participant) => participant.id === message.senderId); + + const senderDetails = + message.senderId === currentUserId + ? { type: 'me' } + : { avatarUrl: sender?.avatarUrl, firstName: sender?.name.split(' ')[0] }; + + const me = senderDetails.type === 'me'; + + const hasImage = message.contentType === 'image'; + + return { hasImage, me, senderDetails }; +} diff --git a/front_minimal/src/sections/chat/hooks/use-messages-scroll.js b/front_minimal/src/sections/chat/hooks/use-messages-scroll.js new file mode 100644 index 0000000..0b27589 --- /dev/null +++ b/front_minimal/src/sections/chat/hooks/use-messages-scroll.js @@ -0,0 +1,28 @@ +import { useRef, useEffect, useCallback } from 'react'; + +// ---------------------------------------------------------------------- + +export function useMessagesScroll(messages) { + const messagesEndRef = useRef(null); + + const scrollToBottom = useCallback(() => { + if (!messages) { + return; + } + + if (!messagesEndRef.current) { + return; + } + + if (messagesEndRef.current) { + messagesEndRef.current.scrollTop = messagesEndRef.current.scrollHeight; + } + }, [messages]); + + useEffect(() => { + scrollToBottom(); + // eslint-disable-next-line react-hooks/exhaustive-deps + }, [messages]); + + return { messagesEndRef }; +} diff --git a/front_minimal/src/sections/chat/hooks/use-nav-item.js b/front_minimal/src/sections/chat/hooks/use-nav-item.js new file mode 100644 index 0000000..c447330 --- /dev/null +++ b/front_minimal/src/sections/chat/hooks/use-nav-item.js @@ -0,0 +1,38 @@ +// ---------------------------------------------------------------------- + +export function useNavItem({ currentUserId, conversation }) { + const { messages, participants } = conversation; + + const participantsInConversation = participants.filter( + (participant) => participant.id !== currentUserId + ); + + const lastMessage = messages[messages.length - 1]; + + const group = participantsInConversation.length > 1; + + const displayName = participantsInConversation.map((participant) => participant.name).join(', '); + + const hasOnlineInGroup = group + ? participantsInConversation.map((item) => item.status).includes('online') + : false; + + let displayText = ''; + + if (lastMessage) { + const sender = lastMessage.senderId === currentUserId ? 'You: ' : ''; + + const message = lastMessage.contentType === 'image' ? 'Sent a photo' : lastMessage.body; + + displayText = `${sender}${message}`; + } + + return { + group, + displayName, + displayText, + participants: participantsInConversation, + lastActivity: lastMessage.createdAt, + hasOnlineInGroup, + }; +} diff --git a/front_minimal/src/sections/chat/layout.jsx b/front_minimal/src/sections/chat/layout.jsx new file mode 100644 index 0000000..92642bd --- /dev/null +++ b/front_minimal/src/sections/chat/layout.jsx @@ -0,0 +1,48 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; + +// ---------------------------------------------------------------------- + +export function Layout({ slots, sx, ...other }) { + const renderNav = ( + + {slots.nav} + + ); + + const renderHeader = ( + `solid 1px ${theme.vars.palette.divider}`, + }} + > + {slots.header} + + ); + + const renderMain = {slots.main}; + + const renderDetails = {slots.details}; + + return ( + + {renderNav} + + + {renderHeader} + + + {renderMain} + {renderDetails} + + + + ); +} diff --git a/front_minimal/src/sections/chat/styles.jsx b/front_minimal/src/sections/chat/styles.jsx new file mode 100644 index 0000000..19224aa --- /dev/null +++ b/front_minimal/src/sections/chat/styles.jsx @@ -0,0 +1,44 @@ +import { styled } from '@mui/material/styles'; +import ButtonBase from '@mui/material/ButtonBase'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export const CollapseButton = styled(({ selected, children, disabled, ...other }) => ( + + {children} + + +))(({ theme }) => ({ + ...theme.typography.overline, + height: 40, + paddingLeft: theme.spacing(2.5), + justifyContent: 'space-between', + paddingRight: theme.spacing(1.5), + color: theme.vars.palette.text.secondary, + backgroundColor: theme.vars.palette.background.neutral, +})); + +// ---------------------------------------------------------------------- + +export const ToggleButton = styled(ButtonBase)(({ theme }) => ({ + top: 84, + left: 0, + zIndex: 9, + width: 32, + height: 32, + position: 'absolute', + borderRadius: `0 12px 12px 0`, + boxShadow: theme.customShadows.primary, + color: theme.vars.palette.primary.contrastText, + backgroundColor: theme.vars.palette.primary.main, + transition: theme.transitions.create(['all'], { duration: theme.transitions.duration.shorter }), + '&:hover': { backgroundColor: theme.vars.palette.primary.darker }, +})); diff --git a/front_minimal/src/sections/chat/view/chat-view.jsx b/front_minimal/src/sections/chat/view/chat-view.jsx new file mode 100644 index 0000000..0e057b3 --- /dev/null +++ b/front_minimal/src/sections/chat/view/chat-view.jsx @@ -0,0 +1,139 @@ +'use client'; + +import { useState, useEffect, useCallback } from 'react'; + +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; +import { useRouter, useSearchParams } from 'src/routes/hooks'; + +import { CONFIG } from 'src/config-global'; +import { DashboardContent } from 'src/layouts/dashboard'; +import { useGetContacts, useGetConversation, useGetConversations } from 'src/actions/chat'; + +import { EmptyContent } from 'src/components/empty-content'; + +import { useMockedUser } from 'src/auth/hooks'; + +import { Layout } from '../layout'; +import { ChatNav } from '../chat-nav'; +import { ChatRoom } from '../chat-room'; +import { ChatMessageList } from '../chat-message-list'; +import { ChatMessageInput } from '../chat-message-input'; +import { ChatHeaderDetail } from '../chat-header-detail'; +import { ChatHeaderCompose } from '../chat-header-compose'; +import { useCollapseNav } from '../hooks/use-collapse-nav'; + +// ---------------------------------------------------------------------- + +export function ChatView() { + const router = useRouter(); + + const { user } = useMockedUser(); + + const { contacts } = useGetContacts(); + + const searchParams = useSearchParams(); + + const selectedConversationId = searchParams.get('id') || ''; + + const [recipients, setRecipients] = useState([]); + + const { conversations, conversationsLoading } = useGetConversations(); + + const { conversation, conversationError, conversationLoading } = useGetConversation( + `${selectedConversationId}` + ); + + const roomNav = useCollapseNav(); + + const conversationsNav = useCollapseNav(); + + const participants = conversation + ? conversation.participants.filter((participant) => participant.id !== `${user?.id}`) + : []; + + useEffect(() => { + if (conversationError || !selectedConversationId) { + router.push(paths.dashboard.chat); + } + }, [conversationError, router, selectedConversationId]); + + const handleAddRecipients = useCallback((selected) => { + setRecipients(selected); + }, []); + + return ( + + + Chat + + + theme.customShadows.card, + }} + slots={{ + header: selectedConversationId ? ( + + ) : ( + + ), + nav: ( + + ), + main: ( + <> + {selectedConversationId ? ( + + ) : ( + + )} + + + + ), + details: selectedConversationId && ( + + ), + }} + /> + + ); +} diff --git a/front_minimal/src/sections/chat/view/index.js b/front_minimal/src/sections/chat/view/index.js new file mode 100644 index 0000000..ecfab5f --- /dev/null +++ b/front_minimal/src/sections/chat/view/index.js @@ -0,0 +1 @@ +export * from './chat-view'; diff --git a/front_minimal/src/sections/checkout/checkout-billing-address.jsx b/front_minimal/src/sections/checkout/checkout-billing-address.jsx new file mode 100644 index 0000000..19ba29a --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-billing-address.jsx @@ -0,0 +1,92 @@ +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Grid from '@mui/material/Unstable_Grid2'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { _addressBooks } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; + +import { useCheckoutContext } from './context'; +import { CheckoutSummary } from './checkout-summary'; +import { AddressItem, AddressNewForm } from '../address'; + +// ---------------------------------------------------------------------- + +export function CheckoutBillingAddress() { + const checkout = useCheckoutContext(); + + const addressForm = useBoolean(); + + return ( + <> + + + {_addressBooks.slice(0, 4).map((address) => ( + + {!address.primary && ( + + )} + + + } + sx={{ + p: 3, + mb: 3, + borderRadius: 2, + boxShadow: (theme) => theme.customShadows.card, + }} + /> + ))} + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/checkout/checkout-billing-info.jsx b/front_minimal/src/sections/checkout/checkout-billing-info.jsx new file mode 100644 index 0000000..c959202 --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-billing-info.jsx @@ -0,0 +1,36 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import CardHeader from '@mui/material/CardHeader'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function CheckoutBillingInfo({ billing, onBackStep }) { + return ( + + } onClick={onBackStep}> + Edit + + } + /> + + + {`${billing?.name} `} + + ({billing?.addressType}) + + + + {billing?.fullAddress} + + {billing?.phoneNumber} + + + ); +} diff --git a/front_minimal/src/sections/checkout/checkout-cart-product-list.jsx b/front_minimal/src/sections/checkout/checkout-cart-product-list.jsx new file mode 100644 index 0000000..9e1e114 --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-cart-product-list.jsx @@ -0,0 +1,46 @@ +import Table from '@mui/material/Table'; +import TableBody from '@mui/material/TableBody'; + +import { Scrollbar } from 'src/components/scrollbar'; +import { TableHeadCustom } from 'src/components/table'; + +import { CheckoutCartProduct } from './checkout-cart-product'; + +// ---------------------------------------------------------------------- + +const TABLE_HEAD = [ + { id: 'product', label: 'Product' }, + { id: 'price', label: 'Price' }, + { id: 'quantity', label: 'Quantity' }, + { id: 'totalAmount', label: 'Total Price', align: 'right' }, + { id: '' }, +]; + +// ---------------------------------------------------------------------- + +export function CheckoutCartProductList({ + products, + onDelete, + onIncreaseQuantity, + onDecreaseQuantity, +}) { + return ( + + + + + + {products.map((row) => ( + onDelete(row.id)} + onDecrease={() => onDecreaseQuantity(row.id)} + onIncrease={() => onIncreaseQuantity(row.id)} + /> + ))} + +
    +
    + ); +} diff --git a/front_minimal/src/sections/checkout/checkout-cart-product.jsx b/front_minimal/src/sections/checkout/checkout-cart-product.jsx new file mode 100644 index 0000000..5291377 --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-cart-product.jsx @@ -0,0 +1,77 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import TableRow from '@mui/material/TableRow'; +import TableCell from '@mui/material/TableCell'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { fCurrency } from 'src/utils/format-number'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { ColorPreview } from 'src/components/color-utils'; + +import { IncrementerButton } from '../product/components/incrementer-button'; + +// ---------------------------------------------------------------------- + +export function CheckoutCartProduct({ row, onDelete, onDecrease, onIncrease }) { + return ( + + + + + + + + {row.name} + + + + size: + + + + + + + + {fCurrency(row.price)} + + + + = row.available} + /> + + + available: {row.available} + + + + + {fCurrency(row.price * row.quantity)} + + + + + + + + ); +} diff --git a/front_minimal/src/sections/checkout/checkout-cart.jsx b/front_minimal/src/sections/checkout/checkout-cart.jsx new file mode 100644 index 0000000..17117c4 --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-cart.jsx @@ -0,0 +1,91 @@ +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; +import Grid from '@mui/material/Unstable_Grid2'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { CONFIG } from 'src/config-global'; + +import { Iconify } from 'src/components/iconify'; +import { EmptyContent } from 'src/components/empty-content'; + +import { useCheckoutContext } from './context'; +import { CheckoutSummary } from './checkout-summary'; +import { CheckoutCartProductList } from './checkout-cart-product-list'; + +// ---------------------------------------------------------------------- + +export function CheckoutCart() { + const checkout = useCheckoutContext(); + + const empty = !checkout.items.length; + + return ( + + + + + Cart + +  ( + {checkout.totalItems} item) + + + } + sx={{ mb: 3 }} + /> + + {empty ? ( + + ) : ( + + )} + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/checkout/checkout-delivery.jsx b/front_minimal/src/sections/checkout/checkout-delivery.jsx new file mode 100644 index 0000000..0f2fe4e --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-delivery.jsx @@ -0,0 +1,85 @@ +import { Controller, useFormContext } from 'react-hook-form'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Paper from '@mui/material/Paper'; +import CardHeader from '@mui/material/CardHeader'; +import ListItemText from '@mui/material/ListItemText'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function CheckoutDelivery({ options, onApplyShipping, ...other }) { + const { control } = useFormContext(); + + return ( + + + + ( + + {options.map((option) => ( + { + field.onChange(option.value); + onApplyShipping(option.value); + }} + /> + ))} + + )} + /> + + ); +} + +function OptionItem({ option, selected, ...other }) { + const { value, label, description } = option; + + return ( + `0 0 0 2px ${theme.vars.palette.text.primary}` }), + }} + {...other} + > + {label === 'Free' && } + {label === 'Standard' && } + {label === 'Express' && } + + + + {label} + + {`$${value}`} + + } + secondary={description} + primaryTypographyProps={{ typography: 'subtitle1', mb: 0.5 }} + secondaryTypographyProps={{ typography: 'body2' }} + /> + + ); +} diff --git a/front_minimal/src/sections/checkout/checkout-order-complete.jsx b/front_minimal/src/sections/checkout/checkout-order-complete.jsx new file mode 100644 index 0000000..cff9dda --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-order-complete.jsx @@ -0,0 +1,81 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import Divider from '@mui/material/Divider'; +import Typography from '@mui/material/Typography'; + +import { OrderCompleteIllustration } from 'src/assets/illustrations'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function CheckoutOrderComplete({ open, onReset, onDownloadPDF }) { + return ( + + + Thank you for your purchase! + + + + + Thanks for placing order +
    +
    + 01dc1370-3df6-11eb-b378-0242ac130002 +
    +
    + We will send you a notification within 5 days when it ships. +
    If you have any question or queries then fell to get in contact us.
    + All the best, +
    + + + + + + + + +
    +
    + ); +} diff --git a/front_minimal/src/sections/checkout/checkout-payment-methods.jsx b/front_minimal/src/sections/checkout/checkout-payment-methods.jsx new file mode 100644 index 0000000..0ad3713 --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-payment-methods.jsx @@ -0,0 +1,126 @@ +import { Controller, useFormContext } from 'react-hook-form'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Paper from '@mui/material/Paper'; +import Button from '@mui/material/Button'; +import TextField from '@mui/material/TextField'; +import CardHeader from '@mui/material/CardHeader'; +import ListItemText from '@mui/material/ListItemText'; +import FormHelperText from '@mui/material/FormHelperText'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; + +import { PaymentNewCardDialog } from '../payment/payment-new-card-dialog'; + +// ---------------------------------------------------------------------- + +export function CheckoutPaymentMethods({ options, ...other }) { + const { control } = useFormContext(); + + const newCard = useBoolean(); + + return ( + <> + + + + ( + + {options.payments.map((option) => ( + { + field.onChange(option.value); + }} + /> + ))} + + {!!error && ( + + {error.message} + + )} + + )} + /> + + + + + ); +} + +function OptionItem({ option, cardOptions, selected, isCredit, onOpen, ...other }) { + const { value, label, description } = option; + + return ( + `0 0 0 2px ${theme.vars.palette.text.primary}` }), + }} + {...other} + > + + + {label} + + + {value === 'credit' && ( + <> + + , + + + )} + {value === 'paypal' && } + {value === 'cash' && } + + + } + secondary={description} + primaryTypographyProps={{ typography: 'subtitle1', mb: 0.5 }} + secondaryTypographyProps={{ typography: 'body2' }} + /> + + {isCredit && ( + + + {cardOptions.map((card) => ( + + ))} + + + + + )} + + ); +} diff --git a/front_minimal/src/sections/checkout/checkout-payment.jsx b/front_minimal/src/sections/checkout/checkout-payment.jsx new file mode 100644 index 0000000..f642019 --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-payment.jsx @@ -0,0 +1,129 @@ +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Button from '@mui/material/Button'; +import Grid from '@mui/material/Unstable_Grid2'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { Form } from 'src/components/hook-form'; +import { Iconify } from 'src/components/iconify'; + +import { useCheckoutContext } from './context'; +import { CheckoutSummary } from './checkout-summary'; +import { CheckoutDelivery } from './checkout-delivery'; +import { CheckoutBillingInfo } from './checkout-billing-info'; +import { CheckoutPaymentMethods } from './checkout-payment-methods'; + +// ---------------------------------------------------------------------- + +const DELIVERY_OPTIONS = [ + { value: 0, label: 'Free', description: '5-7 days delivery' }, + { value: 10, label: 'Standard', description: '3-5 days delivery' }, + { value: 20, label: 'Express', description: '2-3 days delivery' }, +]; + +const PAYMENT_OPTIONS = [ + { + value: 'paypal', + label: 'Pay with Paypal', + description: 'You will be redirected to PayPal website to complete your purchase securely.', + }, + { + value: 'credit', + label: 'Credit / Debit card', + description: 'We support Mastercard, Visa, Discover and Stripe.', + }, + { value: 'cash', label: 'Cash', description: 'Pay with cash when your order is delivered.' }, +]; + +const CARDS_OPTIONS = [ + { value: 'ViSa1', label: '**** **** **** 1212 - Jimmy Holland' }, + { value: 'ViSa2', label: '**** **** **** 2424 - Shawn Stokes' }, + { value: 'MasterCard', label: '**** **** **** 4545 - Cole Armstrong' }, +]; + +// ---------------------------------------------------------------------- + +export const PaymentSchema = zod.object({ + payment: zod.string().min(1, { message: 'Payment is required!' }), + // Not required + delivery: zod.number(), +}); + +// ---------------------------------------------------------------------- + +export function CheckoutPayment() { + const checkout = useCheckoutContext(); + + const defaultValues = { delivery: checkout.shipping, payment: '' }; + + const methods = useForm({ + resolver: zodResolver(PaymentSchema), + defaultValues, + }); + + const { + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + checkout.onNextStep(); + checkout.onReset(); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + return ( +
    + + + + + + + + + + + + + checkout.onGotoStep(0)} + /> + + + Complete order + + + +
    + ); +} diff --git a/front_minimal/src/sections/checkout/checkout-steps.jsx b/front_minimal/src/sections/checkout/checkout-steps.jsx new file mode 100644 index 0000000..0d41958 --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-steps.jsx @@ -0,0 +1,77 @@ +import Box from '@mui/material/Box'; +import Step from '@mui/material/Step'; +import Stack from '@mui/material/Stack'; +import Stepper from '@mui/material/Stepper'; +import { styled } from '@mui/material/styles'; +import StepLabel, { stepLabelClasses } from '@mui/material/StepLabel'; +import MuiStepConnector, { stepConnectorClasses } from '@mui/material/StepConnector'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +const StepConnector = styled(MuiStepConnector)(({ theme }) => ({ + top: 10, + left: 'calc(-50% + 20px)', + right: 'calc(50% + 20px)', + [`& .${stepConnectorClasses.line}`]: { + borderTopWidth: 2, + borderColor: theme.vars.palette.divider, + }, + [`&.${stepConnectorClasses.active}, &.${stepConnectorClasses.completed}`]: { + [`& .${stepConnectorClasses.line}`]: { borderColor: theme.vars.palette.primary.main }, + }, +})); + +// ---------------------------------------------------------------------- + +export function CheckoutSteps({ steps, activeStep, sx, ...other }) { + return ( + } + sx={{ mb: { xs: 3, md: 5 }, ...sx }} + {...other} + > + {steps.map((label) => ( + + + {label} + + + ))} + + ); +} + +function StepIcon({ active, completed }) { + return ( + + {completed ? ( + + ) : ( + + )} + + ); +} diff --git a/front_minimal/src/sections/checkout/checkout-summary.jsx b/front_minimal/src/sections/checkout/checkout-summary.jsx new file mode 100644 index 0000000..67f3632 --- /dev/null +++ b/front_minimal/src/sections/checkout/checkout-summary.jsx @@ -0,0 +1,113 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import TextField from '@mui/material/TextField'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { fCurrency } from 'src/utils/format-number'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function CheckoutSummary({ total, onEdit, discount, subtotal, shipping, onApplyDiscount }) { + const displayShipping = shipping !== null ? 'Free' : '-'; + + return ( + + }> + Edit + + ) + } + /> + + + + + Sub total + + + {fCurrency(subtotal)} + + + + + + Discount + + + {discount ? fCurrency(-discount) : '-'} + + + + + + Shipping + + + {shipping ? fCurrency(shipping) : displayShipping} + + + + + + + + Total + + + + + {fCurrency(total)} + + + (VAT included if applicable) + + + + + {onApplyDiscount && ( + + + + ), + }} + /> + )} + + + ); +} diff --git a/front_minimal/src/sections/checkout/context/checkout-provider.jsx b/front_minimal/src/sections/checkout/context/checkout-provider.jsx new file mode 100644 index 0000000..768f4ff --- /dev/null +++ b/front_minimal/src/sections/checkout/context/checkout-provider.jsx @@ -0,0 +1,249 @@ +'use client'; + +import { useMemo, Suspense, useEffect, useCallback, createContext } from 'react'; + +import { paths } from 'src/routes/paths'; +import { useRouter, useSearchParams } from 'src/routes/hooks'; + +import { getStorage, useLocalStorage } from 'src/hooks/use-local-storage'; + +import { PRODUCT_CHECKOUT_STEPS } from 'src/_mock/_product'; + +import { SplashScreen } from 'src/components/loading-screen'; + +// ---------------------------------------------------------------------- + +export const CheckoutContext = createContext(undefined); + +export const CheckoutConsumer = CheckoutContext.Consumer; + +const STORAGE_KEY = 'app-checkout'; + +const initialState = { + items: [], + subtotal: 0, + total: 0, + discount: 0, + shipping: 0, + billing: null, + totalItems: 0, +}; + +// ---------------------------------------------------------------------- + +export function CheckoutProvider({ children }) { + return ( + }> + {children} + + ); +} + +// ---------------------------------------------------------------------- + +function Container({ children }) { + const router = useRouter(); + + const searchParams = useSearchParams(); + + const activeStep = Number(searchParams.get('step')); + + const { state, setState, setField, canReset, resetState } = useLocalStorage( + STORAGE_KEY, + initialState + ); + + const completed = activeStep === PRODUCT_CHECKOUT_STEPS.length; + + const updateTotalField = useCallback(() => { + const totalItems = state.items.reduce((total, item) => total + item.quantity, 0); + + const subtotal = state.items.reduce((total, item) => total + item.quantity * item.price, 0); + + setField('subtotal', subtotal); + setField('totalItems', totalItems); + setField('total', state.subtotal - state.discount + state.shipping); + }, [setField, state.discount, state.items, state.shipping, state.subtotal]); + + useEffect(() => { + const restoredValue = getStorage(STORAGE_KEY); + if (restoredValue) { + updateTotalField(); + } + }, [updateTotalField]); + + const initialStep = useCallback(() => { + if (!activeStep) { + const href = createUrl('go', 0); + router.push(href); + } + }, [activeStep, router]); + + const onBackStep = useCallback(() => { + const href = createUrl('back', activeStep); + router.push(href); + }, [activeStep, router]); + + const onNextStep = useCallback(() => { + const href = createUrl('next', activeStep); + router.push(href); + }, [activeStep, router]); + + const onGotoStep = useCallback( + (step) => { + const href = createUrl('go', step); + router.push(href); + }, + [router] + ); + + const onAddToCart = useCallback( + (newItem) => { + const updatedItems = state.items.map((item) => { + if (item.id === newItem.id) { + const colorsAdded = [...item.colors, ...newItem.colors]; + + const colors = colorsAdded.filter((color, index) => colorsAdded.indexOf(color) === index); + + return { ...item, colors, quantity: item.quantity + 1 }; + } + return item; + }); + + if (!updatedItems.some((item) => item.id === newItem.id)) { + updatedItems.push(newItem); + } + + setField('items', updatedItems); + }, + [setField, state.items] + ); + + const onDeleteCart = useCallback( + (itemId) => { + const updatedItems = state.items.filter((item) => item.id !== itemId); + + setField('items', updatedItems); + }, + [setField, state.items] + ); + + const onIncreaseQuantity = useCallback( + (itemId) => { + const updatedItems = state.items.map((item) => { + if (item.id === itemId) { + return { ...item, quantity: item.quantity + 1 }; + } + return item; + }); + + setField('items', updatedItems); + }, + [setField, state.items] + ); + + const onDecreaseQuantity = useCallback( + (itemId) => { + const updatedItems = state.items.map((item) => { + if (item.id === itemId) { + return { ...item, quantity: item.quantity - 1 }; + } + return item; + }); + + setField('items', updatedItems); + }, + [setField, state.items] + ); + + const onCreateBilling = useCallback( + (address) => { + setField('billing', address); + + onNextStep(); + }, + [onNextStep, setField] + ); + + const onApplyDiscount = useCallback( + (discount) => { + setField('discount', discount); + }, + [setField] + ); + + const onApplyShipping = useCallback( + (shipping) => { + setField('shipping', shipping); + }, + [setField] + ); + + // Reset + const onReset = useCallback(() => { + if (completed) { + resetState(); + router.push(paths.product.root); + } + }, [completed, resetState, router]); + + const memoizedValue = useMemo( + () => ({ + ...state, + canReset, + onReset, + onUpdate: setState, + onUpdateField: setField, + // + completed, + // + onAddToCart, + onDeleteCart, + // + onIncreaseQuantity, + onDecreaseQuantity, + // + onCreateBilling, + onApplyDiscount, + onApplyShipping, + // + activeStep, + initialStep, + onBackStep, + onNextStep, + onGotoStep, + }), + [ + state, + onReset, + canReset, + setField, + completed, + setState, + activeStep, + onBackStep, + onGotoStep, + onNextStep, + initialStep, + onAddToCart, + onDeleteCart, + onApplyDiscount, + onApplyShipping, + onCreateBilling, + onDecreaseQuantity, + onIncreaseQuantity, + ] + ); + + return {children}; +} + +// ---------------------------------------------------------------------- + +function createUrl(type, activeStep) { + const step = { back: activeStep - 1, next: activeStep + 1, go: activeStep }[type]; + + const stepParams = new URLSearchParams({ step: `${step}` }).toString(); + + return `${paths.product.checkout}?${stepParams}`; +} diff --git a/front_minimal/src/sections/checkout/context/index.js b/front_minimal/src/sections/checkout/context/index.js new file mode 100644 index 0000000..38b6762 --- /dev/null +++ b/front_minimal/src/sections/checkout/context/index.js @@ -0,0 +1,3 @@ +export { CheckoutProvider } from './checkout-provider'; + +export { useCheckoutContext } from './use-checkout-context'; diff --git a/front_minimal/src/sections/checkout/context/use-checkout-context.jsx b/front_minimal/src/sections/checkout/context/use-checkout-context.jsx new file mode 100644 index 0000000..004436b --- /dev/null +++ b/front_minimal/src/sections/checkout/context/use-checkout-context.jsx @@ -0,0 +1,15 @@ +'use client'; + +import { useContext } from 'react'; + +import { CheckoutContext } from './checkout-provider'; + +// ---------------------------------------------------------------------- + +export function useCheckoutContext() { + const context = useContext(CheckoutContext); + + if (!context) throw new Error('useCheckoutContext must be use inside CheckoutProvider'); + + return context; +} diff --git a/front_minimal/src/sections/checkout/view/checkout-view.jsx b/front_minimal/src/sections/checkout/view/checkout-view.jsx new file mode 100644 index 0000000..3ad0874 --- /dev/null +++ b/front_minimal/src/sections/checkout/view/checkout-view.jsx @@ -0,0 +1,53 @@ +'use client'; + +import { useEffect } from 'react'; + +import Container from '@mui/material/Container'; +import Grid from '@mui/material/Unstable_Grid2'; +import Typography from '@mui/material/Typography'; + +import { PRODUCT_CHECKOUT_STEPS } from 'src/_mock/_product'; + +import { CheckoutCart } from '../checkout-cart'; +import { useCheckoutContext } from '../context'; +import { CheckoutSteps } from '../checkout-steps'; +import { CheckoutPayment } from '../checkout-payment'; +import { CheckoutOrderComplete } from '../checkout-order-complete'; +import { CheckoutBillingAddress } from '../checkout-billing-address'; + +// ---------------------------------------------------------------------- + +export function CheckoutView() { + const checkout = useCheckoutContext(); + + useEffect(() => { + checkout.initialStep(); + // eslint-disable-next-line react-hooks/exhaustive-deps + }, []); + + return ( + + + Checkout + + + + + + + + + <> + {checkout.activeStep === 0 && } + + {checkout.activeStep === 1 && } + + {checkout.activeStep === 2 && } + + {checkout.completed && ( + {}} /> + )} + + + ); +} diff --git a/front_minimal/src/sections/checkout/view/index.js b/front_minimal/src/sections/checkout/view/index.js new file mode 100644 index 0000000..2112241 --- /dev/null +++ b/front_minimal/src/sections/checkout/view/index.js @@ -0,0 +1 @@ +export * from './checkout-view'; diff --git a/front_minimal/src/sections/coming-soon/view.jsx b/front_minimal/src/sections/coming-soon/view.jsx new file mode 100644 index 0000000..d68fac1 --- /dev/null +++ b/front_minimal/src/sections/coming-soon/view.jsx @@ -0,0 +1,97 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; +import { outlinedInputClasses } from '@mui/material/OutlinedInput'; + +import { useCountdownDate } from 'src/hooks/use-countdown'; + +import { _socials } from 'src/_mock'; +import { varAlpha } from 'src/theme/styles'; +import { ComingSoonIllustration } from 'src/assets/illustrations'; + +import { SocialIcon } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function ComingSoonView() { + const countdown = useCountdownDate(new Date('08/08/2025 21:30')); + + return ( + + + Coming soon! + + + + We are currently working hard on this page! + + + + + :
    } + sx={{ typography: 'h2' }} + > + + + + + + + + + + ), + sx: { + pr: 0.5, + [`&.${outlinedInputClasses.focused}`]: { + boxShadow: (theme) => theme.customShadows.z20, + transition: (theme) => + theme.transitions.create(['box-shadow'], { + duration: theme.transitions.duration.shorter, + }), + [`& .${outlinedInputClasses.notchedOutline}`]: { + border: (theme) => + `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.32)}`, + }, + }, + }, + }} + sx={{ my: 5 }} + /> + + + {_socials.map((social) => ( + + + + ))} + + + ); +} + +function TimeBlock({ label, value }) { + return ( +
    +
    {value}
    + {label} +
    + ); +} diff --git a/front_minimal/src/sections/contact/contact-form.jsx b/front_minimal/src/sections/contact/contact-form.jsx new file mode 100644 index 0000000..bf043ee --- /dev/null +++ b/front_minimal/src/sections/contact/contact-form.jsx @@ -0,0 +1,28 @@ +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; + +// ---------------------------------------------------------------------- + +export function ContactForm() { + return ( +
    + + Feel free to contact us.
    + We'll be glad to hear from you buddy. +
    + + + + + + + + + +
    + ); +} diff --git a/front_minimal/src/sections/contact/contact-hero.jsx b/front_minimal/src/sections/contact/contact-hero.jsx new file mode 100644 index 0000000..82b784e --- /dev/null +++ b/front_minimal/src/sections/contact/contact-hero.jsx @@ -0,0 +1,96 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Container from '@mui/material/Container'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, bgGradient } from 'src/theme/styles'; + +import { varFade, AnimateText, MotionContainer, animateTextClasses } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +const CONTACTS = [ + { country: 'Bali', address: '508 Bridle Avenue Newnan, GA 30263', phoneNumber: '(239) 555-0108' }, + { + country: 'London', + address: '508 Bridle Avenue Newnan, GA 30263', + phoneNumber: '(319) 555-0115', + }, + { + country: 'Prague', + address: '508 Bridle Avenue Newnan, GA 30263', + phoneNumber: '(252) 555-0126', + }, + { country: 'Moscow', address: '508 Bridle', phoneNumber: '(307) 555-0133' }, +]; + +// ---------------------------------------------------------------------- + +export function ContactHero() { + const theme = useTheme(); + + return ( + + + + + + + {CONTACTS.map((contact) => ( + + + + {contact.country} + + + + + + {contact.address} + + + + ))} + + + + + ); +} diff --git a/front_minimal/src/sections/contact/contact-map.jsx b/front_minimal/src/sections/contact/contact-map.jsx new file mode 100644 index 0000000..6691630 --- /dev/null +++ b/front_minimal/src/sections/contact/contact-map.jsx @@ -0,0 +1,87 @@ +import { useState } from 'react'; +import dynamic from 'next/dynamic'; + +import Box from '@mui/material/Box'; +import Skeleton from '@mui/material/Skeleton'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { Iconify } from 'src/components/iconify'; +import { MapPopup, MapMarker, MapControl } from 'src/components/map'; + +// ---------------------------------------------------------------------- + +const Map = dynamic(() => import('src/components/map').then((mod) => mod.Map), { + loading: () => ( + + ), +}); + +// ---------------------------------------------------------------------- + +export function ContactMap({ contacts }) { + const theme = useTheme(); + + const [popupInfo, setPopupInfo] = useState(null); + + const lightMode = theme.palette.mode === 'light'; + + return ( + + + + + {contacts.map((country, index) => ( + { + event.originalEvent.stopPropagation(); + setPopupInfo(country); + }} + /> + ))} + + {popupInfo && ( + setPopupInfo(null)} + > + + Address + + + + {popupInfo.address} + + + + + {popupInfo.phoneNumber} + + + )} + + + ); +} diff --git a/front_minimal/src/sections/contact/view/contact-view.jsx b/front_minimal/src/sections/contact/view/contact-view.jsx new file mode 100644 index 0000000..0aa06c3 --- /dev/null +++ b/front_minimal/src/sections/contact/view/contact-view.jsx @@ -0,0 +1,32 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Container from '@mui/material/Container'; + +import { _mapContact } from 'src/_mock'; + +import { ContactMap } from '../contact-map'; +import { ContactHero } from '../contact-hero'; +import { ContactForm } from '../contact-form'; + +// ---------------------------------------------------------------------- + +export function ContactView() { + return ( + <> + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/contact/view/index.js b/front_minimal/src/sections/contact/view/index.js new file mode 100644 index 0000000..2518945 --- /dev/null +++ b/front_minimal/src/sections/contact/view/index.js @@ -0,0 +1 @@ +export * from './contact-view'; diff --git a/front_minimal/src/sections/error/403-view.jsx b/front_minimal/src/sections/error/403-view.jsx new file mode 100644 index 0000000..3ef7917 --- /dev/null +++ b/front_minimal/src/sections/error/403-view.jsx @@ -0,0 +1,45 @@ +'use client'; + +import { m } from 'framer-motion'; + +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { RouterLink } from 'src/routes/components'; + +import { SimpleLayout } from 'src/layouts/simple'; +import { ForbiddenIllustration } from 'src/assets/illustrations'; + +import { varBounce, MotionContainer } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export function View403() { + return ( + + + + + No permission + + + + + + The page you’re trying to access has restricted access. Please refer to your system + administrator. + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/error/500-view.jsx b/front_minimal/src/sections/error/500-view.jsx new file mode 100644 index 0000000..e16dbd6 --- /dev/null +++ b/front_minimal/src/sections/error/500-view.jsx @@ -0,0 +1,44 @@ +'use client'; + +import { m } from 'framer-motion'; + +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { RouterLink } from 'src/routes/components'; + +import { SimpleLayout } from 'src/layouts/simple'; +import { ServerErrorIllustration } from 'src/assets/illustrations'; + +import { varBounce, MotionContainer } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export function View500() { + return ( + + + + + 500 Internal server error + + + + + + There was an error, please try again later. + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/error/index.js b/front_minimal/src/sections/error/index.js new file mode 100644 index 0000000..48fdc00 --- /dev/null +++ b/front_minimal/src/sections/error/index.js @@ -0,0 +1,5 @@ +export * from './403-view'; + +export * from './500-view'; + +export * from './not-found-view'; diff --git a/front_minimal/src/sections/error/not-found-view.jsx b/front_minimal/src/sections/error/not-found-view.jsx new file mode 100644 index 0000000..80e31e4 --- /dev/null +++ b/front_minimal/src/sections/error/not-found-view.jsx @@ -0,0 +1,45 @@ +'use client'; + +import { m } from 'framer-motion'; + +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { RouterLink } from 'src/routes/components'; + +import { SimpleLayout } from 'src/layouts/simple'; +import { PageNotFoundIllustration } from 'src/assets/illustrations'; + +import { varBounce, MotionContainer } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export function NotFoundView() { + return ( + + + + + Sorry, page not found! + + + + + + Sorry, we couldn’t find the page you’re looking for. Perhaps you’ve mistyped the URL? Be + sure to check your spelling. + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/faqs/faqs-category.jsx b/front_minimal/src/sections/faqs/faqs-category.jsx new file mode 100644 index 0000000..d9ea685 --- /dev/null +++ b/front_minimal/src/sections/faqs/faqs-category.jsx @@ -0,0 +1,160 @@ +import Box from '@mui/material/Box'; +import Paper from '@mui/material/Paper'; +import Avatar from '@mui/material/Avatar'; +import Drawer from '@mui/material/Drawer'; +import Button from '@mui/material/Button'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { CONFIG } from 'src/config-global'; +import { maxLine } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +const CATEGORIES = [ + { + label: 'Managing your account', + icon: `${CONFIG.site.basePath}/assets/icons/faqs/ic-account.svg`, + href: '#', + }, + { label: 'Payment', icon: `${CONFIG.site.basePath}/assets/icons/faqs/ic-payment.svg`, href: '#' }, + { + label: 'Delivery', + icon: `${CONFIG.site.basePath}/assets/icons/faqs/ic-delivery.svg`, + href: '#', + }, + { + label: 'Problem with the product', + icon: `${CONFIG.site.basePath}/assets/icons/faqs/ic-package.svg`, + href: '#', + }, + { + label: 'Return & refund', + icon: `${CONFIG.site.basePath}/assets/icons/faqs/ic-refund.svg`, + href: '#', + }, + { + label: 'Guarantees and assurances', + icon: `${CONFIG.site.basePath}/assets/icons/faqs/ic-assurances.svg`, + href: '#', + }, +]; + +// ---------------------------------------------------------------------- + +export function FaqsCategory() { + const nav = useBoolean(); + + const renderMobile = ( + <> + `solid 1px ${theme.vars.palette.divider}`, + }} + > + + + + + + {CATEGORIES.map((category) => ( + + ))} + + + + ); + + const renderDesktop = ( + + {CATEGORIES.map((category) => ( + + ))} + + ); + + return ( + <> + {renderMobile} + {renderDesktop} + + ); +} + +function CardDesktop({ category }) { + const theme = useTheme(); + + return ( + + + + + {category.label} + + + ); +} + +// ---------------------------------------------------------------------- + +function CardMobile({ category }) { + return ( + + + + {category.label} + + ); +} diff --git a/front_minimal/src/sections/faqs/faqs-form.jsx b/front_minimal/src/sections/faqs/faqs-form.jsx new file mode 100644 index 0000000..f912b92 --- /dev/null +++ b/front_minimal/src/sections/faqs/faqs-form.jsx @@ -0,0 +1,25 @@ +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; + +// ---------------------------------------------------------------------- + +export function FaqsForm() { + return ( +
    + {`Haven't found the right help?`} + + + + + + + + + +
    + ); +} diff --git a/front_minimal/src/sections/faqs/faqs-hero.jsx b/front_minimal/src/sections/faqs/faqs-hero.jsx new file mode 100644 index 0000000..1f7e8d1 --- /dev/null +++ b/front_minimal/src/sections/faqs/faqs-hero.jsx @@ -0,0 +1,78 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Container from '@mui/material/Container'; +import TextField from '@mui/material/TextField'; +import { useTheme } from '@mui/material/styles'; +import InputAdornment from '@mui/material/InputAdornment'; +import { outlinedInputClasses } from '@mui/material/OutlinedInput'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, bgGradient } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { varFade, AnimateText, MotionContainer, animateTextClasses } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export function FaqsHero() { + const theme = useTheme(); + + return ( + + + + + + + + + + ), + }} + sx={{ + mt: 5, + maxWidth: 360, + [`& .${outlinedInputClasses.root}`]: { bgcolor: 'common.white' }, + [`& .${outlinedInputClasses.input}`]: { typography: 'subtitle1' }, + }} + /> + + + + + ); +} diff --git a/front_minimal/src/sections/faqs/faqs-list.jsx b/front_minimal/src/sections/faqs/faqs-list.jsx new file mode 100644 index 0000000..20c319c --- /dev/null +++ b/front_minimal/src/sections/faqs/faqs-list.jsx @@ -0,0 +1,28 @@ +import Accordion from '@mui/material/Accordion'; +import Typography from '@mui/material/Typography'; +import AccordionSummary from '@mui/material/AccordionSummary'; +import AccordionDetails from '@mui/material/AccordionDetails'; + +import { _faqs } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function FaqsList() { + return ( +
    + {_faqs.map((accordion) => ( + + }> + {accordion.heading} + + + + {accordion.detail} + + + ))} +
    + ); +} diff --git a/front_minimal/src/sections/faqs/view/faqs-view.jsx b/front_minimal/src/sections/faqs/view/faqs-view.jsx new file mode 100644 index 0000000..91c8cf0 --- /dev/null +++ b/front_minimal/src/sections/faqs/view/faqs-view.jsx @@ -0,0 +1,38 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { FaqsHero } from '../faqs-hero'; +import { FaqsList } from '../faqs-list'; +import { FaqsForm } from '../faqs-form'; +import { FaqsCategory } from '../faqs-category'; + +// ---------------------------------------------------------------------- + +export function FaqsView() { + return ( + <> + + + + + + + Frequently asked questions + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/faqs/view/index.js b/front_minimal/src/sections/faqs/view/index.js new file mode 100644 index 0000000..51b36f3 --- /dev/null +++ b/front_minimal/src/sections/faqs/view/index.js @@ -0,0 +1 @@ +export * from './faqs-view'; diff --git a/front_minimal/src/sections/file-manager/file-data-activity.jsx b/front_minimal/src/sections/file-manager/file-data-activity.jsx new file mode 100644 index 0000000..aa49d86 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-data-activity.jsx @@ -0,0 +1,75 @@ +import { useState, useCallback } from 'react'; + +import Card from '@mui/material/Card'; +import CardHeader from '@mui/material/CardHeader'; +import { useTheme, alpha as hexAlpha } from '@mui/material/styles'; + +import { fData } from 'src/utils/format-number'; + +import { Chart, useChart, ChartSelect } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function FileDataActivity({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const [selectedSeries, setSelectedSeries] = useState('Yearly'); + + const currentSeries = chart.series.find((i) => i.name === selectedSeries); + + const chartColors = chart.colors ?? [ + theme.palette.primary.main, + theme.palette.error.main, + theme.palette.warning.main, + hexAlpha(theme.palette.grey[500], 0.48), + ]; + + const chartOptions = useChart({ + chart: { + stacked: true, + }, + colors: chartColors, + stroke: { + width: 0, + }, + legend: { + show: true, + }, + xaxis: { + categories: currentSeries?.categories, + }, + tooltip: { + y: { formatter: (value) => fData(value) }, + }, + ...chart.options, + }); + + const handleChangeSeries = useCallback((newValue) => { + setSelectedSeries(newValue); + }, []); + + return ( + + i.name)} + value={selectedSeries} + onChange={handleChangeSeries} + /> + } + /> + + + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-action-selected.jsx b/front_minimal/src/sections/file-manager/file-manager-action-selected.jsx new file mode 100644 index 0000000..1a25930 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-action-selected.jsx @@ -0,0 +1,62 @@ +import Box from '@mui/material/Box'; +import Portal from '@mui/material/Portal'; +import Checkbox from '@mui/material/Checkbox'; +import Typography from '@mui/material/Typography'; + +import { stylesMode } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function FileManagerActionSelected({ + action, + selected, + rowCount, + numSelected, + onSelectAllItems, + sx, + ...other +}) { + return ( + + theme.spacing(1.5, 2, 1.5, 1), + boxShadow: (theme) => theme.customShadows.z20, + m: { xs: 2, md: 3 }, + ...sx, + }} + {...other} + > + onSelectAllItems(event.target.checked)} + icon={} + checkedIcon={} + indeterminateIcon={} + /> + + {selected && ( + + {selected.length} Items selected + + )} + + {action && action} + + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-file-details.jsx b/front_minimal/src/sections/file-manager/file-manager-file-details.jsx new file mode 100644 index 0000000..625c21a --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-file-details.jsx @@ -0,0 +1,268 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Chip from '@mui/material/Chip'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Drawer from '@mui/material/Drawer'; +import Divider from '@mui/material/Divider'; +import Checkbox from '@mui/material/Checkbox'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import Autocomplete from '@mui/material/Autocomplete'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { fData } from 'src/utils/format-number'; +import { fDateTime } from 'src/utils/format-time'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { fileFormat, FileThumbnail } from 'src/components/file-thumbnail'; + +import { FileManagerShareDialog } from './file-manager-share-dialog'; +import { FileManagerInvitedItem } from './file-manager-invited-item'; + +// ---------------------------------------------------------------------- + +export function FileManagerFileDetails({ + item, + open, + onClose, + onDelete, + favorited, + onFavorite, + onCopyLink, + ...other +}) { + const { name, size, url, type, shared, modifiedAt } = item; + + const hasShared = shared && !!shared.length; + + const toggleTags = useBoolean(true); + + const share = useBoolean(); + + const properties = useBoolean(true); + + const [inviteEmail, setInviteEmail] = useState(''); + + const [tags, setTags] = useState(item.tags.slice(0, 3)); + + const handleChangeInvite = useCallback((event) => { + setInviteEmail(event.target.value); + }, []); + + const handleChangeTags = useCallback((newValue) => { + setTags(newValue); + }, []); + + const renderTags = ( + + + Tags + + + + + + {toggleTags.value && ( + option)} + getOptionLabel={(option) => option} + defaultValue={item.tags.slice(0, 3)} + value={tags} + onChange={(event, newValue) => { + handleChangeTags(newValue); + }} + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + renderInput={(params) => } + /> + )} +
    + ); + + const renderProperties = ( + + + Properties + + + + + + {properties.value && ( + <> + + + Size + + {fData(size)} + + + + + Modified + + {fDateTime(modifiedAt)} + + + + + Type + + {fileFormat(type)} + + + )} + + ); + + const renderShared = ( + <> + + Share with + + + + + + + {hasShared && ( + + {shared.map((person) => ( + + ))} + + )} + + ); + + return ( + <> + + + + Info + + } + checkedIcon={} + checked={favorited} + onChange={onFavorite} + /> + + + + + + + {name} + + + + + {renderTags} + + {renderProperties} + + + {renderShared} + + + + + + + + { + share.onFalse(); + setInviteEmail(''); + }} + /> + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-file-item.jsx b/front_minimal/src/sections/file-manager/file-manager-file-item.jsx new file mode 100644 index 0000000..281c75b --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-file-item.jsx @@ -0,0 +1,275 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Paper from '@mui/material/Paper'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import Checkbox from '@mui/material/Checkbox'; +import { useTheme } from '@mui/material/styles'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import AvatarGroup, { avatarGroupClasses } from '@mui/material/AvatarGroup'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useCopyToClipboard } from 'src/hooks/use-copy-to-clipboard'; + +import { fData } from 'src/utils/format-number'; +import { fDateTime } from 'src/utils/format-time'; + +import { maxLine } from 'src/theme/styles'; + +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { FileThumbnail } from 'src/components/file-thumbnail'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +import { FileManagerShareDialog } from './file-manager-share-dialog'; +import { FileManagerFileDetails } from './file-manager-file-details'; + +// ---------------------------------------------------------------------- + +export function FileManagerFileItem({ file, selected, onSelect, onDelete, sx, ...other }) { + const theme = useTheme(); + + const share = useBoolean(); + + const confirm = useBoolean(); + + const details = useBoolean(); + + const popover = usePopover(); + + const checkbox = useBoolean(); + + const { copy } = useCopyToClipboard(); + + const favorite = useBoolean(file.isFavorited); + + const [inviteEmail, setInviteEmail] = useState(''); + + const handleChangeInvite = useCallback((event) => { + setInviteEmail(event.target.value); + }, []); + + const handleCopy = useCallback(() => { + toast.success('Copied!'); + copy(file.url); + }, [copy, file.url]); + + const renderIcon = ( + + {(checkbox.value || selected) && onSelect ? ( + } + checkedIcon={} + inputProps={{ id: `item-checkbox-${file.id}`, 'aria-label': `Item checkbox` }} + sx={{ width: 1, height: 1 }} + /> + ) : ( + + )} + + ); + + const renderAction = ( + + } + checkedIcon={} + checked={favorite.value} + onChange={favorite.onToggle} + inputProps={{ id: `favorite-checkbox-${file.id}`, 'aria-label': `Favorite checkbox` }} + /> + + + + + + ); + + const renderText = ( + <> + + {file.name} + + + + {fData(file.size)} + + + + {fDateTime(file.modifiedAt)} + + + + ); + + const renderAvatar = ( + + {file.shared?.map((person) => ( + + ))} + + ); + + return ( + <> + + {renderIcon} + + {renderText} + + {renderAvatar} + + {renderAction} + + + + + { + popover.onClose(); + handleCopy(); + }} + > + + Copy Link + + + { + popover.onClose(); + share.onTrue(); + }} + > + + Share + + + + + { + confirm.onTrue(); + popover.onClose(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + { + details.onFalse(); + onDelete(); + }} + /> + + { + share.onFalse(); + setInviteEmail(''); + }} + /> + + + Delete + + } + /> + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-filters-result.jsx b/front_minimal/src/sections/file-manager/file-manager-filters-result.jsx new file mode 100644 index 0000000..64902ad --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-filters-result.jsx @@ -0,0 +1,67 @@ +import { useCallback } from 'react'; + +import Chip from '@mui/material/Chip'; + +import { fDateRangeShortLabel } from 'src/utils/format-time'; + +import { chipProps, FiltersBlock, FiltersResult } from 'src/components/filters-result'; + +// ---------------------------------------------------------------------- + +export function FileManagerFiltersResult({ filters, onResetPage, totalResults, sx }) { + const handleRemoveKeyword = useCallback(() => { + onResetPage(); + filters.setState({ name: '' }); + }, [filters, onResetPage]); + + const handleRemoveTypes = useCallback( + (inputValue) => { + const newValue = filters.state.type.filter((item) => item !== inputValue); + + onResetPage(); + filters.setState({ type: newValue }); + }, + [filters, onResetPage] + ); + + const handleRemoveDate = useCallback(() => { + onResetPage(); + filters.setState({ startDate: null, endDate: null }); + }, [filters, onResetPage]); + + const handleReset = useCallback(() => { + onResetPage(); + filters.onResetState(); + }, [filters, onResetPage]); + + return ( + + + {filters.state.type.map((item) => ( + handleRemoveTypes(item)} + sx={{ textTransform: 'capitalize' }} + /> + ))} + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-filters.jsx b/front_minimal/src/sections/file-manager/file-manager-filters.jsx new file mode 100644 index 0000000..46eabcf --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-filters.jsx @@ -0,0 +1,219 @@ +import { useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import TextField from '@mui/material/TextField'; +import CardActionArea from '@mui/material/CardActionArea'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { fDateRangeShortLabel } from 'src/utils/format-time'; + +import { varAlpha } from 'src/theme/styles'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { FileThumbnail } from 'src/components/file-thumbnail'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; +import { CustomDateRangePicker } from 'src/components/custom-date-range-picker'; + +// ---------------------------------------------------------------------- + +export function FileManagerFilters({ + filters, + options, + dateError, + onResetPage, + openDateRange, + onOpenDateRange, + onCloseDateRange, +}) { + const popover = usePopover(); + + const renderLabel = filters.state.type.length + ? filters.state.type.slice(0, 2).join(',') + : 'All type'; + + const handleFilterName = useCallback( + (event) => { + onResetPage(); + filters.setState({ name: event.target.value }); + }, + [filters, onResetPage] + ); + + const handleFilterStartDate = useCallback( + (newValue) => { + onResetPage(); + filters.setState({ startDate: newValue }); + }, + [filters, onResetPage] + ); + + const handleFilterEndDate = useCallback( + (newValue) => { + filters.setState({ endDate: newValue }); + }, + [filters] + ); + + const handleFilterType = useCallback( + (newValue) => { + const checked = filters.state.type.includes(newValue) + ? filters.state.type.filter((value) => value !== newValue) + : [...filters.state.type, newValue]; + + filters.setState({ type: checked }); + }, + [filters] + ); + + const handleResetType = useCallback(() => { + popover.onClose(); + filters.setState({ type: [] }); + }, [filters, popover]); + + const renderFilterName = ( + + + + ), + }} + sx={{ width: { xs: 1, md: 260 } }} + /> + ); + + const renderFilterType = ( + <> + + + + + + {options.types.map((type) => { + const selected = filters.state.type.includes(type); + + return ( + handleFilterType(type)} + sx={{ + p: 1, + borderRadius: 1, + cursor: 'pointer', + border: (theme) => + `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.08)}`, + ...(selected && { bgcolor: 'action.selected' }), + }} + > + + + {type} + + + ); + })} + + + + + + + + + + + ); + + const renderFilterDate = ( + <> + + + + + ); + + return ( + + {renderFilterName} + + + {renderFilterDate} + + {renderFilterType} + + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-folder-item.jsx b/front_minimal/src/sections/file-manager/file-manager-folder-item.jsx new file mode 100644 index 0000000..9622477 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-folder-item.jsx @@ -0,0 +1,295 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Paper from '@mui/material/Paper'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import Checkbox from '@mui/material/Checkbox'; +import IconButton from '@mui/material/IconButton'; +import ListItemText from '@mui/material/ListItemText'; +import AvatarGroup, { avatarGroupClasses } from '@mui/material/AvatarGroup'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useCopyToClipboard } from 'src/hooks/use-copy-to-clipboard'; + +import { fData } from 'src/utils/format-number'; + +import { CONFIG } from 'src/config-global'; + +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +import { FileManagerShareDialog } from './file-manager-share-dialog'; +import { FileManagerFileDetails } from './file-manager-file-details'; +import { FileManagerNewFolderDialog } from './file-manager-new-folder-dialog'; + +// ---------------------------------------------------------------------- + +export function FileManagerFolderItem({ sx, folder, selected, onSelect, onDelete, ...other }) { + const { copy } = useCopyToClipboard(); + + const share = useBoolean(); + + const popover = usePopover(); + + const confirm = useBoolean(); + + const details = useBoolean(); + + const checkbox = useBoolean(); + + const editFolder = useBoolean(); + + const favorite = useBoolean(folder.isFavorited); + + const [inviteEmail, setInviteEmail] = useState(''); + + const [folderName, setFolderName] = useState(folder.name); + + const handleChangeInvite = useCallback((event) => { + setInviteEmail(event.target.value); + }, []); + + const handleChangeFolderName = useCallback((event) => { + setFolderName(event.target.value); + }, []); + + const handleCopy = useCallback(() => { + toast.success('Copied!'); + copy(folder.url); + }, [copy, folder.url]); + + const renderAction = ( + + } + checkedIcon={} + checked={favorite.value} + onChange={favorite.onToggle} + inputProps={{ + name: 'checkbox-favorite', + 'aria-label': 'Checkbox favorite', + }} + /> + + + + + + ); + + const renderIcon = ( + + {(checkbox.value || selected) && onSelect ? ( + } + checkedIcon={} + sx={{ width: 1, height: 1 }} + /> + ) : ( + + )} + + ); + const renderText = ( + + {fData(folder.size)} + + {folder.totalFiles} files + + } + primaryTypographyProps={{ noWrap: true, typography: 'subtitle1' }} + secondaryTypographyProps={{ + mt: 0.5, + component: 'span', + alignItems: 'center', + typography: 'caption', + color: 'text.disabled', + display: 'inline-flex', + }} + /> + ); + + const renderAvatar = ( + + {folder.shared?.map((person) => ( + + ))} + + ); + + return ( + <> + theme.customShadows.z20, + }), + ...sx, + }} + {...other} + > + {renderIcon} + + {renderAction} + + {renderText} + + {!!folder?.shared?.length && renderAvatar} + + + + + { + popover.onClose(); + handleCopy(); + }} + > + + Copy Link + + + { + popover.onClose(); + share.onTrue(); + }} + > + + Share + + + { + popover.onClose(); + editFolder.onTrue(); + }} + > + + Edit + + + + + { + confirm.onTrue(); + popover.onClose(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + { + details.onFalse(); + onDelete(); + }} + /> + + { + share.onFalse(); + setInviteEmail(''); + }} + /> + + { + editFolder.onFalse(); + setFolderName(folderName); + console.info('UPDATE FOLDER', folderName); + }} + folderName={folderName} + onChangeFolderName={handleChangeFolderName} + /> + + + Delete + + } + /> + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-grid-view.jsx b/front_minimal/src/sections/file-manager/file-manager-grid-view.jsx new file mode 100644 index 0000000..7863a73 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-grid-view.jsx @@ -0,0 +1,186 @@ +import { useRef, useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import Collapse from '@mui/material/Collapse'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; + +import { FileManagerPanel } from './file-manager-panel'; +import { FileManagerFileItem } from './file-manager-file-item'; +import { FileManagerFolderItem } from './file-manager-folder-item'; +import { FileManagerShareDialog } from './file-manager-share-dialog'; +import { FileManagerActionSelected } from './file-manager-action-selected'; +import { FileManagerNewFolderDialog } from './file-manager-new-folder-dialog'; + +// ---------------------------------------------------------------------- + +export function FileManagerGridView({ table, dataFiltered, onDeleteItem, onOpenConfirm }) { + const { selected, onSelectRow: onSelectItem, onSelectAllRows: onSelectAllItems } = table; + + const share = useBoolean(); + + const files = useBoolean(); + + const upload = useBoolean(); + + const folders = useBoolean(); + + const newFolder = useBoolean(); + + const containerRef = useRef(null); + + const [folderName, setFolderName] = useState(''); + + const [inviteEmail, setInviteEmail] = useState(''); + + const handleChangeInvite = useCallback((event) => { + setInviteEmail(event.target.value); + }, []); + + const handleChangeFolderName = useCallback((event) => { + setFolderName(event.target.value); + }, []); + + return ( + <> + + item.type === 'folder').length} folders`} + onOpen={newFolder.onTrue} + collapse={folders.value} + onCollapse={folders.onToggle} + /> + + + + {dataFiltered + .filter((i) => i.type === 'folder') + .map((folder) => ( + onSelectItem(folder.id)} + onDelete={() => onDeleteItem(folder.id)} + sx={{ maxWidth: 'auto' }} + /> + ))} + + + + + + item.type !== 'folder').length} files`} + onOpen={upload.onTrue} + collapse={files.value} + onCollapse={files.onToggle} + /> + + + + {dataFiltered + .filter((i) => i.type !== 'folder') + .map((file) => ( + onSelectItem(file.id)} + onDelete={() => onDeleteItem(file.id)} + sx={{ maxWidth: 'auto' }} + /> + ))} + + + + {!!selected?.length && ( + + onSelectAllItems( + checked, + dataFiltered.map((row) => row.id) + ) + } + action={ + <> + + + + + } + /> + )} + + + { + share.onFalse(); + setInviteEmail(''); + }} + /> + + + + { + newFolder.onFalse(); + setFolderName(''); + console.info('CREATE NEW FOLDER', folderName); + }} + folderName={folderName} + onChangeFolderName={handleChangeFolderName} + /> + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-invited-item.jsx b/front_minimal/src/sections/file-manager/file-manager-invited-item.jsx new file mode 100644 index 0000000..61dd4a9 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-invited-item.jsx @@ -0,0 +1,103 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import Tooltip from '@mui/material/Tooltip'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import ListItemText from '@mui/material/ListItemText'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function FileManagerInvitedItem({ person }) { + const [permission, setPermission] = useState(person.permission); + + const popover = usePopover(); + + const handleChangePermission = useCallback((newPermission) => { + setPermission(newPermission); + }, []); + + return ( + <> + + + + + {person.email} + + } + primaryTypographyProps={{ noWrap: true, typography: 'subtitle2' }} + secondaryTypographyProps={{ noWrap: true, component: 'span' }} + sx={{ flexGrow: 1, pr: 1 }} + /> + + + + + + + { + popover.onClose(); + handleChangePermission('view'); + }} + > + + Can view + + + { + popover.onClose(); + handleChangePermission('edit'); + }} + > + + Can edit + + + + + { + popover.onClose(); + }} + sx={{ color: 'error.main' }} + > + + Remove + + + + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-new-folder-dialog.jsx b/front_minimal/src/sections/file-manager/file-manager-new-folder-dialog.jsx new file mode 100644 index 0000000..d187f86 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-new-folder-dialog.jsx @@ -0,0 +1,98 @@ +import { useState, useEffect, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import TextField from '@mui/material/TextField'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; + +import { Upload } from 'src/components/upload'; +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function FileManagerNewFolderDialog({ + open, + onClose, + onCreate, + onUpdate, + folderName, + onChangeFolderName, + title = 'Upload files', + ...other +}) { + const [files, setFiles] = useState([]); + + useEffect(() => { + if (!open) { + setFiles([]); + } + }, [open]); + + const handleDrop = useCallback( + (acceptedFiles) => { + setFiles([...files, ...acceptedFiles]); + }, + [files] + ); + + const handleUpload = () => { + onClose(); + console.info('ON UPLOAD'); + }; + + const handleRemoveFile = (inputFile) => { + const filtered = files.filter((file) => file !== inputFile); + setFiles(filtered); + }; + + const handleRemoveAllFiles = () => { + setFiles([]); + }; + + return ( + + theme.spacing(3, 3, 2, 3) }}> {title} + + + {(onCreate || onUpdate) && ( + + )} + + + + + + + + {!!files.length && ( + + )} + + {(onCreate || onUpdate) && ( + + + + )} + + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-panel.jsx b/front_minimal/src/sections/file-manager/file-manager-panel.jsx new file mode 100644 index 0000000..16f4e37 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-panel.jsx @@ -0,0 +1,67 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { RouterLink } from 'src/routes/components'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function FileManagerPanel({ + sx, + link, + title, + onOpen, + subtitle, + collapse, + onCollapse, + ...other +}) { + return ( + + + + {title} + + + + + + + {subtitle} + + + {link && ( + + )} + + {onCollapse && ( + + + + )} + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-share-dialog.jsx b/front_minimal/src/sections/file-manager/file-manager-share-dialog.jsx new file mode 100644 index 0000000..6619445 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-share-dialog.jsx @@ -0,0 +1,82 @@ +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import TextField from '@mui/material/TextField'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; + +import { FileManagerInvitedItem } from './file-manager-invited-item'; + +// ---------------------------------------------------------------------- + +export function FileManagerShareDialog({ + open, + shared, + onClose, + onCopyLink, + inviteEmail, + onChangeInvite, + ...other +}) { + const hasShared = shared && !!shared.length; + + return ( + + Invite + + + {onChangeInvite && ( + + + + ), + }} + sx={{ mb: 2 }} + /> + )} + + + {hasShared && ( + + + {shared.map((person) => ( + + ))} + + + )} + + + {onCopyLink && ( + + )} + + {onClose && ( + + )} + + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-table-row.jsx b/front_minimal/src/sections/file-manager/file-manager-table-row.jsx new file mode 100644 index 0000000..657773c --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-table-row.jsx @@ -0,0 +1,260 @@ +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import Checkbox from '@mui/material/Checkbox'; +import { useTheme } from '@mui/material/styles'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; +import TableRow, { tableRowClasses } from '@mui/material/TableRow'; +import TableCell, { tableCellClasses } from '@mui/material/TableCell'; +import AvatarGroup, { avatarGroupClasses } from '@mui/material/AvatarGroup'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useDoubleClick } from 'src/hooks/use-double-click'; +import { useCopyToClipboard } from 'src/hooks/use-copy-to-clipboard'; + +import { fData } from 'src/utils/format-number'; +import { fDate, fTime } from 'src/utils/format-time'; + +import { varAlpha } from 'src/theme/styles'; + +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { FileThumbnail } from 'src/components/file-thumbnail'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +import { FileManagerShareDialog } from './file-manager-share-dialog'; +import { FileManagerFileDetails } from './file-manager-file-details'; + +// ---------------------------------------------------------------------- + +export function FileManagerTableRow({ row, selected, onSelectRow, onDeleteRow }) { + const theme = useTheme(); + + const { copy } = useCopyToClipboard(); + + const [inviteEmail, setInviteEmail] = useState(''); + + const favorite = useBoolean(row.isFavorited); + + const details = useBoolean(); + + const share = useBoolean(); + + const confirm = useBoolean(); + + const popover = usePopover(); + + const handleChangeInvite = useCallback((event) => { + setInviteEmail(event.target.value); + }, []); + + const handleClick = useDoubleClick({ + click: () => { + details.onTrue(); + }, + doubleClick: () => console.info('DOUBLE CLICK'), + }); + + const handleCopy = useCallback(() => { + toast.success('Copied!'); + copy(row.url); + }, [copy, row.url]); + + const defaultStyles = { + borderTop: `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.16)}`, + borderBottom: `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.16)}`, + '&:first-of-type': { + borderTopLeftRadius: 16, + borderBottomLeftRadius: 16, + borderLeft: `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.16)}`, + }, + '&:last-of-type': { + borderTopRightRadius: 16, + borderBottomRightRadius: 16, + borderRight: `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.16)}`, + }, + }; + + return ( + <> + + + console.info('ON DOUBLE CLICK')} + onClick={onSelectRow} + inputProps={{ id: `row-checkbox-${row.id}`, 'aria-label': `row-checkbox` }} + /> + + + + + + + + {row.name} + + + + + + {fData(row.size)} + + + + {row.type} + + + + + + + + + {row.shared && + row.shared.map((person) => ( + + ))} + + + + + } + checkedIcon={} + checked={favorite.value} + onChange={favorite.onToggle} + sx={{ p: 0.75 }} + /> + + + + + + + + + + { + popover.onClose(); + handleCopy(); + }} + > + + Copy Link + + + { + popover.onClose(); + share.onTrue(); + }} + > + + Share + + + + + { + confirm.onTrue(); + popover.onClose(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + + + { + share.onFalse(); + setInviteEmail(''); + }} + /> + + + Delete + + } + /> + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-manager-table.jsx b/front_minimal/src/sections/file-manager/file-manager-table.jsx new file mode 100644 index 0000000..9c6b378 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-manager-table.jsx @@ -0,0 +1,167 @@ +import Box from '@mui/material/Box'; +import Table from '@mui/material/Table'; +import Tooltip from '@mui/material/Tooltip'; +import { useTheme } from '@mui/material/styles'; +import TableBody from '@mui/material/TableBody'; +import IconButton from '@mui/material/IconButton'; +import TableContainer from '@mui/material/TableContainer'; +import { tableCellClasses } from '@mui/material/TableCell'; +import { tablePaginationClasses } from '@mui/material/TablePagination'; + +import { Iconify } from 'src/components/iconify'; +import { + TableNoData, + TableHeadCustom, + TableSelectedAction, + TablePaginationCustom, +} from 'src/components/table'; + +import { FileManagerTableRow } from './file-manager-table-row'; + +// ---------------------------------------------------------------------- + +const TABLE_HEAD = [ + { id: 'name', label: 'Name' }, + { id: 'size', label: 'Size', width: 120 }, + { id: 'type', label: 'Type', width: 120 }, + { id: 'modifiedAt', label: 'Modified', width: 140 }, + { + id: 'shared', + label: 'Shared', + align: 'right', + width: 140, + }, + { id: '', width: 88 }, +]; + +// ---------------------------------------------------------------------- + +export function FileManagerTable({ table, notFound, onDeleteRow, dataFiltered, onOpenConfirm }) { + const theme = useTheme(); + + const { + dense, + page, + order, + orderBy, + rowsPerPage, + // + selected, + onSelectRow, + onSelectAllRows, + // + onSort, + onChangeDense, + onChangePage, + onChangeRowsPerPage, + } = table; + + return ( + <> + + + onSelectAllRows( + checked, + dataFiltered.map((row) => row.id) + ) + } + action={ + <> + + + + + + + + + + + + + } + sx={{ + pl: 1, + pr: 2, + top: 16, + left: 24, + right: 24, + width: 'auto', + borderRadius: 1.5, + }} + /> + + + + + onSelectAllRows( + checked, + dataFiltered.map((row) => row.id) + ) + } + sx={{ + [`& .${tableCellClasses.head}`]: { + '&:first-of-type': { borderTopLeftRadius: 12, borderBottomLeftRadius: 12 }, + '&:last-of-type': { borderTopRightRadius: 12, borderBottomRightRadius: 12 }, + }, + }} + /> + + + {dataFiltered + .slice(page * rowsPerPage, page * rowsPerPage + rowsPerPage) + .map((row) => ( + onSelectRow(row.id)} + onDeleteRow={() => onDeleteRow(row.id)} + /> + ))} + + + +
    +
    +
    + + + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-recent-item.jsx b/front_minimal/src/sections/file-manager/file-recent-item.jsx new file mode 100644 index 0000000..5c7f2c5 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-recent-item.jsx @@ -0,0 +1,226 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Paper from '@mui/material/Paper'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import Checkbox from '@mui/material/Checkbox'; +import IconButton from '@mui/material/IconButton'; +import ListItemText from '@mui/material/ListItemText'; +import AvatarGroup, { avatarGroupClasses } from '@mui/material/AvatarGroup'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useCopyToClipboard } from 'src/hooks/use-copy-to-clipboard'; + +import { fData } from 'src/utils/format-number'; +import { fDateTime } from 'src/utils/format-time'; + +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { FileThumbnail } from 'src/components/file-thumbnail'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +import { FileManagerShareDialog } from './file-manager-share-dialog'; +import { FileManagerFileDetails } from './file-manager-file-details'; + +// ---------------------------------------------------------------------- + +export function FileRecentItem({ file, onDelete, sx, ...other }) { + const { copy } = useCopyToClipboard(); + + const share = useBoolean(); + + const popover = usePopover(); + + const details = useBoolean(); + + const favorite = useBoolean(file.isFavorited); + + const [inviteEmail, setInviteEmail] = useState(''); + + const handleChangeInvite = useCallback((event) => { + setInviteEmail(event.target.value); + }, []); + + const handleCopy = useCallback(() => { + toast.success('Copied!'); + copy(file.url); + }, [copy, file.url]); + + const renderAction = ( + + } + checkedIcon={} + checked={favorite.value} + onChange={favorite.onToggle} + inputProps={{ + name: 'checkbox-favorite', + 'aria-label': 'Checkbox favorite', + }} + /> + + + + + + ); + + const renderText = ( + + {fData(file.size)} + + {fDateTime(file.modifiedAt)} + + } + primaryTypographyProps={{ noWrap: true, typography: 'subtitle2' }} + secondaryTypographyProps={{ + mt: 0.5, + component: 'span', + alignItems: 'center', + typography: 'caption', + color: 'text.disabled', + display: 'inline-flex', + }} + /> + ); + + const renderAvatar = ( + + {file.shared?.map((person) => ( + + ))} + + ); + + return ( + <> + theme.customShadows.z20, + }, + ...sx, + }} + {...other} + > + + + {renderText} + + {!!file?.shared?.length && renderAvatar} + + {renderAction} + + + + + { + popover.onClose(); + handleCopy(); + }} + > + + Copy Link + + + { + popover.onClose(); + share.onTrue(); + }} + > + + Share + + + + + { + popover.onClose(); + onDelete(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + { + details.onFalse(); + onDelete(); + }} + /> + + { + share.onFalse(); + setInviteEmail(''); + }} + /> + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-storage-overview.jsx b/front_minimal/src/sections/file-manager/file-storage-overview.jsx new file mode 100644 index 0000000..70c1cd8 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-storage-overview.jsx @@ -0,0 +1,98 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import { useTheme } from '@mui/material/styles'; + +import { fData } from 'src/utils/format-number'; + +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function FileStorageOverview({ data, total, chart, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [theme.palette.secondary.main, theme.palette.secondary.light]; + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + stroke: { width: 0 }, + fill: { + type: 'gradient', + gradient: { + colorStops: [ + { offset: 0, color: chartColors[0], opacity: 1 }, + { offset: 100, color: chartColors[1], opacity: 1 }, + ], + }, + }, + plotOptions: { + radialBar: { + offsetY: 40, + startAngle: -90, + endAngle: 90, + hollow: { margin: -24 }, + track: { margin: -24 }, + dataLabels: { + name: { offsetY: 8 }, + value: { offsetY: -36 }, + total: { + label: `Used of ${fData(total)} / ${fData(total * 2)}`, + color: theme.vars.palette.text.disabled, + fontSize: theme.typography.caption.fontSize, + fontWeight: theme.typography.caption.fontWeight, + }, + }, + }, + }, + ...chart.options, + }); + + return ( + + + + + {data.map((category) => ( + + {category.icon} + + +
    {category.name}
    + {`${category.filesCount} files`} +
    + + {fData(category.usedStorage)} +
    + ))} +
    +
    + ); +} diff --git a/front_minimal/src/sections/file-manager/file-upgrade.jsx b/front_minimal/src/sections/file-manager/file-upgrade.jsx new file mode 100644 index 0000000..dcf1ae1 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-upgrade.jsx @@ -0,0 +1,65 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { CONFIG } from 'src/config-global'; + +import { SvgColor } from 'src/components/svg-color'; + +// ---------------------------------------------------------------------- + +export function FileUpgrade({ sx, ...other }) { + const theme = useTheme(); + + return ( + + + + + + + + Upgrade your plan and get more space + + + + + + ); +} diff --git a/front_minimal/src/sections/file-manager/file-widget.jsx b/front_minimal/src/sections/file-manager/file-widget.jsx new file mode 100644 index 0000000..e6461d6 --- /dev/null +++ b/front_minimal/src/sections/file-manager/file-widget.jsx @@ -0,0 +1,46 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import LinearProgress from '@mui/material/LinearProgress'; + +import { fData } from 'src/utils/format-number'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function FileWidget({ title, value, total, icon, sx, ...other }) { + return ( + + + + + + + + + {title} + + + + + + {fData(value)} + + {` / ${fData(total)}`} + + + ); +} diff --git a/front_minimal/src/sections/file-manager/view/file-manager-view.jsx b/front_minimal/src/sections/file-manager/view/file-manager-view.jsx new file mode 100644 index 0000000..a68ebff --- /dev/null +++ b/front_minimal/src/sections/file-manager/view/file-manager-view.jsx @@ -0,0 +1,242 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Typography from '@mui/material/Typography'; +import ToggleButton from '@mui/material/ToggleButton'; +import ToggleButtonGroup from '@mui/material/ToggleButtonGroup'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useSetState } from 'src/hooks/use-set-state'; + +import { fIsAfter, fIsBetween } from 'src/utils/format-time'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { _allFiles, FILE_TYPE_OPTIONS } from 'src/_mock'; + +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { fileFormat } from 'src/components/file-thumbnail'; +import { EmptyContent } from 'src/components/empty-content'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { useTable, rowInPage, getComparator } from 'src/components/table'; + +import { FileManagerTable } from '../file-manager-table'; +import { FileManagerFilters } from '../file-manager-filters'; +import { FileManagerGridView } from '../file-manager-grid-view'; +import { FileManagerFiltersResult } from '../file-manager-filters-result'; +import { FileManagerNewFolderDialog } from '../file-manager-new-folder-dialog'; + +// ---------------------------------------------------------------------- + +export function FileManagerView() { + const table = useTable({ defaultRowsPerPage: 10 }); + + const openDateRange = useBoolean(); + + const confirm = useBoolean(); + + const upload = useBoolean(); + + const [view, setView] = useState('list'); + + const [tableData, setTableData] = useState(_allFiles); + + const filters = useSetState({ + name: '', + type: [], + startDate: null, + endDate: null, + }); + + const dateError = fIsAfter(filters.state.startDate, filters.state.endDate); + + const dataFiltered = applyFilter({ + inputData: tableData, + comparator: getComparator(table.order, table.orderBy), + filters: filters.state, + dateError, + }); + + const dataInPage = rowInPage(dataFiltered, table.page, table.rowsPerPage); + + const canReset = + !!filters.state.name || + filters.state.type.length > 0 || + (!!filters.state.startDate && !!filters.state.endDate); + + const notFound = (!dataFiltered.length && canReset) || !dataFiltered.length; + + const handleChangeView = useCallback((event, newView) => { + if (newView !== null) { + setView(newView); + } + }, []); + + const handleDeleteItem = useCallback( + (id) => { + const deleteRow = tableData.filter((row) => row.id !== id); + + toast.success('Delete success!'); + + setTableData(deleteRow); + + table.onUpdatePageDeleteRow(dataInPage.length); + }, + [dataInPage.length, table, tableData] + ); + + const handleDeleteItems = useCallback(() => { + const deleteRows = tableData.filter((row) => !table.selected.includes(row.id)); + + toast.success('Delete success!'); + + setTableData(deleteRows); + + table.onUpdatePageDeleteRows({ + totalRowsInPage: dataInPage.length, + totalRowsFiltered: dataFiltered.length, + }); + }, [dataFiltered.length, dataInPage.length, table, tableData]); + + const renderFilters = ( + + + + + + + + + + + + + + ); + + const renderResults = ( + + ); + + return ( + <> + + + File manager + + + + + {renderFilters} + + {canReset && renderResults} + + + {notFound ? ( + + ) : ( + <> + {view === 'list' ? ( + + ) : ( + + )} + + )} + + + + + + Are you sure want to delete {table.selected.length} items? + + } + action={ + + } + /> + + ); +} + +function applyFilter({ inputData, comparator, filters, dateError }) { + const { name, type, startDate, endDate } = filters; + + const stabilizedThis = inputData.map((el, index) => [el, index]); + + stabilizedThis.sort((a, b) => { + const order = comparator(a[0], b[0]); + if (order !== 0) return order; + return a[1] - b[1]; + }); + + inputData = stabilizedThis.map((el) => el[0]); + + if (name) { + inputData = inputData.filter( + (file) => file.name.toLowerCase().indexOf(name.toLowerCase()) !== -1 + ); + } + + if (type.length) { + inputData = inputData.filter((file) => type.includes(fileFormat(file.type))); + } + + if (!dateError) { + if (startDate && endDate) { + inputData = inputData.filter((file) => fIsBetween(file.createdAt, startDate, endDate)); + } + } + + return inputData; +} diff --git a/front_minimal/src/sections/file-manager/view/index.js b/front_minimal/src/sections/file-manager/view/index.js new file mode 100644 index 0000000..98db4b0 --- /dev/null +++ b/front_minimal/src/sections/file-manager/view/index.js @@ -0,0 +1 @@ +export * from './file-manager-view'; diff --git a/front_minimal/src/sections/home/components/hero-background.jsx b/front_minimal/src/sections/home/components/hero-background.jsx new file mode 100644 index 0000000..a857d7c --- /dev/null +++ b/front_minimal/src/sections/home/components/hero-background.jsx @@ -0,0 +1,122 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import { useTheme } from '@mui/material/styles'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, stylesMode } from 'src/theme/styles'; + +import { MotionContainer } from 'src/components/animate'; + +import { Dots, Lines, Texts, Circles, PlusIcon } from './hero-svg'; + +// ---------------------------------------------------------------------- + +export function HeroBackground({ sx }) { + const theme = useTheme(); + + const upMd = useResponsive('up', 'md'); + + const lightMode = theme.palette.mode === 'light'; + + const strokeCount = 12; + + return ( + + + + {upMd && } + + + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/home/components/hero-svg.jsx b/front_minimal/src/sections/home/components/hero-svg.jsx new file mode 100644 index 0000000..e9aa3d2 --- /dev/null +++ b/front_minimal/src/sections/home/components/hero-svg.jsx @@ -0,0 +1,336 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import { useTheme } from '@mui/material/styles'; + +import { stylesMode } from 'src/theme/styles'; + +import { varFade } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export function Lines({ strokeCount }) { + const draw = { + x: { + hidden: { x2: 0, strokeOpacity: 0 }, + visible: (i) => { + const delay = 1 + i * 0.5; + return { + x2: '100%', + strokeOpacity: 1, + transition: { + strokeOpacity: { delay, duration: 0.01 }, + x2: { + delay, + bounce: 0, + duration: 1.5, + type: 'spring', + }, + }, + }; + }, + }, + y: { + hidden: { y2: 0, strokeOpacity: 0 }, + visible: (i) => { + const delay = 1 + i * 0.5; + return { + y2: '100%', + strokeOpacity: 1, + transition: { + strokeOpacity: { delay, duration: 0.01 }, + y2: { + delay, + bounce: 0, + duration: 1.5, + type: 'spring', + }, + }, + }; + }, + }, + }; + + const translateY = (index) => + strokeCount / 2 > index + ? `translateY(calc(((${index} * var(--stroke-spacing)) + var(--stroke-spacing) / 2) * -1))` + : `translateY(calc(((${strokeCount - (index + 1)} * var(--stroke-spacing)) + var(--stroke-spacing) / 2)))`; + + const linesX = ( + <> + {[...Array(strokeCount)].map((_, index) => ( + + ))} + + ); + + const translateX = (index) => + strokeCount / 2 > index + ? `translateX(calc(((${index} * var(--stroke-spacing)) + var(--stroke-spacing) / 2) * -1))` + : `translateX(calc(((${strokeCount - (index + 1)} * var(--stroke-spacing)) + var(--stroke-spacing) / 2)))`; + + const linesY = ( + <> + {[...Array(strokeCount)].map((_, index) => ( + + ))} + + ); + + return ( + <> + {linesX} + {linesY} + + ); +} + +// ---------------------------------------------------------------------- + +export function Circles() { + const drawCircle = { + hidden: { opacity: 0 }, + visible: (i) => { + const delay = 1 + i * 0.5; + return { opacity: 1, transition: { opacity: { delay, duration: 0.01 } } }; + }, + }; + + return ( + <> + + + + + + + ); +} + +// ---------------------------------------------------------------------- + +export function PlusIcon() { + const drawPlus = { + hidden: { opacity: 0, pathLength: 0 }, + visible: (i) => { + const delay = 1 + i * 0.5; + return { + opacity: 1, + pathLength: 1, + transition: { + opacity: { delay, duration: 0.01 }, + pathLength: { + delay, + bounce: 0, + duration: 1.5, + type: 'spring', + }, + }, + }; + }, + }; + + return ( + <> + + + + + ); +} + +// ---------------------------------------------------------------------- + +export function Texts({ sx, ...other }) { + return ( + + theme.typography.fontSecondaryFamily, + }, + }} + > + + Minimal Design System Minimal Design System + + + + ); +} + +function Dot({ color = 'primary', animate, transition, sx, ...other }) { + const theme = useTheme(); + + return ( + + + + ); +} + +// ---------------------------------------------------------------------- + +export function Dots() { + return ( + <> + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/home/components/section-title.jsx b/front_minimal/src/sections/home/components/section-title.jsx new file mode 100644 index 0000000..140585d --- /dev/null +++ b/front_minimal/src/sections/home/components/section-title.jsx @@ -0,0 +1,73 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { varAlpha, textGradient } from 'src/theme/styles'; + +import { varFade } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export function SectionTitle({ title, caption, slotProps, txtGradient, description, ...other }) { + const theme = useTheme(); + + return ( + + {caption && ( + + )} + + + {`${title} `} + + {txtGradient} + + + + {description && ( + + {description} + + )} + + ); +} + +// ---------------------------------------------------------------------- + +export function SectionCaption({ title, variants, sx }) { + return ( + + {title} + + ); +} diff --git a/front_minimal/src/sections/home/components/svg-elements.jsx b/front_minimal/src/sections/home/components/svg-elements.jsx new file mode 100644 index 0000000..7b19191 --- /dev/null +++ b/front_minimal/src/sections/home/components/svg-elements.jsx @@ -0,0 +1,254 @@ +import { useId } from 'react'; +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; + +import { varFade } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +const baseStyles = { + zIndex: 2, + display: 'none', + color: 'grey.500', + position: 'absolute', + '& line': { strokeDasharray: 3, stroke: 'currentColor' }, + '& path': { fill: 'currentColor', stroke: 'currentColor' }, + '@media (min-width: 1440px)': { display: 'block' }, +}; + +const transition = { duration: 0.64, ease: [0.43, 0.13, 0.23, 0.96] }; + +// ---------------------------------------------------------------------- + +export function FloatLine({ sx, vertical, ...other }) { + return ( + + {vertical ? ( + + ) : ( + + )} + + ); +} + +// ---------------------------------------------------------------------- + +export function FloatPlusIcon({ sx, ...other }) { + return ( + + + + ); +} + +// ---------------------------------------------------------------------- + +export function FloatXIcon({ sx, ...other }) { + return ( + + + + ); +} + +// ---------------------------------------------------------------------- + +export function FloatTriangleLeftIcon({ sx, ...other }) { + return ( + + + + ); +} + +// ---------------------------------------------------------------------- + +export function FloatTriangleDownIcon({ sx, ...other }) { + return ( + + + + ); +} + +// ---------------------------------------------------------------------- + +export function FloatDotIcon({ sx, ...other }) { + return ( + + ); +} + +// ---------------------------------------------------------------------- + +export function CircleSvg({ sx, variants }) { + const maskId = useId(); + const clipPathId = useId(); + const gradientId = useId(); + + return ( + + + + + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/home/home-advertisement.jsx b/front_minimal/src/sections/home/home-advertisement.jsx new file mode 100644 index 0000000..3cc7327 --- /dev/null +++ b/front_minimal/src/sections/home/home-advertisement.jsx @@ -0,0 +1,179 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import { useTheme } from '@mui/material/styles'; +import Container from '@mui/material/Container'; + +import { paths } from 'src/routes/paths'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, textGradient } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { SvgColor } from 'src/components/svg-color'; +import { varFade, MotionViewport } from 'src/components/animate'; + +import { FloatLine, FloatPlusIcon } from './components/svg-elements'; + +// ---------------------------------------------------------------------- + +export function HomeAdvertisement({ sx, ...other }) { + const theme = useTheme(); + + const renderLines = ( + <> + + + + + ); + + const renderDescription = ( + + + Get started with +
    Minimal kit + + today + +
    + + + + + + + + + + +
    + ); + + const renderImg = ( + + + + ); + + const renderGridBg = ( + + + + ); + + const renderBlur = ( + + ); + + return ( + + + {renderLines} + + + + {renderImg} + + {renderDescription} + + {renderGridBg} + + {renderBlur} + + + + + ); +} diff --git a/front_minimal/src/sections/home/home-faqs.jsx b/front_minimal/src/sections/home/home-faqs.jsx new file mode 100644 index 0000000..666c08e --- /dev/null +++ b/front_minimal/src/sections/home/home-faqs.jsx @@ -0,0 +1,299 @@ +import { useState } from 'react'; +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; +import Accordion, { accordionClasses } from '@mui/material/Accordion'; +import AccordionDetails, { accordionDetailsClasses } from '@mui/material/AccordionDetails'; +import AccordionSummary, { accordionSummaryClasses } from '@mui/material/AccordionSummary'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { varFade, MotionViewport } from 'src/components/animate'; + +import { SectionTitle } from './components/section-title'; +import { FloatLine, FloatPlusIcon, FloatTriangleDownIcon } from './components/svg-elements'; + +// ---------------------------------------------------------------------- + +const FAQs = [ + { + question: 'How can I get the update?', + answer: ( + + You will get 12 months of free + + updates + + with the purchase. Please renew your license to get updates after that. + + ), + }, + { + question: 'Which license is right for you?', + answer: ( + +
  • All licenses do not apply to open source.
  • +
  • One licenses / one end product (3 licenses / 3 products...).
  • +
  • + Standard / Plus license used in free products (Internal management...). +
  • +
  • + Extended license used in charge products, collect fees from users + (SAAS...). +
  • +
  • + Learn more about the + + package & license + +
  • +
    + ), + }, + { + question: 'How long is my license valid for?', + answer: ( + +
  • The license is lifetime.
  • +
  • You get 12 months of free updates.
  • +
    + ), + }, + { + question: 'Which platforms will the template support?', + answer: ( + + {`The components in MUI are designed to work in the latest, stable releases of all major browsers, including Chrome, Firefox, Safari, and Edge. We don't support Internet Explorer 11. `} + Learn more about the + + supported platforms + + + ), + }, + { + question: 'For what kind of projects is the Standard license intended?', + answer: ( + + The Standard license is designed for internal applications in which staff will access the + application. An example could be the back-office dashboard of a public-facing e-commerce + website in which staff would sign in and manage inventory, customers, etc. + + ), + }, + { + question: 'Do you have a free demo to review the code before purchasing?', + answer: ( + + Yes, you can check out our + + open source + + dashboard template which should give you an overview of the code quality and folder + structure. Keep in mind that some aspects may differ from this Paid version. + + ), + }, +]; + +// ---------------------------------------------------------------------- + +export function HomeFAQs({ sx, ...other }) { + const [expanded, setExpanded] = useState(FAQs[0].question); + + const handleChange = (panel) => (event, isExpanded) => { + setExpanded(isExpanded ? panel : false); + }; + + const renderDescription = ( + + ); + + const renderContent = ( + + {FAQs.map((item, index) => ( + + theme.transitions.create(['background-color'], { + duration: theme.transitions.duration.short, + }), + '&::before': { display: 'none' }, + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + }, + '&:first-of-type, &:last-of-type': { borderRadius: 2 }, + [`&.${accordionClasses.expanded}`]: { + m: 0, + borderRadius: 2, + boxShadow: 'none', + bgcolor: (theme) => varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + }, + [`& .${accordionSummaryClasses.root}`]: { + py: 3, + px: 2.5, + minHeight: 'auto', + [`& .${accordionSummaryClasses.content}`]: { + m: 0, + [`&.${accordionSummaryClasses.expanded}`]: { m: 0 }, + }, + }, + [`& .${accordionDetailsClasses.root}`]: { px: 2.5, pt: 0, pb: 3 }, + }} + > + + } + aria-controls={`panel${index}bh-content`} + id={`panel${index}bh-header`} + > + {item.question} + + {item.answer} + + ))} + + ); + + const renderContact = ( + + `linear-gradient(270deg, ${varAlpha(theme.vars.palette.grey['500Channel'], 0.08)}, ${varAlpha(theme.vars.palette.grey['500Channel'], 0)})`, + }} + > + + Still have questions? + + + + + Please describe your case to receive the most accurate advice + + + + + + + + ); + + return ( + + + + + + {renderDescription} + {renderContent} + + + + + {renderContact} + + + + ); +} + +// ---------------------------------------------------------------------- + +function TopLines() { + return ( + <> + + + + + + + ); +} + +function BottomLines() { + return ( + <> + + + + + + ); +} diff --git a/front_minimal/src/sections/home/home-for-designer.jsx b/front_minimal/src/sections/home/home-for-designer.jsx new file mode 100644 index 0000000..4fd771a --- /dev/null +++ b/front_minimal/src/sections/home/home-for-designer.jsx @@ -0,0 +1,176 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import { useTheme } from '@mui/material/styles'; + +import { paths } from 'src/routes/paths'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, textGradient } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { varFade, AnimateBorder, MotionViewport } from 'src/components/animate'; + +import { SectionTitle } from './components/section-title'; + +// ---------------------------------------------------------------------- + +export function HomeForDesigner({ sx, ...other }) { + const theme = useTheme(); + + const borderTop = ( + + ); + + const borderBottom = ( + + ); + + return ( + + + + {borderTop} + + + + + + + + + + + {borderBottom} + + + ); +} diff --git a/front_minimal/src/sections/home/home-hero.jsx b/front_minimal/src/sections/home/home-hero.jsx new file mode 100644 index 0000000..bf27460 --- /dev/null +++ b/front_minimal/src/sections/home/home-hero.jsx @@ -0,0 +1,342 @@ +import { useRef, useState } from 'react'; +import { m, useScroll, useSpring, useTransform, useMotionValueEvent } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; +import AvatarGroup from '@mui/material/AvatarGroup'; +import Avatar, { avatarClasses } from '@mui/material/Avatar'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +import { _mock } from 'src/_mock'; +import { CONFIG } from 'src/config-global'; +import { textGradient } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { SvgColor } from 'src/components/svg-color'; +import { varFade, MotionContainer } from 'src/components/animate'; + +import { HeroBackground } from './components/hero-background'; + +// ---------------------------------------------------------------------- + +const smKey = 'sm'; +const mdKey = 'md'; +const lgKey = 'lg'; + +export function HomeHero({ sx, ...other }) { + const theme = useTheme(); + + const scroll = useScrollPercent(); + + const mdUp = useResponsive('up', mdKey); + + const distance = mdUp ? scroll.percent : 0; + + const y1 = useTransformY(scroll.scrollY, distance * -7); + const y2 = useTransformY(scroll.scrollY, distance * -6); + const y3 = useTransformY(scroll.scrollY, distance * -5); + const y4 = useTransformY(scroll.scrollY, distance * -4); + const y5 = useTransformY(scroll.scrollY, distance * -3); + + const opacity = useTransform( + scroll.scrollY, + [0, 1], + [1, mdUp ? Number((1 - scroll.percent / 100).toFixed(1)) : 1] + ); + + const renderHeading = ( + + + + Boost your building + + process with + + Minimal + + + + ); + + const renderText = ( + + + {`The starting point for your next project is based on MUI. \nEasy customization helps you build apps faster and better.`} + + + ); + + const renderRatings = ( + + + + {[...Array(3)].map((_, index) => ( + + ))} + + 160+ Happy customers + + + ); + + const renderButtons = ( + + + + + + + Get free version + + + + + + + + + + ); + + const renderIcons = ( + + + + Available For + + + + + {['js', 'ts', 'nextjs', 'vite', 'figma'].map((platform) => ( + + {platform === 'nextjs' ? ( + + ) : ( + + )} + + ))} + + + ); + + return ( + + + + + {renderHeading} + {renderText} + + {renderRatings} + {renderButtons} + {renderIcons} + + + + + + ); +} + +// ---------------------------------------------------------------------- + +function MInview({ children, component = m.div }) { + return ( + + {children} + + ); +} + +// ---------------------------------------------------------------------- + +function useTransformY(value, distance) { + const physics = { + mass: 0.1, + damping: 20, + stiffness: 300, + restDelta: 0.001, + }; + + return useSpring(useTransform(value, [0, 1], [0, distance]), physics); +} + +function useScrollPercent() { + const elementRef = useRef(null); + + const { scrollY } = useScroll(); + + const [percent, setPercent] = useState(0); + + useMotionValueEvent(scrollY, 'change', (scrollHeight) => { + let heroHeight = 0; + + if (elementRef.current) { + heroHeight = elementRef.current.offsetHeight; + } + + const scrollPercent = Math.floor((scrollHeight / heroHeight) * 100); + + if (scrollPercent >= 100) { + setPercent(100); + } else { + setPercent(Math.floor(scrollPercent)); + } + }); + + return { elementRef, percent, scrollY }; +} diff --git a/front_minimal/src/sections/home/home-highlight-features.jsx b/front_minimal/src/sections/home/home-highlight-features.jsx new file mode 100644 index 0000000..8a2c00a --- /dev/null +++ b/front_minimal/src/sections/home/home-highlight-features.jsx @@ -0,0 +1,249 @@ +import { useRef, useState, forwardRef } from 'react'; +import { m, useSpring, useScroll, useTransform, useMotionValueEvent } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import SvgIcon from '@mui/material/SvgIcon'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; +import { styled, useTheme } from '@mui/material/styles'; + +import { useClientRect } from 'src/hooks/use-client-rect'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, stylesMode } from 'src/theme/styles'; +import PRIMARY_COLOR from 'src/theme/with-settings/primary-color.json'; + +import { Iconify } from 'src/components/iconify'; +import { varFade, MotionViewport } from 'src/components/animate'; + +import { SectionTitle } from './components/section-title'; +import { FloatLine, FloatPlusIcon } from './components/svg-elements'; + +// ---------------------------------------------------------------------- + +export function HomeHighlightFeatures({ sx, ...other }) { + const containerRoot = useClientRect(); + + const renderLines = ( + <> + + + + + ); + + return ( + + + {renderLines} + + + + + + + + + + + + + + + + ); +} + +// ---------------------------------------------------------------------- + +const StyledRoot = styled( + forwardRef((props, ref) => ) +)(({ theme }) => ({ + zIndex: 9, + position: 'relative', + paddingTop: theme.spacing(5), + [theme.breakpoints.up('md')]: { paddingTop: theme.spacing(8) }, +})); + +const StyledContainer = styled((props) => )(({ theme }) => ({ + top: 0, + height: '100vh', + display: 'flex', + position: 'sticky', + overflow: 'hidden', + flexDirection: 'column', + alignItems: 'flex-start', + transition: theme.transitions.create(['background-color']), + '&[data-scrolling="true"]': { justifyContent: 'center' }, +})); + +const StyledContent = styled( + forwardRef((props, ref) => ( + + )) +)(({ theme }) => ({ + display: 'flex', + gap: theme.spacing(5), + paddingLeft: theme.spacing(3), + transition: theme.transitions.create(['margin-left', 'margin-top']), + [theme.breakpoints.up('md')]: { + gap: theme.spacing(8), + paddingLeft: theme.spacing(0), + }, +})); + +// ---------------------------------------------------------------------- + +function ScrollContent({ containerRoot }) { + const theme = useTheme(); + + const containerRef = useRef(null); + const containeRect = useClientRect(containerRef); + + const scrollRef = useRef(null); + const scrollRect = useClientRect(scrollRef); + + const { scrollYProgress } = useScroll({ target: containerRef }); + + const [startScroll, setStartScroll] = useState(false); + + const physics = { damping: 16, mass: 0.12, stiffness: 80 }; + + const scrollRange = -scrollRect.scrollWidth + containeRect.width / 2; + + const x = useSpring(useTransform(scrollYProgress, [0, 1], [0, scrollRange]), physics); + + const background = useTransform( + scrollYProgress, + [0, 0.12, 0.28, 0.48, 0.58, 0.62, 0.72, 0.92], + [ + `transparent`, + `linear-gradient(180deg, ${theme.palette.primary.light}, ${theme.palette.primary.dark})`, + `linear-gradient(180deg, ${PRIMARY_COLOR.cyan.light}, ${PRIMARY_COLOR.cyan.dark})`, + `linear-gradient(180deg, ${PRIMARY_COLOR.purple.light}, ${PRIMARY_COLOR.purple.dark})`, + `linear-gradient(180deg, ${PRIMARY_COLOR.blue.light}, ${PRIMARY_COLOR.blue.dark})`, + `linear-gradient(180deg, ${PRIMARY_COLOR.orange.light}, ${PRIMARY_COLOR.orange.dark})`, + `linear-gradient(180deg, ${PRIMARY_COLOR.red.light}, ${PRIMARY_COLOR.red.dark})`, + `linear-gradient(180deg, ${theme.palette.background.neutral}, ${theme.palette.background.neutral})`, + ] + ); + + useMotionValueEvent(scrollYProgress, 'change', (latest) => { + if (latest !== 0 && latest !== 1) { + setStartScroll(true); + } else { + setStartScroll(false); + } + }); + + return ( + + + + {ITEMS.map((item) => ( + + ))} + + + + ); +} + +function Item({ item, sx, ...other }) { + return ( + + + + + {item.title} + {item.subtitle} + + + + + {item.imgUrl.map((url) => ( + + `-40px 40px 80px 0px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.16)}`, + [stylesMode.dark]: { + boxShadow: (theme) => + `-40px 40px 80px 0px ${varAlpha(theme.vars.palette.common.blackChannel, 0.16)}`, + }, + }} + > + + + ))} + + + ); +} + +// ---------------------------------------------------------------------- + +const ITEMS = [ + { + title: 'Dark mode', + subtitle: 'A dark theme that feels easier on the eyes.', + icon: 'solar:cloudy-moon-bold-duotone', + imgUrl: [`${CONFIG.site.basePath}/assets/images/home/highlight-darkmode.webp`], + }, + { + title: 'Color presets', + subtitle: 'Express your own style with just one click.', + icon: 'solar:pallete-2-bold-duotone', + imgUrl: [ + `${CONFIG.site.basePath}/assets/images/home/highlight-presets-1.webp`, + `${CONFIG.site.basePath}/assets/images/home/highlight-presets-2.webp`, + `${CONFIG.site.basePath}/assets/images/home/highlight-presets-3.webp`, + `${CONFIG.site.basePath}/assets/images/home/highlight-presets-4.webp`, + `${CONFIG.site.basePath}/assets/images/home/highlight-presets-5.webp`, + ], + }, + { + title: 'Right-to-left', + subtitle: 'Support languages such as Arabic, Persian, and Hebrew.', + icon: 'solar:align-right-bold-duotone', + imgUrl: [`${CONFIG.site.basePath}/assets/images/home/highlight-rtl.webp`], + }, +]; diff --git a/front_minimal/src/sections/home/home-hugepack-elements.jsx b/front_minimal/src/sections/home/home-hugepack-elements.jsx new file mode 100644 index 0000000..b530bb9 --- /dev/null +++ b/front_minimal/src/sections/home/home-hugepack-elements.jsx @@ -0,0 +1,198 @@ +import { useRef, useState, forwardRef } from 'react'; +import { m, useSpring, useScroll, useTransform, useMotionValueEvent } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import Grid from '@mui/material/Unstable_Grid2'; +import Typography from '@mui/material/Typography'; +import { styled, useTheme } from '@mui/material/styles'; + +import { paths } from 'src/routes/paths'; + +import { useClientRect } from 'src/hooks/use-client-rect'; + +import { CONFIG } from 'src/config-global'; + +import { Iconify } from 'src/components/iconify'; +import { varFade, MotionViewport } from 'src/components/animate'; + +import { SectionTitle, SectionCaption } from './components/section-title'; +import { FloatLine, FloatTriangleLeftIcon } from './components/svg-elements'; + +// ---------------------------------------------------------------------- + +export function HomeHugePackElements({ sx, ...other }) { + const renderLines = ( + <> + + + + ); + + return ( + + + {renderLines} + + + + + + + + + + + + + Explore a comprehensive range of elements + +
    + like menus, sliders, buttons, inputs, and others, all conveniently gathered here. +
    +
    +
    +
    + + + + +
    +
    + + +
    + ); +} + +// ---------------------------------------------------------------------- + +const StyledRoot = styled( + forwardRef((props, ref) => ) +)(({ theme }) => ({ + zIndex: 9, + position: 'relative', + paddingTop: theme.spacing(5), + [theme.breakpoints.up('md')]: { paddingTop: theme.spacing(15) }, +})); + +const StyledContainer = styled((props) => )(({ theme }) => ({ + top: 0, + height: '100vh', + display: 'flex', + position: 'sticky', + overflow: 'hidden', + flexDirection: 'column', + justifyContent: 'flex-start', + transition: theme.transitions.create(['background-color']), + '&[data-scrolling="true"]': { justifyContent: 'center' }, +})); + +const StyledContent = styled( + forwardRef((props, ref) => ( + + )) +)(({ theme }) => ({ + display: 'flex', + flexDirection: 'column', + gap: theme.spacing(3), + [theme.breakpoints.up('md')]: { gap: theme.spacing(5) }, +})); + +const StyledItem = styled((props) => )({ + backgroundSize: 'auto 100%', + backgroundRepeat: 'repeat-x', + backgroundPosition: 'center center', +}); + +// ---------------------------------------------------------------------- + +function ScrollContent() { + const theme = useTheme(); + + const containerRef = useRef(null); + const containerRect = useClientRect(containerRef); + + const scrollRef = useRef(null); + const scrollRect = useClientRect(scrollRef); + + const [startScroll, setStartScroll] = useState(false); + + const { scrollYProgress } = useScroll({ target: containerRef }); + + const physics = { damping: 16, mass: 0.16, stiffness: 50 }; + + const scrollRange = -scrollRect.scrollWidth + containerRect.width; + + const x1 = useSpring(useTransform(scrollYProgress, [0, 1], [0, scrollRange]), physics); + const x2 = useSpring(useTransform(scrollYProgress, [0, 1], [scrollRange, 0]), physics); + + const background = useTransform( + scrollYProgress, + [0, 0.25, 0.5, 0.75, 1], + [ + theme.vars.palette.background.default, + theme.vars.palette.background.neutral, + theme.vars.palette.background.neutral, + theme.vars.palette.background.neutral, + theme.vars.palette.background.default, + ] + ); + + useMotionValueEvent(scrollYProgress, 'change', (latest) => { + if (latest !== 0 && latest !== 1) { + setStartScroll(true); + } else { + setStartScroll(false); + } + }); + + return ( + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/home/home-integrations.jsx b/front_minimal/src/sections/home/home-integrations.jsx new file mode 100644 index 0000000..2c7f559 --- /dev/null +++ b/front_minimal/src/sections/home/home-integrations.jsx @@ -0,0 +1,95 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Container from '@mui/material/Container'; +import Grid from '@mui/material/Unstable_Grid2'; + +import { CONFIG } from 'src/config-global'; + +import { varScale, MotionViewport } from 'src/components/animate'; + +import { SectionTitle } from './components/section-title'; +import { FloatLine, FloatDotIcon } from './components/svg-elements'; + +// ---------------------------------------------------------------------- + +export function HomeIntegrations({ sx, ...other }) { + const renderLines = ( + <> + + + + + + + + + + ); + + const renderDescription = ( + + + A comprehensive suite of integrations offers diverse functionalities. + + + * Only includes authentication methods. +
    * Database not included. +
    + + } + sx={{ textAlign: { xs: 'center', md: 'left' } }} + /> + ); + + const renderImg = ( + + ); + + return ( + + + {renderLines} + + + + + {renderDescription} + + + + {renderImg} + + + + + + ); +} diff --git a/front_minimal/src/sections/home/home-minimal.jsx b/front_minimal/src/sections/home/home-minimal.jsx new file mode 100644 index 0000000..9041b0d --- /dev/null +++ b/front_minimal/src/sections/home/home-minimal.jsx @@ -0,0 +1,151 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Grid from '@mui/material/Unstable_Grid2'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, stylesMode } from 'src/theme/styles'; + +import { SvgColor } from 'src/components/svg-color'; +import { varFade, MotionViewport } from 'src/components/animate'; + +import { SectionTitle } from './components/section-title'; +import { CircleSvg, FloatLine, FloatPlusIcon } from './components/svg-elements'; + +// ---------------------------------------------------------------------- + +export function HomeMinimal({ sx, ...other }) { + const renderLines = ( + <> + + + + + + + ); + + const renderDescription = ( + <> + + + + {ITEMS.map((item) => ( + + + + + {item.title} + + {item.description} + + + ))} + + + ); + + const renderImg = ( + + + `-40px 40px 80px 0px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.16)}`, + [stylesMode.dark]: { + boxShadow: (theme) => + `-40px 40px 80px 0px ${varAlpha(theme.vars.palette.common.blackChannel, 0.16)}`, + }, + }} + > + + + + ); + + return ( + + + {renderLines} + + + + + {renderDescription} + + + + {renderImg} + + + + + + + + ); +} + +// ---------------------------------------------------------------------- + +const ITEMS = [ + { + icon: `${CONFIG.site.basePath}/assets/icons/home/ic-make-brand.svg`, + title: 'Branding', + description: 'Consistent design makes it easy to brand your own.', + }, + { + icon: `${CONFIG.site.basePath}/assets/icons/home/ic-design.svg`, + title: 'UI & UX design', + description: 'The kit is built on the principles of the atomic design system.', + }, + { + icon: `${CONFIG.site.basePath}/assets/icons/home/ic-development.svg`, + title: 'Development', + description: 'Easy to customize and extend, saving you time and money.', + }, +]; diff --git a/front_minimal/src/sections/home/home-pricing.jsx b/front_minimal/src/sections/home/home-pricing.jsx new file mode 100644 index 0000000..94ac0d6 --- /dev/null +++ b/front_minimal/src/sections/home/home-pricing.jsx @@ -0,0 +1,288 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Tab from '@mui/material/Tab'; +import Tabs from '@mui/material/Tabs'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import Container from '@mui/material/Container'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; + +import { useTabs } from 'src/hooks/use-tabs'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { varFade, varScale, MotionViewport } from 'src/components/animate'; + +import { SectionTitle } from './components/section-title'; +import { FloatLine, FloatXIcon } from './components/svg-elements'; + +// ---------------------------------------------------------------------- + +export function HomePricing({ sx, ...other }) { + const theme = useTheme(); + + const tabs = useTabs('Standard'); + + const renderDescription = ( + + ); + + const renderContentDesktop = ( + + {PLANS.map((plan) => ( + + ))} + + ); + + const renderContentMobile = ( + + + {PLANS.map((tab) => ( + + ))} + + + + {PLANS.map( + (tab) => tab.license === tabs.value && + )} + + + ); + + return ( + + + + + {renderDescription} + + + {renderContentDesktop} + + + + + + {renderContentMobile} + + + ); +} + +function PlanCard({ plan, sx, ...other }) { + const standardLicense = plan.license === 'Standard'; + + const plusLicense = plan.license === 'Plus'; + + const renderLines = ( + <> + + + + + + + + ); + + return ( + + {plusLicense && renderLines} + + + + + + {plan.license} + + + + + + + + + + + ${plan.price} + + + + + + {plan.icons.map((icon, index) => ( + + ))} + {standardLicense && ( + + (only) + + )} + + + + {plan.commons.map((option) => ( + + + {option} + + ))} + + + + + + {plan.options.map((option, index) => { + const disabled = + (standardLicense && [1, 2, 3].includes(index)) || (plusLicense && [3].includes(index)); + + return ( + + + {option} + + ); + })} + + + + + + + ); +} + +// ---------------------------------------------------------------------- + +const PLANS = [...Array(3)].map((_, index) => ({ + license: ['Standard', 'Plus', 'Extended'][index], + price: [69, 129, 599][index], + commons: [ + 'One end products', + '12 months updates', + '6 months of support', + 'One-time payments', + 'Lifetime perpetual license.', + ], + options: [ + 'JavaScript version', + 'TypeScript version', + 'Design resources (Figma)', + 'Commercial applications', + ], + icons: [ + `${CONFIG.site.basePath}/assets/icons/platforms/ic-js.svg`, + `${CONFIG.site.basePath}/assets/icons/platforms/ic-ts.svg`, + `${CONFIG.site.basePath}/assets/icons/platforms/ic-figma.svg`, + ], +})); diff --git a/front_minimal/src/sections/home/home-testimonials.jsx b/front_minimal/src/sections/home/home-testimonials.jsx new file mode 100644 index 0000000..bb9e4bc --- /dev/null +++ b/front_minimal/src/sections/home/home-testimonials.jsx @@ -0,0 +1,273 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Rating from '@mui/material/Rating'; +import Divider from '@mui/material/Divider'; +import Container from '@mui/material/Container'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { fToNow } from 'src/utils/format-time'; + +import { _mock } from 'src/_mock'; +import { maxLine, varAlpha, textGradient } from 'src/theme/styles'; + +import { varFade, MotionViewport, AnimateCountUp } from 'src/components/animate'; +import { + Carousel, + useCarousel, + CarouselDotButtons, + carouselBreakpoints, + CarouselArrowBasicButtons, +} from 'src/components/carousel'; + +import { SectionTitle } from './components/section-title'; +import { FloatLine, FloatTriangleDownIcon } from './components/svg-elements'; + +// ---------------------------------------------------------------------- + +export function HomeTestimonials({ sx, ...other }) { + const theme = useTheme(); + + const renderLines = ( + <> + + + + + + + ); + + const carousel = useCarousel({ + align: 'start', + slidesToShow: { xs: 1, sm: 2, md: 3, lg: 4 }, + breakpoints: { + [carouselBreakpoints.sm]: { slideSpacing: '24px' }, + [carouselBreakpoints.md]: { slideSpacing: '40px' }, + [carouselBreakpoints.lg]: { slideSpacing: '64px' }, + }, + }); + + const renderDescription = ( + + ); + + const horizontalDivider = (position) => ( + + ); + + const verticalDivider = ( + + ); + + const renderContent = ( + + {horizontalDivider('top')} + + + {TESTIMONIALS.map((item) => ( + + + + {item.category} + + + + {item.content} + + + + + + {item.name} + + {fToNow(new Date(item.postedAt))} + + + + + ))} + + + + + + + + + ); + + const renderNumber = ( + + {horizontalDivider('top')} + + + {[ + { label: 'Purchased order', value: 12.121 }, + { label: 'Happy customers', value: 160 }, + { label: 'Review rate', value: 4.9 }, + ].map((item) => ( + + + + + + + + {item.label} + + + + ))} + + + {horizontalDivider('bottom')} + + ); + + return ( + + + {renderLines} + + + {renderDescription} + + {renderContent} + + {renderNumber} + + + + ); +} + +// ---------------------------------------------------------------------- + +const base = (index) => ({ + id: _mock.id(index), + name: _mock.fullName(index), + avatar: _mock.image.avatar(index), + rating: 5, +}); + +const TESTIMONIALS = [ + { + ...base(1), + category: 'Design Quality', + content: `The quality of this template is very good, the TypeScript files are neat and the communication with the team behind this template is very good! I would recommend this template for any kind of project, as they implement new features every now and then and enhance their design. I will definitely be using more templates from this team and re-purchasing this template for other projects.`, + postedAt: 'April 20, 2024 23:15:30', + }, + { + ...base(2), + category: 'Design Quality', + content: `Amazing. I've never purchased complete front ends before, but I'll definitely be doing this again!`, + postedAt: 'March 19, 2024 23:15:30', + }, + { + ...base(3), + category: 'Code Quality', + content: `Clean & Complete (Design & Code). Thansk Minimal team :)`, + postedAt: 'April 19, 2023 23:15:30', + }, + { + ...base(4), + category: 'Customer Support', + content: `Thanks to Minimal for customer support with email. I solved the problem. And the code quality is good, too.`, + postedAt: 'May 19, 2023 23:15:30', + }, + { + ...base(5), + category: 'Customer Support', + content: + 'Great UI kit, really beautiful as well. Also the customer support is very warm-hearted. However, I hope the components and themes can be provided as a separated project (package).', + postedAt: 'June 19, 2023 23:15:30', + }, + { + ...base(6), + category: 'Design Quality', + content: 'I would never have been able to create all these beautifull components myself!', + postedAt: 'July 19, 2023 23:15:30', + }, + { + ...base(7), + category: 'Code Quality', + content: + 'The quality of this template is excellent. However, as an individual, the cost of obtaining the TypeScript Source version is beyond my means. Despite my strong desire to acquire it, my limited personal budget does not allow me to do so.', + postedAt: 'August 19, 2023 23:15:30', + }, + { + ...base(8), + category: 'Customizability', + content: + 'The design and code quality are impressive. Regular updates and excellent customer support are major advantages.', + postedAt: 'September 19, 2023 23:15:30', + }, +]; diff --git a/front_minimal/src/sections/home/home-zone-ui.jsx b/front_minimal/src/sections/home/home-zone-ui.jsx new file mode 100644 index 0000000..5407f38 --- /dev/null +++ b/front_minimal/src/sections/home/home-zone-ui.jsx @@ -0,0 +1,140 @@ +import { m } from 'framer-motion'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Container from '@mui/material/Container'; +import Grid from '@mui/material/Unstable_Grid2'; + +import { paths } from 'src/routes/paths'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, stylesMode } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { varFade, MotionViewport } from 'src/components/animate'; + +import { SectionTitle } from './components/section-title'; +import { FloatLine, CircleSvg, FloatTriangleDownIcon } from './components/svg-elements'; + +// ---------------------------------------------------------------------- + +export function HomeZoneUI({ sx, ...other }) { + const renderLines = ( + <> + + + + + + + ); + + const renderDescription = ( + + ); + + const renderImg = ( + + `drop-shadow(0 24px 48px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.16)})`, + [stylesMode.dark]: { + filter: (theme) => + `drop-shadow(0 24px 48px ${varAlpha(theme.vars.palette.common.blackChannel, 0.16)})`, + }, + }} + > + `solid 2px ${theme.vars.palette.common.white}`, + }} + /> + + + + + + ); + + return ( + + + {renderLines} + + + + + {renderDescription} + + + + {renderImg} + + + + + + + + ); +} diff --git a/front_minimal/src/sections/home/view/home-view.jsx b/front_minimal/src/sections/home/view/home-view.jsx new file mode 100644 index 0000000..dfea790 --- /dev/null +++ b/front_minimal/src/sections/home/view/home-view.jsx @@ -0,0 +1,60 @@ +'use client'; + +import Stack from '@mui/material/Stack'; + +import { BackToTop } from 'src/components/animate/back-to-top'; +import { ScrollProgress, useScrollProgress } from 'src/components/animate/scroll-progress'; + +import { HomeHero } from '../home-hero'; +import { HomeFAQs } from '../home-faqs'; +import { HomeZoneUI } from '../home-zone-ui'; +import { HomeMinimal } from '../home-minimal'; +import { HomePricing } from '../home-pricing'; +import { HomeForDesigner } from '../home-for-designer'; +import { HomeTestimonials } from '../home-testimonials'; +import { HomeIntegrations } from '../home-integrations'; +import { HomeAdvertisement } from '../home-advertisement'; +import { HomeHugePackElements } from '../home-hugepack-elements'; +import { HomeHighlightFeatures } from '../home-highlight-features'; + +// ---------------------------------------------------------------------- + +export function HomeView() { + const pageProgress = useScrollProgress(); + + return ( + <> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/home/view/index.js b/front_minimal/src/sections/home/view/index.js new file mode 100644 index 0000000..6942855 --- /dev/null +++ b/front_minimal/src/sections/home/view/index.js @@ -0,0 +1 @@ +export * from './home-view'; diff --git a/front_minimal/src/sections/invoice/invoice-analytic.jsx b/front_minimal/src/sections/invoice/invoice-analytic.jsx new file mode 100644 index 0000000..d7ed68a --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-analytic.jsx @@ -0,0 +1,60 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Typography from '@mui/material/Typography'; +import CircularProgress from '@mui/material/CircularProgress'; + +import { fCurrency, fShortenNumber } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function InvoiceAnalytic({ title, total, icon, color, percent, price }) { + return ( + + + + + + + varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + }} + /> + + + + {title} + + + {fShortenNumber(total)} invoices + + + {fCurrency(price)} + + + ); +} diff --git a/front_minimal/src/sections/invoice/invoice-details.jsx b/front_minimal/src/sections/invoice/invoice-details.jsx new file mode 100644 index 0000000..f29baad --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-details.jsx @@ -0,0 +1,243 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Table from '@mui/material/Table'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import { styled } from '@mui/material/styles'; +import TableRow from '@mui/material/TableRow'; +import TableHead from '@mui/material/TableHead'; +import TableBody from '@mui/material/TableBody'; +import Typography from '@mui/material/Typography'; +import TableCell, { tableCellClasses } from '@mui/material/TableCell'; + +import { fDate } from 'src/utils/format-time'; +import { fCurrency } from 'src/utils/format-number'; + +import { INVOICE_STATUS_OPTIONS } from 'src/_mock'; + +import { Label } from 'src/components/label'; +import { Scrollbar } from 'src/components/scrollbar'; + +import { InvoiceToolbar } from './invoice-toolbar'; + +// ---------------------------------------------------------------------- + +const StyledTableRow = styled(TableRow)(({ theme }) => ({ + [`& .${tableCellClasses.root}`]: { + textAlign: 'right', + borderBottom: 'none', + paddingTop: theme.spacing(1), + paddingBottom: theme.spacing(1), + }, +})); + +// ---------------------------------------------------------------------- + +export function InvoiceDetails({ invoice }) { + const [currentStatus, setCurrentStatus] = useState(invoice?.status); + + const handleChangeStatus = useCallback((event) => { + setCurrentStatus(event.target.value); + }, []); + + const renderTotal = ( + <> + + + + + Subtotal + + + + {fCurrency(invoice?.subtotal)} + + + + + + Shipping + + - {fCurrency(invoice?.shipping)} + + + + + + Discount + + - {fCurrency(invoice?.discount)} + + + + + + Taxes + {fCurrency(invoice?.taxes)} + + + + + Total + + {fCurrency(invoice?.totalAmount)} + + + + ); + + const renderFooter = ( + +
    + + NOTES + + + We appreciate your business. Should you need us to add VAT or extra notes let us know! + +
    + + + + Have a question? + + support@minimals.cc + +
    + ); + + const renderList = ( + + + + + # + + Description + + Qty + + Unit price + + Total + + + + + {invoice?.items.map((row, index) => ( + + {index + 1} + + + + {row.title} + + + {row.description} + + + + + {row.quantity} + + {fCurrency(row.price)} + + {fCurrency(row.price * row.quantity)} + + ))} + + {renderTotal} + +
    +
    + ); + + return ( + <> + + + + + + + + + + {invoice?.invoiceNumber} + + + + + Invoice from + + {invoice?.invoiceFrom.name} +
    + {invoice?.invoiceFrom.fullAddress} +
    + Phone: {invoice?.invoiceFrom.phoneNumber} +
    +
    + + + + Invoice to + + {invoice?.invoiceTo.name} +
    + {invoice?.invoiceTo.fullAddress} +
    + Phone: {invoice?.invoiceTo.phoneNumber} +
    +
    + + + + Date create + + {fDate(invoice?.createDate)} + + + + + Due date + + {fDate(invoice?.dueDate)} + +
    + + {renderList} + + + + {renderFooter} +
    + + ); +} diff --git a/front_minimal/src/sections/invoice/invoice-new-edit-address.jsx b/front_minimal/src/sections/invoice/invoice-new-edit-address.jsx new file mode 100644 index 0000000..889c31f --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-new-edit-address.jsx @@ -0,0 +1,131 @@ +import { useFormContext } from 'react-hook-form'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useResponsive } from 'src/hooks/use-responsive'; + +import { _addressBooks } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; + +import { AddressListDialog } from '../address'; + +// ---------------------------------------------------------------------- + +export function InvoiceNewEditAddress() { + const { + watch, + setValue, + formState: { errors }, + } = useFormContext(); + + const mdUp = useResponsive('up', 'md'); + + const values = watch(); + + const { invoiceFrom, invoiceTo } = values; + + const from = useBoolean(); + + const to = useBoolean(); + + return ( + <> + + } + sx={{ p: 3 }} + > + + + + From: + + + + + + + + + {invoiceFrom.name} + {invoiceFrom.fullAddress} + {invoiceFrom.phoneNumber} + + + + + + + To: + + + + + + + + {invoiceTo ? ( + + {invoiceTo.name} + {invoiceTo.fullAddress} + {invoiceTo.phoneNumber} + + ) : ( + + {errors.invoiceTo?.message} + + )} + + + + invoiceFrom?.id === selectedId} + onSelect={(address) => setValue('invoiceFrom', address)} + list={_addressBooks} + action={ + + } + /> + + invoiceTo?.id === selectedId} + onSelect={(address) => setValue('invoiceTo', address)} + list={_addressBooks} + action={ + + } + /> + + ); +} diff --git a/front_minimal/src/sections/invoice/invoice-new-edit-details.jsx b/front_minimal/src/sections/invoice/invoice-new-edit-details.jsx new file mode 100644 index 0000000..eb7b2b4 --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-new-edit-details.jsx @@ -0,0 +1,305 @@ +import { useEffect, useCallback } from 'react'; +import { useFieldArray, useFormContext } from 'react-hook-form'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import MenuItem from '@mui/material/MenuItem'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; +import { inputBaseClasses } from '@mui/material/InputBase'; + +import { fCurrency } from 'src/utils/format-number'; + +import { INVOICE_SERVICE_OPTIONS } from 'src/_mock'; + +import { Field } from 'src/components/hook-form'; +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function InvoiceNewEditDetails() { + const { control, setValue, watch } = useFormContext(); + + const { fields, append, remove } = useFieldArray({ control, name: 'items' }); + + const values = watch(); + + const totalOnRow = values.items.map((item) => item.quantity * item.price); + + const subtotal = totalOnRow.reduce((acc, num) => acc + num, 0); + + const totalAmount = subtotal - values.discount - values.shipping + values.taxes; + + useEffect(() => { + setValue('totalAmount', totalAmount); + }, [setValue, totalAmount]); + + const handleAdd = () => { + append({ + title: '', + description: '', + service: '', + quantity: 1, + price: 0, + total: 0, + }); + }; + + const handleRemove = (index) => { + remove(index); + }; + + const handleClearService = useCallback( + (index) => { + setValue(`items[${index}].quantity`, 1); + setValue(`items[${index}].price`, 0); + setValue(`items[${index}].total`, 0); + }, + [setValue] + ); + + const handleSelectService = useCallback( + (index, option) => { + setValue( + `items[${index}].price`, + INVOICE_SERVICE_OPTIONS.find((service) => service.name === option)?.price + ); + setValue( + `items[${index}].total`, + values.items.map((item) => item.quantity * item.price)[index] + ); + }, + [setValue, values.items] + ); + + const handleChangeQuantity = useCallback( + (event, index) => { + setValue(`items[${index}].quantity`, Number(event.target.value)); + setValue( + `items[${index}].total`, + values.items.map((item) => item.quantity * item.price)[index] + ); + }, + [setValue, values.items] + ); + + const handleChangePrice = useCallback( + (event, index) => { + setValue(`items[${index}].price`, Number(event.target.value)); + setValue( + `items[${index}].total`, + values.items.map((item) => item.quantity * item.price)[index] + ); + }, + [setValue, values.items] + ); + + const renderTotal = ( + + + Subtotal + {fCurrency(subtotal) || '-'} + + + + Shipping + + {values.shipping ? `- ${fCurrency(values.shipping)}` : '-'} + + + + + Discount + + {values.discount ? `- ${fCurrency(values.discount)}` : '-'} + + + + + Taxes + {values.taxes ? fCurrency(values.taxes) : '-'} + + + +
    Total
    + {fCurrency(totalAmount) || '-'} +
    +
    + ); + + return ( + + + Details: + + + } spacing={3}> + {fields.map((item, index) => ( + + + + + + + + handleClearService(index)} + sx={{ fontStyle: 'italic', color: 'text.secondary' }} + > + None + + + + + {INVOICE_SERVICE_OPTIONS.map((service) => ( + handleSelectService(index, service.name)} + > + {service.name} + + ))} + + + handleChangeQuantity(event, index)} + InputLabelProps={{ shrink: true }} + sx={{ maxWidth: { md: 96 } }} + /> + + handleChangePrice(event, index)} + InputProps={{ + startAdornment: ( + + $ + + ), + }} + sx={{ maxWidth: { md: 96 } }} + /> + + handleChangePrice(event, index)} + InputProps={{ + startAdornment: ( + + $ + + ), + }} + sx={{ + maxWidth: { md: 104 }, + [`& .${inputBaseClasses.input}`]: { + textAlign: { md: 'right' }, + }, + }} + /> + + + + + ))} + + + + + + + + + + + + + + + + + {renderTotal} + + ); +} diff --git a/front_minimal/src/sections/invoice/invoice-new-edit-form.jsx b/front_minimal/src/sections/invoice/invoice-new-edit-form.jsx new file mode 100644 index 0000000..accd93c --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-new-edit-form.jsx @@ -0,0 +1,164 @@ +import { z as zod } from 'zod'; +import { useMemo } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { today, fIsAfter } from 'src/utils/format-time'; + +import { _addressBooks } from 'src/_mock'; + +import { Form, schemaHelper } from 'src/components/hook-form'; + +import { InvoiceNewEditDetails } from './invoice-new-edit-details'; +import { InvoiceNewEditAddress } from './invoice-new-edit-address'; +import { InvoiceNewEditStatusDate } from './invoice-new-edit-status-date'; + +export const NewInvoiceSchema = zod + .object({ + invoiceTo: zod.custom().refine((data) => data !== null, { message: 'Invoice to is required!' }), + createDate: schemaHelper.date({ message: { required_error: 'Create date is required!' } }), + dueDate: schemaHelper.date({ message: { required_error: 'Due date is required!' } }), + items: zod.array( + zod.object({ + title: zod.string().min(1, { message: 'Title is required!' }), + service: zod.string().min(1, { message: 'Service is required!' }), + quantity: zod.number().min(1, { message: 'Quantity must be more than 0' }), + // Not required + price: zod.number(), + total: zod.number(), + description: zod.string(), + }) + ), + // Not required + taxes: zod.number(), + status: zod.string(), + discount: zod.number(), + shipping: zod.number(), + totalAmount: zod.number(), + invoiceNumber: zod.string(), + invoiceFrom: zod.custom().nullable(), + }) + .refine((data) => !fIsAfter(data.createDate, data.dueDate), { + message: 'Due date cannot be earlier than create date!', + path: ['dueDate'], + }); + +// ---------------------------------------------------------------------- + +export function InvoiceNewEditForm({ currentInvoice }) { + const router = useRouter(); + + const loadingSave = useBoolean(); + + const loadingSend = useBoolean(); + + const defaultValues = useMemo( + () => ({ + invoiceNumber: currentInvoice?.invoiceNumber || 'INV-1990', + createDate: currentInvoice?.createDate || today(), + dueDate: currentInvoice?.dueDate || null, + taxes: currentInvoice?.taxes || 0, + shipping: currentInvoice?.shipping || 0, + status: currentInvoice?.status || 'draft', + discount: currentInvoice?.discount || 0, + invoiceFrom: currentInvoice?.invoiceFrom || _addressBooks[0], + invoiceTo: currentInvoice?.invoiceTo || null, + totalAmount: currentInvoice?.totalAmount || 0, + items: currentInvoice?.items || [ + { + title: '', + description: '', + service: '', + quantity: 1, + price: 0, + total: 0, + }, + ], + }), + [currentInvoice] + ); + + const methods = useForm({ + mode: 'all', + resolver: zodResolver(NewInvoiceSchema), + defaultValues, + }); + + const { + reset, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const handleSaveAsDraft = handleSubmit(async (data) => { + loadingSave.onTrue(); + + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + reset(); + loadingSave.onFalse(); + router.push(paths.dashboard.invoice.root); + console.info('DATA', JSON.stringify(data, null, 2)); + } catch (error) { + console.error(error); + loadingSave.onFalse(); + } + }); + + const handleCreateAndSend = handleSubmit(async (data) => { + loadingSend.onTrue(); + + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + reset(); + loadingSend.onFalse(); + router.push(paths.dashboard.invoice.root); + console.info('DATA', JSON.stringify(data, null, 2)); + } catch (error) { + console.error(error); + loadingSend.onFalse(); + } + }); + + return ( +
    + + + + + + + + + + + Save as draft + + + + {currentInvoice ? 'Update' : 'Create'} & send + + +
    + ); +} diff --git a/front_minimal/src/sections/invoice/invoice-new-edit-status-date.jsx b/front_minimal/src/sections/invoice/invoice-new-edit-status-date.jsx new file mode 100644 index 0000000..226b1a0 --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-new-edit-status-date.jsx @@ -0,0 +1,40 @@ +import { useFormContext } from 'react-hook-form'; + +import Stack from '@mui/material/Stack'; +import MenuItem from '@mui/material/MenuItem'; + +import { Field } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export function InvoiceNewEditStatusDate() { + const { watch } = useFormContext(); + + const values = watch(); + + return ( + + + + + {['paid', 'pending', 'overdue', 'draft'].map((option) => ( + + {option} + + ))} + + + + + + ); +} diff --git a/front_minimal/src/sections/invoice/invoice-pdf.jsx b/front_minimal/src/sections/invoice/invoice-pdf.jsx new file mode 100644 index 0000000..0ae49b0 --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-pdf.jsx @@ -0,0 +1,233 @@ +import { useMemo } from 'react'; +import { Page, View, Text, Font, Image, Document, StyleSheet } from '@react-pdf/renderer'; + +import { fDate } from 'src/utils/format-time'; +import { fCurrency } from 'src/utils/format-number'; + +// ---------------------------------------------------------------------- + +Font.register({ + family: 'Roboto', + fonts: [{ src: '/fonts/Roboto-Regular.ttf' }, { src: '/fonts/Roboto-Bold.ttf' }], +}); + +const useStyles = () => + useMemo( + () => + StyleSheet.create({ + // layout + page: { + fontSize: 9, + lineHeight: 1.6, + fontFamily: 'Roboto', + backgroundColor: '#FFFFFF', + padding: '40px 24px 120px 24px', + }, + footer: { + left: 0, + right: 0, + bottom: 0, + padding: 24, + margin: 'auto', + borderTopWidth: 1, + borderStyle: 'solid', + position: 'absolute', + borderColor: '#e9ecef', + }, + container: { + flexDirection: 'row', + justifyContent: 'space-between', + }, + // margin + mb4: { marginBottom: 4 }, + mb8: { marginBottom: 8 }, + mb40: { marginBottom: 40 }, + // text + h3: { fontSize: 16, fontWeight: 700 }, + h4: { fontSize: 13, fontWeight: 700 }, + body1: { fontSize: 10 }, + subtitle1: { fontSize: 10, fontWeight: 700 }, + body2: { fontSize: 9 }, + subtitle2: { fontSize: 9, fontWeight: 700 }, + // table + table: { display: 'flex', width: '100%' }, + row: { + padding: '10px 0 8px 0', + flexDirection: 'row', + borderBottomWidth: 1, + borderStyle: 'solid', + borderColor: '#e9ecef', + }, + cell_1: { width: '5%' }, + cell_2: { width: '50%' }, + cell_3: { width: '15%', paddingLeft: 32 }, + cell_4: { width: '15%', paddingLeft: 8 }, + cell_5: { width: '15%' }, + noBorder: { paddingTop: '10px', paddingBottom: 0, borderBottomWidth: 0 }, + }), + [] + ); + +// ---------------------------------------------------------------------- + +export function InvoicePDF({ invoice, currentStatus }) { + const { + items, + taxes, + dueDate, + discount, + shipping, + subtotal, + invoiceTo, + createDate, + totalAmount, + invoiceFrom, + invoiceNumber, + } = invoice; + + const styles = useStyles(); + + const renderHeader = ( + + + + + {currentStatus} + {invoiceNumber} + + + ); + + const renderFooter = ( + + + NOTES + + We appreciate your business. Should you need us to add VAT or extra notes let us know! + + + + Have a question? + support@abcapp.com + + + ); + + const renderInfo = ( + + + Invoice from + {invoiceFrom.name} + {invoiceFrom.fullAddress} + {invoiceFrom.phoneNumber} + + + + Invoice to + {invoiceTo.name} + {invoiceTo.fullAddress} + {invoiceTo.phoneNumber} + + + ); + + const renderTime = ( + + + Date create + {fDate(createDate)} + + + Due date + {fDate(dueDate)} + + + ); + + const renderTable = ( + <> + Invoice details + + + + + + # + + + Description + + + Qty + + + Unit price + + + Total + + + + + + {items.map((item, index) => ( + + + {index + 1} + + + {item.title} + {item.description} + + + {item.quantity} + + + {item.price} + + + {fCurrency(item.price * item.quantity)} + + + ))} + + {[ + { name: 'Subtotal', value: subtotal }, + { name: 'Shipping', value: -shipping }, + { name: 'Discount', value: -discount }, + { name: 'Taxes', value: taxes }, + { name: 'Total', value: totalAmount, styles: styles.h4 }, + ].map((item) => ( + + + + + + {item.name} + + + {fCurrency(item.value)} + + + ))} + + + + ); + + return ( + + + {renderHeader} + + {renderInfo} + + {renderTime} + + {renderTable} + + {renderFooter} + + + ); +} diff --git a/front_minimal/src/sections/invoice/invoice-table-filters-result.jsx b/front_minimal/src/sections/invoice/invoice-table-filters-result.jsx new file mode 100644 index 0000000..2e61731 --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-table-filters-result.jsx @@ -0,0 +1,70 @@ +import { useCallback } from 'react'; + +import Chip from '@mui/material/Chip'; + +import { fDateRangeShortLabel } from 'src/utils/format-time'; + +import { chipProps, FiltersBlock, FiltersResult } from 'src/components/filters-result'; + +// ---------------------------------------------------------------------- + +export function InvoiceTableFiltersResult({ filters, totalResults, onResetPage, sx }) { + const handleRemoveKeyword = useCallback(() => { + onResetPage(); + filters.setState({ name: '' }); + }, [filters, onResetPage]); + + const handleRemoveService = useCallback( + (inputValue) => { + const newValue = filters.state.service.filter((item) => item !== inputValue); + + onResetPage(); + filters.setState({ service: newValue }); + }, + [filters, onResetPage] + ); + + const handleRemoveStatus = useCallback(() => { + onResetPage(); + filters.setState({ status: 'all' }); + }, [filters, onResetPage]); + + const handleRemoveDate = useCallback(() => { + onResetPage(); + filters.setState({ startDate: null, endDate: null }); + }, [filters, onResetPage]); + + return ( + + + {filters.state.service.map((item) => ( + handleRemoveService(item)} /> + ))} + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/invoice/invoice-table-row.jsx b/front_minimal/src/sections/invoice/invoice-table-row.jsx new file mode 100644 index 0000000..b99da0e --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-table-row.jsx @@ -0,0 +1,166 @@ +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import TableRow from '@mui/material/TableRow'; +import Checkbox from '@mui/material/Checkbox'; +import TableCell from '@mui/material/TableCell'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { fCurrency } from 'src/utils/format-number'; +import { fDate, fTime } from 'src/utils/format-time'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function InvoiceTableRow({ row, selected, onSelectRow, onViewRow, onEditRow, onDeleteRow }) { + const confirm = useBoolean(); + + const popover = usePopover(); + + return ( + <> + + + + + + + + {row.invoiceTo.name.charAt(0).toUpperCase()} + + + {row.invoiceTo.name} + + } + secondary={ + + {row.invoiceNumber} + + } + /> + + + + + + + + + + + + {fCurrency(row.totalAmount)} + + {row.sent} + + + + + + + + + + + + + + + { + onViewRow(); + popover.onClose(); + }} + > + + View + + + { + onEditRow(); + popover.onClose(); + }} + > + + Edit + + + + + { + confirm.onTrue(); + popover.onClose(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + + Delete + + } + /> + + ); +} diff --git a/front_minimal/src/sections/invoice/invoice-table-toolbar.jsx b/front_minimal/src/sections/invoice/invoice-table-toolbar.jsx new file mode 100644 index 0000000..1a4c556 --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-table-toolbar.jsx @@ -0,0 +1,181 @@ +import { useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Select from '@mui/material/Select'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import Checkbox from '@mui/material/Checkbox'; +import TextField from '@mui/material/TextField'; +import InputLabel from '@mui/material/InputLabel'; +import IconButton from '@mui/material/IconButton'; +import FormControl from '@mui/material/FormControl'; +import OutlinedInput from '@mui/material/OutlinedInput'; +import InputAdornment from '@mui/material/InputAdornment'; +import { DatePicker } from '@mui/x-date-pickers/DatePicker'; +import { formHelperTextClasses } from '@mui/material/FormHelperText'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function InvoiceTableToolbar({ filters, options, dateError, onResetPage }) { + const popover = usePopover(); + + const handleFilterName = useCallback( + (event) => { + onResetPage(); + filters.setState({ name: event.target.value }); + }, + [filters, onResetPage] + ); + + const handleFilterService = useCallback( + (event) => { + const newValue = + typeof event.target.value === 'string' ? event.target.value.split(',') : event.target.value; + + onResetPage(); + filters.setState({ service: newValue }); + }, + [filters, onResetPage] + ); + + const handleFilterStartDate = useCallback( + (newValue) => { + onResetPage(); + filters.setState({ startDate: newValue }); + }, + [filters, onResetPage] + ); + + const handleFilterEndDate = useCallback( + (newValue) => { + onResetPage(); + filters.setState({ endDate: newValue }); + }, + [filters, onResetPage] + ); + + return ( + <> + + + Service + + + + + + + + + + + + + ), + }} + /> + + + + + + + + + + + { + popover.onClose(); + }} + > + + Print + + + { + popover.onClose(); + }} + > + + Import + + + { + popover.onClose(); + }} + > + + Export + + + + + + ); +} diff --git a/front_minimal/src/sections/invoice/invoice-toolbar.jsx b/front_minimal/src/sections/invoice/invoice-toolbar.jsx new file mode 100644 index 0000000..0919c93 --- /dev/null +++ b/front_minimal/src/sections/invoice/invoice-toolbar.jsx @@ -0,0 +1,137 @@ +import { useCallback } from 'react'; +import { PDFViewer, PDFDownloadLink } from '@react-pdf/renderer'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import NoSsr from '@mui/material/NoSsr'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import Tooltip from '@mui/material/Tooltip'; +import MenuItem from '@mui/material/MenuItem'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import DialogActions from '@mui/material/DialogActions'; +import CircularProgress from '@mui/material/CircularProgress'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; + +import { InvoicePDF } from './invoice-pdf'; + +// ---------------------------------------------------------------------- + +export function InvoiceToolbar({ invoice, currentStatus, statusOptions, onChangeStatus }) { + const router = useRouter(); + + const view = useBoolean(); + + const handleEdit = useCallback(() => { + router.push(paths.dashboard.invoice.edit(`${invoice?.id}`)); + }, [invoice?.id, router]); + + const renderDownload = ( + + : + } + fileName={invoice?.invoiceNumber} + style={{ textDecoration: 'none' }} + > + {({ loading }) => ( + + + {loading ? ( + + ) : ( + + )} + + + )} + + + ); + + return ( + <> + + + + + + + + + + + + + + + {renderDownload} + + + + + + + + + + + + + + + + + + + + + + {statusOptions.map((option) => ( + + {option.label} + + ))} + + + + + + + + + + + + {invoice && } + + + + + + ); +} diff --git a/front_minimal/src/sections/invoice/view/index.js b/front_minimal/src/sections/invoice/view/index.js new file mode 100644 index 0000000..b1006bf --- /dev/null +++ b/front_minimal/src/sections/invoice/view/index.js @@ -0,0 +1,7 @@ +export * from './invoice-list-view'; + +export * from './invoice-edit-view'; + +export * from './invoice-create-view'; + +export * from './invoice-details-view'; diff --git a/front_minimal/src/sections/invoice/view/invoice-create-view.jsx b/front_minimal/src/sections/invoice/view/invoice-create-view.jsx new file mode 100644 index 0000000..79f79d1 --- /dev/null +++ b/front_minimal/src/sections/invoice/view/invoice-create-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { InvoiceNewEditForm } from '../invoice-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function InvoiceCreateView() { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/invoice/view/invoice-details-view.jsx b/front_minimal/src/sections/invoice/view/invoice-details-view.jsx new file mode 100644 index 0000000..78f447d --- /dev/null +++ b/front_minimal/src/sections/invoice/view/invoice-details-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { InvoiceDetails } from '../invoice-details'; + +// ---------------------------------------------------------------------- + +export function InvoiceDetailsView({ invoice }) { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/invoice/view/invoice-edit-view.jsx b/front_minimal/src/sections/invoice/view/invoice-edit-view.jsx new file mode 100644 index 0000000..333f99f --- /dev/null +++ b/front_minimal/src/sections/invoice/view/invoice-edit-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { InvoiceNewEditForm } from '../invoice-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function InvoiceEditView({ invoice }) { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/invoice/view/invoice-list-view.jsx b/front_minimal/src/sections/invoice/view/invoice-list-view.jsx new file mode 100644 index 0000000..9d70298 --- /dev/null +++ b/front_minimal/src/sections/invoice/view/invoice-list-view.jsx @@ -0,0 +1,484 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Tab from '@mui/material/Tab'; +import Tabs from '@mui/material/Tabs'; +import Card from '@mui/material/Card'; +import Table from '@mui/material/Table'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import Tooltip from '@mui/material/Tooltip'; +import TableBody from '@mui/material/TableBody'; +import { useTheme } from '@mui/material/styles'; +import IconButton from '@mui/material/IconButton'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useSetState } from 'src/hooks/use-set-state'; + +import { sumBy } from 'src/utils/helper'; +import { fIsAfter, fIsBetween } from 'src/utils/format-time'; + +import { varAlpha } from 'src/theme/styles'; +import { DashboardContent } from 'src/layouts/dashboard'; +import { _invoices, INVOICE_SERVICE_OPTIONS } from 'src/_mock'; + +import { Label } from 'src/components/label'; +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; +import { + useTable, + emptyRows, + rowInPage, + TableNoData, + getComparator, + TableEmptyRows, + TableHeadCustom, + TableSelectedAction, + TablePaginationCustom, +} from 'src/components/table'; + +import { InvoiceAnalytic } from '../invoice-analytic'; +import { InvoiceTableRow } from '../invoice-table-row'; +import { InvoiceTableToolbar } from '../invoice-table-toolbar'; +import { InvoiceTableFiltersResult } from '../invoice-table-filters-result'; + +// ---------------------------------------------------------------------- + +const TABLE_HEAD = [ + { id: 'invoiceNumber', label: 'Customer' }, + { id: 'createDate', label: 'Create' }, + { id: 'dueDate', label: 'Due' }, + { id: 'price', label: 'Amount' }, + { id: 'sent', label: 'Sent', align: 'center' }, + { id: 'status', label: 'Status' }, + { id: '' }, +]; + +// ---------------------------------------------------------------------- + +export function InvoiceListView() { + const theme = useTheme(); + + const router = useRouter(); + + const table = useTable({ defaultOrderBy: 'createDate' }); + + const confirm = useBoolean(); + + const [tableData, setTableData] = useState(_invoices); + + const filters = useSetState({ + name: '', + service: [], + status: 'all', + startDate: null, + endDate: null, + }); + + const dateError = fIsAfter(filters.state.startDate, filters.state.endDate); + + const dataFiltered = applyFilter({ + inputData: tableData, + comparator: getComparator(table.order, table.orderBy), + filters: filters.state, + dateError, + }); + + const dataInPage = rowInPage(dataFiltered, table.page, table.rowsPerPage); + + const canReset = + !!filters.state.name || + filters.state.service.length > 0 || + filters.state.status !== 'all' || + (!!filters.state.startDate && !!filters.state.endDate); + + const notFound = (!dataFiltered.length && canReset) || !dataFiltered.length; + + const getInvoiceLength = (status) => tableData.filter((item) => item.status === status).length; + + const getTotalAmount = (status) => + sumBy( + tableData.filter((item) => item.status === status), + (invoice) => invoice.totalAmount + ); + + const getPercentByStatus = (status) => (getInvoiceLength(status) / tableData.length) * 100; + + const TABS = [ + { + value: 'all', + label: 'All', + color: 'default', + count: tableData.length, + }, + { + value: 'paid', + label: 'Paid', + color: 'success', + count: getInvoiceLength('paid'), + }, + { + value: 'pending', + label: 'Pending', + color: 'warning', + count: getInvoiceLength('pending'), + }, + { + value: 'overdue', + label: 'Overdue', + color: 'error', + count: getInvoiceLength('overdue'), + }, + { + value: 'draft', + label: 'Draft', + color: 'default', + count: getInvoiceLength('draft'), + }, + ]; + + const handleDeleteRow = useCallback( + (id) => { + const deleteRow = tableData.filter((row) => row.id !== id); + + toast.success('Delete success!'); + + setTableData(deleteRow); + + table.onUpdatePageDeleteRow(dataInPage.length); + }, + [dataInPage.length, table, tableData] + ); + + const handleDeleteRows = useCallback(() => { + const deleteRows = tableData.filter((row) => !table.selected.includes(row.id)); + + toast.success('Delete success!'); + + setTableData(deleteRows); + + table.onUpdatePageDeleteRows({ + totalRowsInPage: dataInPage.length, + totalRowsFiltered: dataFiltered.length, + }); + }, [dataFiltered.length, dataInPage.length, table, tableData]); + + const handleEditRow = useCallback( + (id) => { + router.push(paths.dashboard.invoice.edit(id)); + }, + [router] + ); + + const handleViewRow = useCallback( + (id) => { + router.push(paths.dashboard.invoice.details(id)); + }, + [router] + ); + + const handleFilterStatus = useCallback( + (event, newValue) => { + table.onResetPage(); + filters.setState({ status: newValue }); + }, + [filters, table] + ); + + return ( + <> + + } + > + New invoice + + } + sx={{ mb: { xs: 3, md: 5 } }} + /> + + + + } + sx={{ py: 2 }} + > + invoice.totalAmount)} + icon="solar:bill-list-bold-duotone" + color={theme.vars.palette.info.main} + /> + + + + + + + + + + + + + + + {TABS.map((tab) => ( + + {tab.count} + + } + /> + ))} + + + option.name) }} + /> + + {canReset && ( + + )} + + + { + table.onSelectAllRows( + checked, + dataFiltered.map((row) => row.id) + ); + }} + action={ + + + + + + + + + + + + + + + + + + + + + + + + + + } + /> + + + + + table.onSelectAllRows( + checked, + dataFiltered.map((row) => row.id) + ) + } + /> + + + {dataFiltered + .slice( + table.page * table.rowsPerPage, + table.page * table.rowsPerPage + table.rowsPerPage + ) + .map((row) => ( + table.onSelectRow(row.id)} + onViewRow={() => handleViewRow(row.id)} + onEditRow={() => handleEditRow(row.id)} + onDeleteRow={() => handleDeleteRow(row.id)} + /> + ))} + + + + + +
    +
    +
    + + +
    +
    + + + Are you sure want to delete {table.selected.length} items? + + } + action={ + + } + /> + + ); +} + +function applyFilter({ inputData, comparator, filters, dateError }) { + const { name, status, service, startDate, endDate } = filters; + + const stabilizedThis = inputData.map((el, index) => [el, index]); + + stabilizedThis.sort((a, b) => { + const order = comparator(a[0], b[0]); + if (order !== 0) return order; + return a[1] - b[1]; + }); + + inputData = stabilizedThis.map((el) => el[0]); + + if (name) { + inputData = inputData.filter( + (invoice) => + invoice.invoiceNumber.toLowerCase().indexOf(name.toLowerCase()) !== -1 || + invoice.invoiceTo.name.toLowerCase().indexOf(name.toLowerCase()) !== -1 + ); + } + + if (status !== 'all') { + inputData = inputData.filter((invoice) => invoice.status === status); + } + + if (service.length) { + inputData = inputData.filter((invoice) => + invoice.items.some((filterItem) => service.includes(filterItem.service)) + ); + } + + if (!dateError) { + if (startDate && endDate) { + inputData = inputData.filter((invoice) => fIsBetween(invoice.createDate, startDate, endDate)); + } + } + + return inputData; +} diff --git a/front_minimal/src/sections/job/job-details-candidates.jsx b/front_minimal/src/sections/job/job-details-candidates.jsx new file mode 100644 index 0000000..a8dfea8 --- /dev/null +++ b/front_minimal/src/sections/job/job-details-candidates.jsx @@ -0,0 +1,112 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Tooltip from '@mui/material/Tooltip'; +import Pagination from '@mui/material/Pagination'; +import IconButton from '@mui/material/IconButton'; +import ListItemText from '@mui/material/ListItemText'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function JobDetailsCandidates({ candidates }) { + return ( + <> + + {candidates.map((candidate) => ( + + + + + + + + + + + + varAlpha(theme.vars.palette.error.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.error.mainChannel, 0.16), + }, + }} + > + + + + varAlpha(theme.vars.palette.info.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.info.mainChannel, 0.16), + }, + }} + > + + + + varAlpha(theme.vars.palette.primary.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.primary.mainChannel, 0.16), + }, + }} + > + + + + + varAlpha(theme.vars.palette.secondary.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => + varAlpha(theme.vars.palette.secondary.mainChannel, 0.16), + }, + }} + > + + + + + + + ))} + + + + + ); +} diff --git a/front_minimal/src/sections/job/job-details-content.jsx b/front_minimal/src/sections/job/job-details-content.jsx new file mode 100644 index 0000000..cb34de3 --- /dev/null +++ b/front_minimal/src/sections/job/job-details-content.jsx @@ -0,0 +1,121 @@ +import Chip from '@mui/material/Chip'; +import Card from '@mui/material/Card'; +import Paper from '@mui/material/Paper'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Grid from '@mui/material/Unstable_Grid2'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { fDate } from 'src/utils/format-time'; +import { fCurrency } from 'src/utils/format-number'; + +import { Iconify } from 'src/components/iconify'; +import { Markdown } from 'src/components/markdown'; + +// ---------------------------------------------------------------------- + +export function JobDetailsContent({ job }) { + const renderContent = ( + + {job?.title} + + + + + Skills + + {job?.skills.map((skill) => ( + + ))} + + + + + Benefits + + {job?.benefits.map((benefit) => ( + + ))} + + + + ); + + const renderOverview = ( + + {[ + { + label: 'Date posted', + value: fDate(job?.createdAt), + icon: , + }, + { + label: 'Expiration date', + value: fDate(job?.expiredDate), + icon: , + }, + { + label: 'Employment type', + value: job?.employmentTypes, + icon: , + }, + { + label: 'Offered salary', + value: job?.salary.negotiable ? 'Negotiable' : fCurrency(job?.salary.price), + icon: , + }, + { + label: 'Experience', + value: job?.experience, + icon: , + }, + ].map((item) => ( + + {item.icon} + + + ))} + + ); + + const renderCompany = ( + + + + + {job?.company.name} + {job?.company.fullAddress} + {job?.company.phoneNumber} + + + ); + + return ( + + + {renderContent} + + + + {renderOverview} + + {renderCompany} + + + ); +} diff --git a/front_minimal/src/sections/job/job-details-toolbar.jsx b/front_minimal/src/sections/job/job-details-toolbar.jsx new file mode 100644 index 0000000..2bc980b --- /dev/null +++ b/front_minimal/src/sections/job/job-details-toolbar.jsx @@ -0,0 +1,89 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Tooltip from '@mui/material/Tooltip'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { RouterLink } from 'src/routes/components'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function JobDetailsToolbar({ + publish, + backLink, + editLink, + liveLink, + publishOptions, + onChangePublish, + sx, + ...other +}) { + const popover = usePopover(); + + return ( + <> + + + + + + {publish === 'published' && ( + + + + + + )} + + + + + + + + } + onClick={popover.onOpen} + sx={{ textTransform: 'capitalize' }} + > + {publish} + + + + + + {publishOptions.map((option) => ( + { + popover.onClose(); + onChangePublish(option.value); + }} + > + {option.value === 'published' && } + {option.value === 'draft' && } + {option.label} + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/job/job-filters-result.jsx b/front_minimal/src/sections/job/job-filters-result.jsx new file mode 100644 index 0000000..d338f15 --- /dev/null +++ b/front_minimal/src/sections/job/job-filters-result.jsx @@ -0,0 +1,78 @@ +import Chip from '@mui/material/Chip'; + +import { chipProps, FiltersBlock, FiltersResult } from 'src/components/filters-result'; + +// ---------------------------------------------------------------------- + +export function JobFiltersResult({ filters, totalResults, sx }) { + const handleRemoveEmploymentTypes = (inputValue) => { + const newValue = filters.state.employmentTypes.filter((item) => item !== inputValue); + filters.setState({ employmentTypes: newValue }); + }; + + const handleRemoveExperience = () => { + filters.setState({ experience: 'all' }); + }; + + const handleRemoveRoles = (inputValue) => { + const newValue = filters.state.roles.filter((item) => item !== inputValue); + filters.setState({ roles: newValue }); + }; + + const handleRemoveLocations = (inputValue) => { + const newValue = filters.state.locations.filter((item) => item !== inputValue); + filters.setState({ locations: newValue }); + }; + + const handleRemoveBenefits = (inputValue) => { + const newValue = filters.state.benefits.filter((item) => item !== inputValue); + filters.setState({ benefits: newValue }); + }; + + return ( + + + {filters.state.employmentTypes.map((item) => ( + handleRemoveEmploymentTypes(item)} + /> + ))} + + + + + + + + {filters.state.roles.map((item) => ( + handleRemoveRoles(item)} /> + ))} + + + + {filters.state.locations.map((item) => ( + handleRemoveLocations(item)} + /> + ))} + + + + {filters.state.benefits.map((item) => ( + handleRemoveBenefits(item)} + /> + ))} + + + ); +} diff --git a/front_minimal/src/sections/job/job-filters.jsx b/front_minimal/src/sections/job/job-filters.jsx new file mode 100644 index 0000000..07475bb --- /dev/null +++ b/front_minimal/src/sections/job/job-filters.jsx @@ -0,0 +1,240 @@ +import { useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Chip from '@mui/material/Chip'; +import Radio from '@mui/material/Radio'; +import Stack from '@mui/material/Stack'; +import Badge from '@mui/material/Badge'; +import Drawer from '@mui/material/Drawer'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import Tooltip from '@mui/material/Tooltip'; +import Checkbox from '@mui/material/Checkbox'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import Autocomplete from '@mui/material/Autocomplete'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { CountrySelect } from 'src/components/country-select'; + +// ---------------------------------------------------------------------- + +export function JobFilters({ open, canReset, onOpen, onClose, filters, options }) { + const handleFilterEmploymentTypes = useCallback( + (newValue) => { + const checked = filters.state.employmentTypes.includes(newValue) + ? filters.state.employmentTypes.filter((value) => value !== newValue) + : [...filters.state.employmentTypes, newValue]; + + filters.setState({ employmentTypes: checked }); + }, + [filters] + ); + + const handleFilterExperience = useCallback( + (newValue) => { + filters.setState({ experience: newValue }); + }, + [filters] + ); + + const handleFilterRoles = useCallback( + (newValue) => { + filters.setState({ roles: newValue }); + }, + [filters] + ); + + const handleFilterLocations = useCallback( + (newValue) => { + filters.setState({ locations: newValue }); + }, + [filters] + ); + + const handleFilterBenefits = useCallback( + (newValue) => { + const checked = filters.state.benefits.includes(newValue) + ? filters.state.benefits.filter((value) => value !== newValue) + : [...filters.state.benefits, newValue]; + + filters.setState({ benefits: checked }); + }, + [filters] + ); + + const renderHead = ( + <> + + + Filters + + + + + + + + + + + + + + + + + + ); + + const renderEmploymentTypes = ( + + + Employment types + + {options.employmentTypes.map((option) => ( + handleFilterEmploymentTypes(option)} + /> + } + label={option} + /> + ))} + + ); + + const renderExperience = ( + + + Experience + + {options.experiences.map((option) => ( + handleFilterExperience(option)} + /> + } + label={option} + sx={{ ...(option === 'all' && { textTransform: 'capitalize' }) }} + /> + ))} + + ); + + const renderRoles = ( + + + Roles + + option)} + getOptionLabel={(option) => option} + value={filters.state.roles} + onChange={(event, newValue) => handleFilterRoles(newValue)} + renderInput={(params) => } + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + /> +
    + ); + + const renderLocations = ( + + + Locations + + + handleFilterLocations(newValue)} + /> + + ); + + const renderBenefits = ( + + + Benefits + + {options.benefits.map((option) => ( + handleFilterBenefits(option)} + /> + } + label={option} + /> + ))} + + ); + + return ( + <> + + + + {renderHead} + + + + {renderEmploymentTypes} + {renderExperience} + {renderRoles} + {renderLocations} + {renderBenefits} + + + + + ); +} diff --git a/front_minimal/src/sections/job/job-item.jsx b/front_minimal/src/sections/job/job-item.jsx new file mode 100644 index 0000000..2fcfbd0 --- /dev/null +++ b/front_minimal/src/sections/job/job-item.jsx @@ -0,0 +1,153 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { fDate } from 'src/utils/format-time'; +import { fCurrency } from 'src/utils/format-number'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function JobItem({ job, onView, onEdit, onDelete }) { + const popover = usePopover(); + + return ( + <> + + + + + + + + + + {job.title} + + } + secondary={`Posted date: ${fDate(job.createdAt)}`} + primaryTypographyProps={{ typography: 'subtitle1' }} + secondaryTypographyProps={{ + mt: 1, + component: 'span', + typography: 'caption', + color: 'text.disabled', + }} + /> + + + + {job.candidates.length} candidates + + + + + + + {[ + { + label: job.experience, + icon: , + }, + { + label: job.employmentTypes.join(', '), + icon: , + }, + { + label: job.salary.negotiable ? 'Negotiable' : fCurrency(job.salary.price), + icon: , + }, + { + label: job.role, + icon: , + }, + ].map((item) => ( + + {item.icon} + + {item.label} + + + ))} + + + + + + { + popover.onClose(); + onView(); + }} + > + + View + + + { + popover.onClose(); + onEdit(); + }} + > + + Edit + + + { + popover.onClose(); + onDelete(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + ); +} diff --git a/front_minimal/src/sections/job/job-list.jsx b/front_minimal/src/sections/job/job-list.jsx new file mode 100644 index 0000000..9baaea0 --- /dev/null +++ b/front_minimal/src/sections/job/job-list.jsx @@ -0,0 +1,63 @@ +import { useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Pagination, { paginationClasses } from '@mui/material/Pagination'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { JobItem } from './job-item'; + +// ---------------------------------------------------------------------- + +export function JobList({ jobs }) { + const router = useRouter(); + + const handleView = useCallback( + (id) => { + router.push(paths.dashboard.job.details(id)); + }, + [router] + ); + + const handleEdit = useCallback( + (id) => { + router.push(paths.dashboard.job.edit(id)); + }, + [router] + ); + + const handleDelete = useCallback((id) => { + console.info('DELETE', id); + }, []); + + return ( + <> + + {jobs.map((job) => ( + handleView(job.id)} + onEdit={() => handleEdit(job.id)} + onDelete={() => handleDelete(job.id)} + /> + ))} + + + {jobs.length > 8 && ( + + )} + + ); +} diff --git a/front_minimal/src/sections/job/job-new-edit-form.jsx b/front_minimal/src/sections/job/job-new-edit-form.jsx new file mode 100644 index 0000000..f1f292b --- /dev/null +++ b/front_minimal/src/sections/job/job-new-edit-form.jsx @@ -0,0 +1,352 @@ +import { z as zod } from 'zod'; +import { useMemo, useEffect } from 'react'; +import { zodResolver } from '@hookform/resolvers/zod'; +import { useForm, Controller } from 'react-hook-form'; + +import Box from '@mui/material/Box'; +import Chip from '@mui/material/Chip'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Paper from '@mui/material/Paper'; +import Switch from '@mui/material/Switch'; +import Divider from '@mui/material/Divider'; +import ButtonBase from '@mui/material/ButtonBase'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { + _roles, + JOB_SKILL_OPTIONS, + JOB_BENEFIT_OPTIONS, + JOB_EXPERIENCE_OPTIONS, + JOB_EMPLOYMENT_TYPE_OPTIONS, + JOB_WORKING_SCHEDULE_OPTIONS, +} from 'src/_mock'; + +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { Form, Field, schemaHelper } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const NewJobSchema = zod.object({ + title: zod.string().min(1, { message: 'Title is required!' }), + content: zod.string().min(1, { message: 'Content is required!' }), + employmentTypes: zod.string().array().nonempty({ message: 'Choose at least one option!' }), + role: schemaHelper.objectOrNull({ + message: { required_error: 'Role is required!' }, + }), + skills: zod.string().array().nonempty({ message: 'Choose at least one option!' }), + workingSchedule: zod.string().array().nonempty({ message: 'Choose at least one option!' }), + locations: zod.string().array().nonempty({ message: 'Choose at least one option!' }), + expiredDate: schemaHelper.date({ + message: { required_error: 'Expired date is required!' }, + }), + salary: zod.object({ + price: zod.number().min(1, { message: 'Price is required!' }), + // Not required + type: zod.string(), + negotiable: zod.boolean(), + }), + benefits: zod.string().array().nonempty({ message: 'Choose at least one option!' }), + // Not required + experience: zod.string(), +}); + +export function JobNewEditForm({ currentJob }) { + const router = useRouter(); + + const defaultValues = useMemo( + () => ({ + title: currentJob?.title || '', + content: currentJob?.content || '', + employmentTypes: currentJob?.employmentTypes || [], + experience: currentJob?.experience || '1 year exp', + role: currentJob?.role || _roles[1], + skills: currentJob?.skills || [], + workingSchedule: currentJob?.workingSchedule || [], + locations: currentJob?.locations || [], + expiredDate: currentJob?.expiredDate || null, + salary: currentJob?.salary || { + type: 'Hourly', + price: 0, + negotiable: false, + }, + benefits: currentJob?.benefits || [], + }), + [currentJob] + ); + + const methods = useForm({ + mode: 'all', + resolver: zodResolver(NewJobSchema), + defaultValues, + }); + + const { + reset, + control, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + useEffect(() => { + if (currentJob) { + reset(defaultValues); + } + }, [currentJob, defaultValues, reset]); + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + reset(); + toast.success(currentJob ? 'Update success!' : 'Create success!'); + router.push(paths.dashboard.job.root); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const renderDetails = ( + + + + + + + + Title + + + + + Content + + + + + ); + + const renderProperties = ( + + + + + + + + Employment type + + + + + Experience + + + + + Role + option)} + getOptionLabel={(option) => option} + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + /> +
    + + + Skills + option)} + getOptionLabel={(option) => option} + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + /> +
    + + + Working schedule + option)} + getOptionLabel={(option) => option} + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + /> +
    + + + Locations + + + + + Expired + + + + + + Salary + + ( + + {[ + { + label: 'Hourly', + icon: , + }, + { + label: 'Custom', + icon: , + }, + ].map((item) => ( + field.onChange(item.label)} + sx={{ + p: 2.5, + borderRadius: 1, + typography: 'subtitle2', + flexDirection: 'column', + ...(item.label === field.value && { + borderWidth: 2, + borderColor: 'text.primary', + }), + }} + > + {item.icon} + {item.label} + + ))} + + )} + /> + + + $ + + ), + }} + /> + + + + + Benefits + + +
    +
    + ); + + const renderActions = ( + + } + label="Publish" + sx={{ flexGrow: 1, pl: 3 }} + /> + + + {!currentJob ? 'Create job' : 'Save changes'} + + + ); + + return ( +
    + + {renderDetails} + + {renderProperties} + + {renderActions} + +
    + ); +} diff --git a/front_minimal/src/sections/job/job-search.jsx b/front_minimal/src/sections/job/job-search.jsx new file mode 100644 index 0000000..2de4717 --- /dev/null +++ b/front_minimal/src/sections/job/job-search.jsx @@ -0,0 +1,88 @@ +import parse from 'autosuggest-highlight/parse'; +import match from 'autosuggest-highlight/match'; + +import Box from '@mui/material/Box'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import Autocomplete from '@mui/material/Autocomplete'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { Iconify } from 'src/components/iconify'; +import { SearchNotFound } from 'src/components/search-not-found'; + +// ---------------------------------------------------------------------- + +export function JobSearch({ search, onSearch }) { + const router = useRouter(); + + const handleClick = (id) => { + router.push(paths.dashboard.job.details(id)); + }; + + const handleKeyUp = (event) => { + if (search.state.query) { + if (event.key === 'Enter') { + const selectProduct = search.state.results.filter( + (job) => job.title === search.state.query + )[0]; + + handleClick(selectProduct.id); + } + } + }; + + return ( + onSearch(newValue)} + getOptionLabel={(option) => option.title} + noOptionsText={} + isOptionEqualToValue={(option, value) => option.id === value.id} + renderInput={(params) => ( + + + + ), + }} + /> + )} + renderOption={(props, job, { inputValue }) => { + const matches = match(job.title, inputValue); + const parts = parse(job.title, matches); + + return ( + handleClick(job.id)} key={job.id}> +
    + {parts.map((part, index) => ( + + {part.text} + + ))} +
    +
    + ); + }} + /> + ); +} diff --git a/front_minimal/src/sections/job/job-sort.jsx b/front_minimal/src/sections/job/job-sort.jsx new file mode 100644 index 0000000..937d999 --- /dev/null +++ b/front_minimal/src/sections/job/job-sort.jsx @@ -0,0 +1,54 @@ +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function JobSort({ sort, onSort, sortOptions }) { + const popover = usePopover(); + + return ( + <> + + + + + {sortOptions.map((option) => ( + { + popover.onClose(); + onSort(option.value); + }} + > + {option.label} + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/job/view/index.js b/front_minimal/src/sections/job/view/index.js new file mode 100644 index 0000000..1f96715 --- /dev/null +++ b/front_minimal/src/sections/job/view/index.js @@ -0,0 +1,7 @@ +export * from './job-list-view'; + +export * from './job-edit-view'; + +export * from './job-create-view'; + +export * from './job-details-view'; diff --git a/front_minimal/src/sections/job/view/job-create-view.jsx b/front_minimal/src/sections/job/view/job-create-view.jsx new file mode 100644 index 0000000..5e40c28 --- /dev/null +++ b/front_minimal/src/sections/job/view/job-create-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { JobNewEditForm } from '../job-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function JobCreateView() { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/job/view/job-details-view.jsx b/front_minimal/src/sections/job/view/job-details-view.jsx new file mode 100644 index 0000000..54734f1 --- /dev/null +++ b/front_minimal/src/sections/job/view/job-details-view.jsx @@ -0,0 +1,69 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Tab from '@mui/material/Tab'; +import Tabs from '@mui/material/Tabs'; + +import { paths } from 'src/routes/paths'; + +import { useTabs } from 'src/hooks/use-tabs'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { JOB_DETAILS_TABS, JOB_PUBLISH_OPTIONS } from 'src/_mock'; + +import { Label } from 'src/components/label'; + +import { JobDetailsToolbar } from '../job-details-toolbar'; +import { JobDetailsContent } from '../job-details-content'; +import { JobDetailsCandidates } from '../job-details-candidates'; + +// ---------------------------------------------------------------------- + +export function JobDetailsView({ job }) { + const tabs = useTabs('content'); + + const [publish, setPublish] = useState(job?.publish); + + const handleChangePublish = useCallback((newValue) => { + setPublish(newValue); + }, []); + + const renderTabs = ( + + {JOB_DETAILS_TABS.map((tab) => ( + {job?.candidates.length} + ) : ( + '' + ) + } + /> + ))} + + ); + + return ( + + + {renderTabs} + + {tabs.value === 'content' && } + + {tabs.value === 'candidates' && } + + ); +} diff --git a/front_minimal/src/sections/job/view/job-edit-view.jsx b/front_minimal/src/sections/job/view/job-edit-view.jsx new file mode 100644 index 0000000..905a269 --- /dev/null +++ b/front_minimal/src/sections/job/view/job-edit-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { JobNewEditForm } from '../job-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function JobEditView({ job }) { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/job/view/job-list-view.jsx b/front_minimal/src/sections/job/view/job-list-view.jsx new file mode 100644 index 0000000..d6664e9 --- /dev/null +++ b/front_minimal/src/sections/job/view/job-list-view.jsx @@ -0,0 +1,189 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useSetState } from 'src/hooks/use-set-state'; + +import { orderBy } from 'src/utils/helper'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { + _jobs, + _roles, + JOB_SORT_OPTIONS, + JOB_BENEFIT_OPTIONS, + JOB_EXPERIENCE_OPTIONS, + JOB_EMPLOYMENT_TYPE_OPTIONS, +} from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; +import { EmptyContent } from 'src/components/empty-content'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { JobList } from '../job-list'; +import { JobSort } from '../job-sort'; +import { JobSearch } from '../job-search'; +import { JobFilters } from '../job-filters'; +import { JobFiltersResult } from '../job-filters-result'; + +// ---------------------------------------------------------------------- + +export function JobListView() { + const openFilters = useBoolean(); + + const [sortBy, setSortBy] = useState('latest'); + + const search = useSetState({ query: '', results: [] }); + + const filters = useSetState({ + roles: [], + locations: [], + benefits: [], + experience: 'all', + employmentTypes: [], + }); + + const dataFiltered = applyFilter({ inputData: _jobs, filters: filters.state, sortBy }); + + const canReset = + filters.state.roles.length > 0 || + filters.state.locations.length > 0 || + filters.state.benefits.length > 0 || + filters.state.employmentTypes.length > 0 || + filters.state.experience !== 'all'; + + const notFound = !dataFiltered.length && canReset; + + const handleSortBy = useCallback((newValue) => { + setSortBy(newValue); + }, []); + + const handleSearch = useCallback( + (inputValue) => { + search.setState({ query: inputValue }); + + if (inputValue) { + const results = _jobs.filter( + (job) => job.title.toLowerCase().indexOf(search.state.query.toLowerCase()) !== -1 + ); + + search.setState({ results }); + } + }, + [search] + ); + + const renderFilters = ( + + + + + option.label), + employmentTypes: JOB_EMPLOYMENT_TYPE_OPTIONS.map((option) => option.label), + experiences: ['all', ...JOB_EXPERIENCE_OPTIONS.map((option) => option.label)], + }} + /> + + + + + ); + + const renderResults = ; + + return ( + + } + > + New job + + } + sx={{ mb: { xs: 3, md: 5 } }} + /> + + + {renderFilters} + + {canReset && renderResults} + + + {notFound && } + + + + ); +} + +const applyFilter = ({ inputData, filters, sortBy }) => { + const { employmentTypes, experience, roles, locations, benefits } = filters; + + // Sort by + if (sortBy === 'latest') { + inputData = orderBy(inputData, ['createdAt'], ['desc']); + } + + if (sortBy === 'oldest') { + inputData = orderBy(inputData, ['createdAt'], ['asc']); + } + + if (sortBy === 'popular') { + inputData = orderBy(inputData, ['totalViews'], ['desc']); + } + + // Filters + if (employmentTypes.length) { + inputData = inputData.filter((job) => + job.employmentTypes.some((item) => employmentTypes.includes(item)) + ); + } + + if (experience !== 'all') { + inputData = inputData.filter((job) => job.experience === experience); + } + + if (roles.length) { + inputData = inputData.filter((job) => roles.includes(job.role)); + } + + if (locations.length) { + inputData = inputData.filter((job) => job.locations.some((item) => locations.includes(item))); + } + + if (benefits.length) { + inputData = inputData.filter((job) => job.benefits.some((item) => benefits.includes(item))); + } + + return inputData; +}; diff --git a/front_minimal/src/sections/kanban/classes.js b/front_minimal/src/sections/kanban/classes.js new file mode 100644 index 0000000..ec10485 --- /dev/null +++ b/front_minimal/src/sections/kanban/classes.js @@ -0,0 +1,16 @@ +// ---------------------------------------------------------------------- + +export const kanbanClasses = { + item: 'mnl__kanban__item', + column: 'mnl__kanban__column', + itemWrap: 'mnl__kanban__item__wrap', + columnList: 'mnl__kanban__column_list', + state: { + hover: 'state-hover', + fadeIn: 'state-fade-in', + sorting: 'state-sorting', + dragging: 'state-dragging', + disabled: 'state-disabled', + dragOverlay: 'state-drag-overlay', + }, +}; diff --git a/front_minimal/src/sections/kanban/column/column-base.jsx b/front_minimal/src/sections/kanban/column/column-base.jsx new file mode 100644 index 0000000..dfdc2fb --- /dev/null +++ b/front_minimal/src/sections/kanban/column/column-base.jsx @@ -0,0 +1,87 @@ +import { memo, forwardRef } from 'react'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import { styled } from '@mui/material/styles'; + +import { varAlpha, stylesMode } from 'src/theme/styles'; + +import { kanbanClasses } from '../classes'; + +// ---------------------------------------------------------------------- + +export const StyledRoot = styled(Stack)(({ theme }) => ({ + flexShrink: 0, + height: '100%', + borderWidth: 1, + position: 'relative', + borderStyle: 'solid', + borderColor: 'transparent', + padding: 'var(--column-padding)', + borderRadius: 'var(--column-radius)', + backgroundColor: theme.vars.palette.background.neutral, + [stylesMode.dark]: { backgroundColor: theme.vars.palette.grey[800] }, + '&::before': { + top: 0, + left: 0, + content: '""', + width: '100%', + height: '100%', + position: 'absolute', + borderRadius: 'inherit', + backgroundColor: 'transparent', + transition: theme.transitions.create(['background-color']), + }, + [`&.${kanbanClasses.state.hover}`]: { + '&::before': { + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + [stylesMode.dark]: { backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.16) }, + }, + }, + [`&.${kanbanClasses.state.dragOverlay}`]: { + backdropFilter: `blur(6px)`, + borderColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + backgroundColor: varAlpha(theme.vars.palette.background.neutralChannel, 0.48), + [stylesMode.dark]: { backgroundColor: varAlpha(theme.vars.palette.grey['800Channel'], 0.48) }, + }, + [`&.${kanbanClasses.state.dragging}`]: { opacity: 0 }, +})); + +const ColumnBase = forwardRef(({ slots, stateProps, sx, ...other }, ref) => { + const className = kanbanClasses.column.concat( + (stateProps?.hover && ` ${kanbanClasses.state.hover}`) || + (stateProps?.dragOverlay && ` ${kanbanClasses.state.dragOverlay}`) || + (stateProps?.dragging && ` ${kanbanClasses.state.dragging}`) || + '' + ); + + return ( + + {slots?.header && slots.header} + + {slots?.action && slots?.action} + + {slots?.main && ( + + {slots.main} + + )} + + ); +}); + +export default memo(ColumnBase); diff --git a/front_minimal/src/sections/kanban/column/kanban-column-add.jsx b/front_minimal/src/sections/kanban/column/kanban-column-add.jsx new file mode 100644 index 0000000..3ab859d --- /dev/null +++ b/front_minimal/src/sections/kanban/column/kanban-column-add.jsx @@ -0,0 +1,89 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import TextField from '@mui/material/TextField'; +import { inputBaseClasses } from '@mui/material/InputBase'; +import ClickAwayListener from '@mui/material/ClickAwayListener'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { uuidv4 } from 'src/utils/uuidv4'; + +import { createColumn } from 'src/actions/kanban'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function KanbanColumnAdd({ sx, ...other }) { + const [columnName, setColumnName] = useState(''); + + const openAddColumn = useBoolean(); + + const handleChangeName = useCallback((event) => { + setColumnName(event.target.value); + }, []); + + const handleCreateColumn = useCallback(async () => { + try { + const columnData = { id: uuidv4(), name: columnName.trim() ? columnName : 'Untitled' }; + + createColumn(columnData); + + setColumnName(''); + + openAddColumn.onFalse(); + } catch (error) { + console.error(error); + } + }, [columnName, openAddColumn]); + + const handleKeyUpCreateColumn = useCallback( + (event) => { + if (event.key === 'Enter') { + handleCreateColumn(); + } + }, + [handleCreateColumn] + ); + + const handleCancel = useCallback(() => { + setColumnName(''); + openAddColumn.onFalse(); + }, [openAddColumn]); + + return ( + <> + + {openAddColumn.value ? ( + + + + ) : ( + + )} + + + + + ); +} diff --git a/front_minimal/src/sections/kanban/column/kanban-column-toolbar.jsx b/front_minimal/src/sections/kanban/column/kanban-column-toolbar.jsx new file mode 100644 index 0000000..87336ae --- /dev/null +++ b/front_minimal/src/sections/kanban/column/kanban-column-toolbar.jsx @@ -0,0 +1,160 @@ +import { useRef, useState, useEffect, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { varAlpha } from 'src/theme/styles'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +import { KanbanInputName } from '../components/kanban-input-name'; + +// ---------------------------------------------------------------------- + +export function KanbanColumnToolBar({ + columnName, + totalTasks, + handleProps, + onClearColumn, + onToggleAddTask, + onDeleteColumn, + onUpdateColumn, +}) { + const renameRef = useRef(null); + + const popover = usePopover(); + + const confirmDialog = useBoolean(); + + const [name, setName] = useState(columnName); + + useEffect(() => { + if (popover.open) { + if (renameRef.current) { + renameRef.current.focus(); + } + } + }, [popover.open]); + + const handleChangeName = useCallback((event) => { + setName(event.target.value); + }, []); + + const handleKeyUpUpdateColumn = useCallback( + (event) => { + if (event.key === 'Enter') { + if (renameRef.current) { + renameRef.current.blur(); + } + onUpdateColumn?.(name); + } + }, + [name, onUpdateColumn] + ); + + return ( + <> + + + + + + + + + + + + + + + + + + + + + + + Rename + + + { + onClearColumn?.(); + popover.onClose(); + }} + > + + Clear + + + { + confirmDialog.onTrue(); + popover.onClose(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + + Are you sure want to delete column? + + NOTE: All tasks related to this category will also be deleted. + + + } + action={ + + } + /> + + ); +} diff --git a/front_minimal/src/sections/kanban/column/kanban-column.jsx b/front_minimal/src/sections/kanban/column/kanban-column.jsx new file mode 100644 index 0000000..0966c29 --- /dev/null +++ b/front_minimal/src/sections/kanban/column/kanban-column.jsx @@ -0,0 +1,117 @@ +import { useCallback } from 'react'; +import { CSS } from '@dnd-kit/utilities'; +import { useSortable, defaultAnimateLayoutChanges } from '@dnd-kit/sortable'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { createTask, clearColumn, deleteColumn, updateColumn } from 'src/actions/kanban'; + +import { toast } from 'src/components/snackbar'; + +import ColumnBase from './column-base'; +import { KanbanTaskAdd } from '../components/kanban-task-add'; +import { KanbanColumnToolBar } from './kanban-column-toolbar'; + +// ---------------------------------------------------------------------- + +export function KanbanColumn({ children, column, tasks, disabled, sx }) { + const openAddTask = useBoolean(); + + const { attributes, isDragging, listeners, setNodeRef, transition, active, over, transform } = + useSortable({ + id: column.id, + data: { type: 'container', children: tasks }, + animateLayoutChanges, + }); + + const tasksIds = tasks.map((task) => task.id); + + const isOverContainer = over + ? (column.id === over.id && active?.data.current?.type !== 'container') || + tasksIds.includes(over.id) + : false; + + const handleUpdateColumn = useCallback( + async (columnName) => { + try { + if (column.name !== columnName) { + updateColumn(column.id, columnName); + + toast.success('Update success!', { position: 'top-center' }); + } + } catch (error) { + console.error(error); + } + }, + [column.id, column.name] + ); + + const handleClearColumn = useCallback(async () => { + try { + clearColumn(column.id); + } catch (error) { + console.error(error); + } + }, [column.id]); + + const handleDeleteColumn = useCallback(async () => { + try { + deleteColumn(column.id); + + toast.success('Delete success!', { position: 'top-center' }); + } catch (error) { + console.error(error); + } + }, [column.id]); + + const handleAddTask = useCallback( + async (taskData) => { + try { + createTask(column.id, taskData); + + openAddTask.onFalse(); + } catch (error) { + console.error(error); + } + }, + [column.id, openAddTask] + ); + + return ( + + ), + main: <>{children}, + action: ( + + ), + }} + /> + ); +} + +// ---------------------------------------------------------------------- + +const animateLayoutChanges = (args) => defaultAnimateLayoutChanges({ ...args, wasDragging: true }); diff --git a/front_minimal/src/sections/kanban/components/kanban-contacts-dialog.jsx b/front_minimal/src/sections/kanban/components/kanban-contacts-dialog.jsx new file mode 100644 index 0000000..8366d7c --- /dev/null +++ b/front_minimal/src/sections/kanban/components/kanban-contacts-dialog.jsx @@ -0,0 +1,122 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Dialog from '@mui/material/Dialog'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import DialogTitle from '@mui/material/DialogTitle'; +import ListItemText from '@mui/material/ListItemText'; +import DialogContent from '@mui/material/DialogContent'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { _contacts } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { SearchNotFound } from 'src/components/search-not-found'; + +// ---------------------------------------------------------------------- + +const ITEM_HEIGHT = 64; + +// ---------------------------------------------------------------------- + +export function KanbanContactsDialog({ assignee = [], open, onClose }) { + const [searchContact, setSearchContact] = useState(''); + + const handleSearchContacts = useCallback((event) => { + setSearchContact(event.target.value); + }, []); + + const dataFiltered = applyFilter({ inputData: _contacts, query: searchContact }); + + const notFound = !dataFiltered.length && !!searchContact; + + return ( + + + Contacts ({_contacts.length}) + + + + + + + ), + }} + /> + + + + {notFound ? ( + + ) : ( + + + {dataFiltered.map((contact) => { + const checked = assignee.map((person) => person.name).includes(contact.name); + + return ( + + + + + + + + ); + })} + + + )} + + + ); +} + +function applyFilter({ inputData, query }) { + if (query) { + inputData = inputData.filter( + (contact) => + contact.name.toLowerCase().indexOf(query.toLowerCase()) !== -1 || + contact.email.toLowerCase().indexOf(query.toLowerCase()) !== -1 + ); + } + + return inputData; +} diff --git a/front_minimal/src/sections/kanban/components/kanban-drag-overlay.jsx b/front_minimal/src/sections/kanban/components/kanban-drag-overlay.jsx new file mode 100644 index 0000000..4a7f5b2 --- /dev/null +++ b/front_minimal/src/sections/kanban/components/kanban-drag-overlay.jsx @@ -0,0 +1,60 @@ +import { DragOverlay as DndDragOverlay, defaultDropAnimationSideEffects } from '@dnd-kit/core'; + +import Portal from '@mui/material/Portal'; + +import ItemBase from '../item/item-base'; +import ColumnBase from '../column/column-base'; +import { KanbanColumnToolBar } from '../column/kanban-column-toolbar'; + +const dropAnimation = { + sideEffects: defaultDropAnimationSideEffects({ styles: { active: { opacity: '0.5' } } }), +}; + +// ---------------------------------------------------------------------- + +export function KanbanDragOverlay({ columns, tasks, activeId, sx }) { + const columnIds = columns.map((column) => column.id); + + const activeColumn = columns.find((column) => column.id === activeId); + + const allTasks = Object.values(tasks).flat(); + + const activeTask = allTasks.find((task) => task.id === activeId); + + return ( + + + {activeId ? ( + <> + {columnIds.includes(activeId) ? ( + + ) : ( + + )} + + ) : null} + + + ); +} + +// ---------------------------------------------------------------------- + +export function ColumnOverlay({ column, tasks, sx }) { + return ( + , + main: tasks.map((task) => ), + }} + stateProps={{ dragOverlay: true }} + sx={sx} + /> + ); +} + +// ---------------------------------------------------------------------- + +export function TaskItemOverlay({ task, sx }) { + return ; +} diff --git a/front_minimal/src/sections/kanban/components/kanban-input-name.jsx b/front_minimal/src/sections/kanban/components/kanban-input-name.jsx new file mode 100644 index 0000000..2bc3e28 --- /dev/null +++ b/front_minimal/src/sections/kanban/components/kanban-input-name.jsx @@ -0,0 +1,25 @@ +import InputBase, { inputBaseClasses } from '@mui/material/InputBase'; + +// ---------------------------------------------------------------------- + +export function KanbanInputName({ sx, ...other }) { + return ( + theme.transitions.create(['padding-left', 'border-color']), + [`&.${inputBaseClasses.focused}`]: { pl: 0.75, borderColor: 'text.primary' }, + }, + [`& .${inputBaseClasses.input}`]: { typography: 'h6' }, + ...sx, + }} + {...other} + /> + ); +} diff --git a/front_minimal/src/sections/kanban/components/kanban-skeleton.jsx b/front_minimal/src/sections/kanban/components/kanban-skeleton.jsx new file mode 100644 index 0000000..270c09c --- /dev/null +++ b/front_minimal/src/sections/kanban/components/kanban-skeleton.jsx @@ -0,0 +1,28 @@ +import Paper from '@mui/material/Paper'; +import Skeleton from '@mui/material/Skeleton'; + +// ---------------------------------------------------------------------- + +export function KanbanColumnSkeleton({ amount = 3, sx, ...other }) { + return [...Array(amount)].map((_, index) => ( + + + {[0].includes(index) && } + {[0, 1].includes(index) && } + {[0, 1, 2].includes(index) && } + + )); +} diff --git a/front_minimal/src/sections/kanban/components/kanban-task-add.jsx b/front_minimal/src/sections/kanban/components/kanban-task-add.jsx new file mode 100644 index 0000000..c42c31d --- /dev/null +++ b/front_minimal/src/sections/kanban/components/kanban-task-add.jsx @@ -0,0 +1,85 @@ +import { useMemo, useState, useCallback } from 'react'; + +import Paper from '@mui/material/Paper'; +import FormHelperText from '@mui/material/FormHelperText'; +import ClickAwayListener from '@mui/material/ClickAwayListener'; +import InputBase, { inputBaseClasses } from '@mui/material/InputBase'; + +import { uuidv4 } from 'src/utils/uuidv4'; + +import { _mock } from 'src/_mock'; + +// ---------------------------------------------------------------------- + +export function KanbanTaskAdd({ status, openAddTask, onAddTask, onCloseAddTask }) { + const [taskName, setTaskName] = useState(''); + + const defaultTask = useMemo( + () => ({ + id: uuidv4(), + status, + name: taskName.trim() ? taskName : 'Untitled', + priority: 'medium', + attachments: [], + labels: [], + comments: [], + assignee: [], + due: [null, null], + reporter: { id: _mock.id(16), name: _mock.fullName(16), avatarUrl: _mock.image.avatar(16) }, + }), + [status, taskName] + ); + + const handleChangeName = useCallback((event) => { + setTaskName(event.target.value); + }, []); + + const handleKeyUpAddTask = useCallback( + (event) => { + if (event.key === 'Enter') { + onAddTask(defaultTask); + setTaskName(''); + } + }, + [defaultTask, onAddTask] + ); + + const handleCancel = useCallback(() => { + setTaskName(''); + onCloseAddTask(); + }, [onCloseAddTask]); + + if (!openAddTask) { + return null; + } + + return ( + +
    + theme.customShadows.z1, + }} + > + + + + Press Enter to create the task. +
    +
    + ); +} diff --git a/front_minimal/src/sections/kanban/details/kanban-details-attachments.jsx b/front_minimal/src/sections/kanban/details/kanban-details-attachments.jsx new file mode 100644 index 0000000..79876e4 --- /dev/null +++ b/front_minimal/src/sections/kanban/details/kanban-details-attachments.jsx @@ -0,0 +1,34 @@ +import { useState, useCallback } from 'react'; + +import { UploadBox, MultiFilePreview } from 'src/components/upload'; + +// ---------------------------------------------------------------------- + +export function KanbanDetailsAttachments({ attachments }) { + const [files, setFiles] = useState(attachments); + + const handleDrop = useCallback( + (acceptedFiles) => { + setFiles([...files, ...acceptedFiles]); + }, + [files] + ); + + const handleRemoveFile = useCallback( + (inputFile) => { + const filtered = files.filter((file) => file !== inputFile); + setFiles(filtered); + }, + [files] + ); + + return ( + handleRemoveFile(file)} + slotProps={{ thumbnail: { sx: { width: 64, height: 64 } } }} + lastNode={} + /> + ); +} diff --git a/front_minimal/src/sections/kanban/details/kanban-details-comment-input.jsx b/front_minimal/src/sections/kanban/details/kanban-details-comment-input.jsx new file mode 100644 index 0000000..e3ac751 --- /dev/null +++ b/front_minimal/src/sections/kanban/details/kanban-details-comment-input.jsx @@ -0,0 +1,42 @@ +import Paper from '@mui/material/Paper'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import InputBase from '@mui/material/InputBase'; +import IconButton from '@mui/material/IconButton'; + +import { Iconify } from 'src/components/iconify'; + +import { useMockedUser } from 'src/auth/hooks'; + +// ---------------------------------------------------------------------- + +export function KanbanDetailsCommentInput() { + const { user } = useMockedUser(); + + return ( + + + {user?.displayName?.charAt(0).toUpperCase()} + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/kanban/details/kanban-details-comment-list.jsx b/front_minimal/src/sections/kanban/details/kanban-details-comment-list.jsx new file mode 100644 index 0000000..daf9e12 --- /dev/null +++ b/front_minimal/src/sections/kanban/details/kanban-details-comment-list.jsx @@ -0,0 +1,62 @@ +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Typography from '@mui/material/Typography'; + +import { fToNow } from 'src/utils/format-time'; + +import { Image } from 'src/components/image'; +import { Lightbox, useLightBox } from 'src/components/lightbox'; + +// ---------------------------------------------------------------------- + +export function KanbanDetailsCommentList({ comments }) { + const slides = comments + .filter((comment) => comment.messageType === 'image') + .map((slide) => ({ src: slide.message })); + + const lightbox = useLightBox(slides); + + return ( + <> + + {comments.map((comment) => ( + + + + + + {comment.name} + + {fToNow(comment.createdAt)} + + + + {comment.messageType === 'image' ? ( + {comment.message} lightbox.onOpen(comment.message)} + sx={{ + borderRadius: 1.5, + cursor: 'pointer', + transition: (theme) => theme.transitions.create(['opacity']), + '&:hover': { opacity: 0.8 }, + }} + /> + ) : ( + {comment.message} + )} + + + ))} + + + + + ); +} diff --git a/front_minimal/src/sections/kanban/details/kanban-details-priority.jsx b/front_minimal/src/sections/kanban/details/kanban-details-priority.jsx new file mode 100644 index 0000000..7b6f3ee --- /dev/null +++ b/front_minimal/src/sections/kanban/details/kanban-details-priority.jsx @@ -0,0 +1,52 @@ +import Stack from '@mui/material/Stack'; +import ButtonBase from '@mui/material/ButtonBase'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function KanbanDetailsPriority({ priority, onChangePriority }) { + return ( + + {['low', 'medium', 'hight'].map((option) => ( + onChangePriority(option)} + sx={{ + py: 0.5, + pl: 0.75, + pr: 1.25, + fontSize: 12, + borderRadius: 1, + lineHeight: '20px', + textTransform: 'capitalize', + fontWeight: 'fontWeightBold', + boxShadow: (theme) => + `inset 0 0 0 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.24)}`, + ...(option === priority && { + boxShadow: (theme) => `inset 0 0 0 2px ${theme.vars.palette.text.primary}`, + }), + }} + > + + + {option} + + ))} + + ); +} diff --git a/front_minimal/src/sections/kanban/details/kanban-details-toolbar.jsx b/front_minimal/src/sections/kanban/details/kanban-details-toolbar.jsx new file mode 100644 index 0000000..2078b50 --- /dev/null +++ b/front_minimal/src/sections/kanban/details/kanban-details-toolbar.jsx @@ -0,0 +1,127 @@ +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Tooltip from '@mui/material/Tooltip'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useResponsive } from 'src/hooks/use-responsive'; + +import { Iconify } from 'src/components/iconify'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function KanbanDetailsToolbar({ + liked, + onLike, + taskName, + onDelete, + taskStatus, + onCloseDetails, +}) { + const smUp = useResponsive('up', 'sm'); + + const confirm = useBoolean(); + + const popover = usePopover(); + + const [status, setStatus] = useState(taskStatus); + + const handleChangeStatus = useCallback( + (newValue) => { + popover.onClose(); + setStatus(newValue); + }, + [popover] + ); + + return ( + <> + theme.spacing(2.5, 1, 2.5, 2.5), + borderBottom: (theme) => `solid 1px ${theme.vars.palette.divider}`, + }} + > + {!smUp && ( + + + + + + )} + + + + + + + + + + + + + + + + + + + + + + + + + {['To do', 'In progress', 'Ready to test', 'Done'].map((option) => ( + { + handleChangeStatus(option); + }} + > + {option} + + ))} + + + + + Are you sure want to delete {taskName} ? + + } + action={ + + } + /> + + ); +} diff --git a/front_minimal/src/sections/kanban/details/kanban-details.jsx b/front_minimal/src/sections/kanban/details/kanban-details.jsx new file mode 100644 index 0000000..63964ee --- /dev/null +++ b/front_minimal/src/sections/kanban/details/kanban-details.jsx @@ -0,0 +1,326 @@ +import dayjs from 'dayjs'; +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Tab from '@mui/material/Tab'; +import Chip from '@mui/material/Chip'; +import Drawer from '@mui/material/Drawer'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Tooltip from '@mui/material/Tooltip'; +import { styled } from '@mui/material/styles'; +import Checkbox from '@mui/material/Checkbox'; +import TextField from '@mui/material/TextField'; +import FormGroup from '@mui/material/FormGroup'; +import Typography from '@mui/material/Typography'; +import IconButton from '@mui/material/IconButton'; +import LinearProgress from '@mui/material/LinearProgress'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { useTabs } from 'src/hooks/use-tabs'; +import { useBoolean } from 'src/hooks/use-boolean'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { CustomTabs } from 'src/components/custom-tabs'; +import { useDateRangePicker, CustomDateRangePicker } from 'src/components/custom-date-range-picker'; + +import { KanbanDetailsToolbar } from './kanban-details-toolbar'; +import { KanbanInputName } from '../components/kanban-input-name'; +import { KanbanDetailsPriority } from './kanban-details-priority'; +import { KanbanDetailsAttachments } from './kanban-details-attachments'; +import { KanbanDetailsCommentList } from './kanban-details-comment-list'; +import { KanbanDetailsCommentInput } from './kanban-details-comment-input'; +import { KanbanContactsDialog } from '../components/kanban-contacts-dialog'; + +// ---------------------------------------------------------------------- + +const SUBTASKS = [ + 'Complete project proposal', + 'Conduct market research', + 'Design user interface mockups', + 'Develop backend api', + 'Implement authentication system', +]; + +const StyledLabel = styled('span')(({ theme }) => ({ + ...theme.typography.caption, + width: 100, + flexShrink: 0, + color: theme.vars.palette.text.secondary, + fontWeight: theme.typography.fontWeightSemiBold, +})); + +// ---------------------------------------------------------------------- + +export function KanbanDetails({ task, openDetails, onUpdateTask, onDeleteTask, onCloseDetails }) { + const tabs = useTabs('overview'); + + const [priority, setPriority] = useState(task.priority); + + const [taskName, setTaskName] = useState(task.name); + + const [subtaskCompleted, setSubtaskCompleted] = useState(SUBTASKS.slice(0, 2)); + + const like = useBoolean(); + + const contacts = useBoolean(); + + const [taskDescription, setTaskDescription] = useState(task.description); + + const rangePicker = useDateRangePicker(dayjs(task.due[0]), dayjs(task.due[1])); + + const handleChangeTaskName = useCallback((event) => { + setTaskName(event.target.value); + }, []); + + const handleUpdateTask = useCallback( + (event) => { + try { + if (event.key === 'Enter') { + if (taskName) { + onUpdateTask({ ...task, name: taskName }); + } + } + } catch (error) { + console.error(error); + } + }, + [onUpdateTask, task, taskName] + ); + + const handleChangeTaskDescription = useCallback((event) => { + setTaskDescription(event.target.value); + }, []); + + const handleChangePriority = useCallback((newValue) => { + setPriority(newValue); + }, []); + + const handleClickSubtaskComplete = (taskId) => { + const selected = subtaskCompleted.includes(taskId) + ? subtaskCompleted.filter((value) => value !== taskId) + : [...subtaskCompleted, taskId]; + + setSubtaskCompleted(selected); + }; + + const renderToolbar = ( + + ); + + const renderTabs = ( + + {[ + { value: 'overview', label: 'Overview' }, + { value: 'subTasks', label: 'Subtasks' }, + { value: 'comments', label: `Comments (${task.comments.length})` }, + ].map((tab) => ( + + ))} + + ); + + const renderTabOverview = ( + + {/* Task name */} + + + {/* Reporter */} + + Reporter + + + + {/* Assignee */} + + Assignee + + + {task.assignee.map((user) => ( + + ))} + + + varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + border: (theme) => `dashed 1px ${theme.vars.palette.divider}`, + }} + > + + + + + + + + + {/* Label */} + + Labels + + {!!task.labels.length && ( + + {task.labels.map((label) => ( + + ))} + + )} + + + {/* Due date */} + + Due date + + {rangePicker.selected ? ( + + ) : ( + + varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + border: (theme) => `dashed 1px ${theme.vars.palette.divider}`, + }} + > + + + + )} + + + + + {/* Priority */} + + Priority + + + + {/* Description */} + + Description + + + + {/* Attachments */} + + Attachments + + + + ); + + const renderTabSubtasks = ( + +
    + + {subtaskCompleted.length} of {SUBTASKS.length} + + + +
    + + + {SUBTASKS.map((taskItem) => ( + + } + label={taskItem} + onChange={() => handleClickSubtaskComplete(taskItem)} + /> + ))} + + + +
    + ); + + const renderTabComments = ( + <>{!!task.comments.length && } + ); + + return ( + + {renderToolbar} + + {renderTabs} + + + {tabs.value === 'overview' && renderTabOverview} + {tabs.value === 'subTasks' && renderTabSubtasks} + {tabs.value === 'comments' && renderTabComments} + + + {tabs.value === 'comments' && } + + ); +} diff --git a/front_minimal/src/sections/kanban/item/item-base.jsx b/front_minimal/src/sections/kanban/item/item-base.jsx new file mode 100644 index 0000000..c13575d --- /dev/null +++ b/front_minimal/src/sections/kanban/item/item-base.jsx @@ -0,0 +1,184 @@ +import { memo, useEffect, forwardRef } from 'react'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import ListItem from '@mui/material/ListItem'; +import Typography from '@mui/material/Typography'; +import { styled, useTheme } from '@mui/material/styles'; +import AvatarGroup, { avatarGroupClasses } from '@mui/material/AvatarGroup'; + +import { varAlpha, stylesMode } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { imageClasses } from 'src/components/image'; + +import { kanbanClasses } from '../classes'; + +// ---------------------------------------------------------------------- + +export const StyledItemWrap = styled(ListItem)(() => ({ + '@keyframes fadeIn': { '0%': { opacity: 0 }, '100%': { opacity: 1 } }, + transform: + 'translate3d(var(--translate-x, 0), var(--translate-y, 0), 0) scaleX(var(--scale-x, 1)) scaleY(var(--scale-y, 1))', + transformOrigin: '0 0', + touchAction: 'manipulation', + [`&.${kanbanClasses.state.fadeIn}`]: { animation: 'fadeIn 500ms ease' }, + [`&.${kanbanClasses.state.dragOverlay}`]: { zIndex: 999 }, +})); + +export const StyledItem = styled(Stack)(({ theme }) => ({ + width: '100%', + cursor: 'grab', + outline: 'none', + overflow: 'hidden', + position: 'relative', + transformOrigin: '50% 50%', + touchAction: 'manipulation', + boxShadow: theme.customShadows.z1, + borderRadius: 'var(--item-radius)', + WebkitTapHighlightColor: 'transparent', + backgroundColor: theme.vars.palette.common.white, + transition: theme.transitions.create(['box-shadow']), + [stylesMode.dark]: { backgroundColor: theme.vars.palette.grey[900] }, + [`&.${kanbanClasses.state.disabled}`]: {}, + [`&.${kanbanClasses.state.sorting}`]: {}, + [`&.${kanbanClasses.state.dragOverlay}`]: { + backdropFilter: `blur(6px)`, + boxShadow: theme.customShadows.z20, + backgroundColor: varAlpha(theme.vars.palette.common.whiteChannel, 0.48), + [stylesMode.dark]: { backgroundColor: varAlpha(theme.vars.palette.grey['900Channel'], 0.48) }, + }, + [`&.${kanbanClasses.state.dragging}`]: { opacity: 0.2, filter: 'grayscale(1)' }, +})); + +const ItemBase = forwardRef(({ task, stateProps, sx, ...other }, ref) => { + const theme = useTheme(); + + useEffect(() => { + if (!stateProps?.dragOverlay) { + return; + } + + document.body.style.cursor = 'grabbing'; + + // eslint-disable-next-line consistent-return + return () => { + document.body.style.cursor = ''; + }; + }, [stateProps?.dragOverlay]); + + const itemWrapClassName = kanbanClasses.itemWrap.concat( + (stateProps?.fadeIn && ` ${kanbanClasses.state.fadeIn}`) || + (stateProps?.dragOverlay && ` ${kanbanClasses.state.dragOverlay}`) || + '' + ); + + const itemClassName = kanbanClasses.item.concat( + (stateProps?.dragging && ` ${kanbanClasses.state.dragging}`) || + (stateProps?.disabled && ` ${kanbanClasses.state.disabled}`) || + (stateProps?.sorting && ` ${kanbanClasses.state.sorting}`) || + (stateProps?.dragOverlay && ` ${kanbanClasses.state.dragOverlay}`) || + '' + ); + + const renderPriority = ( + + ); + + const renderImg = !!task?.attachments?.length && ( + + + + ); + + const renderInfo = ( + + + + + + {task?.comments?.length} + + + + {task?.attachments?.length} + + + + {task?.assignee?.map((user) => ( + + ))} + + + ); + + return ( + + + {renderImg} + + + {renderPriority} + + {task.name} + + {renderInfo} + + + + ); +}); + +export default memo(ItemBase); diff --git a/front_minimal/src/sections/kanban/item/kanban-task-item.jsx b/front_minimal/src/sections/kanban/item/kanban-task-item.jsx new file mode 100644 index 0000000..b38cf48 --- /dev/null +++ b/front_minimal/src/sections/kanban/item/kanban-task-item.jsx @@ -0,0 +1,87 @@ +import { useSortable } from '@dnd-kit/sortable'; +import { useState, useEffect, useCallback } from 'react'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { deleteTask, updateTask } from 'src/actions/kanban'; + +import { toast } from 'src/components/snackbar'; +import { imageClasses } from 'src/components/image'; + +import ItemBase from './item-base'; +import { KanbanDetails } from '../details/kanban-details'; + +// ---------------------------------------------------------------------- + +export function KanbanTaskItem({ task, disabled, columnId, sx }) { + const openDetails = useBoolean(); + + const { setNodeRef, listeners, isDragging, isSorting, transform, transition } = useSortable({ + id: task?.id, + }); + + const mounted = useMountStatus(); + + const mountedWhileDragging = isDragging && !mounted; + + const handleDeleteTask = useCallback(async () => { + try { + deleteTask(columnId, task.id); + toast.success('Delete success!', { position: 'top-center' }); + } catch (error) { + console.error(error); + } + }, [columnId, task.id]); + + const handleUpdateTask = useCallback( + async (taskData) => { + try { + updateTask(columnId, taskData); + } catch (error) { + console.error(error); + } + }, + [columnId] + ); + + return ( + <> + + + + + ); +} + +// ---------------------------------------------------------------------- + +function useMountStatus() { + const [isMounted, setIsMounted] = useState(false); + + useEffect(() => { + const timeout = setTimeout(() => setIsMounted(true), 500); + + return () => clearTimeout(timeout); + }, []); + + return isMounted; +} diff --git a/front_minimal/src/sections/kanban/utils.js b/front_minimal/src/sections/kanban/utils.js new file mode 100644 index 0000000..261c0dc --- /dev/null +++ b/front_minimal/src/sections/kanban/utils.js @@ -0,0 +1,101 @@ +/* eslint-disable consistent-return */ +/* eslint-disable default-case */ +import { KeyboardCode, closestCorners, getFirstCollision } from '@dnd-kit/core'; + +// ---------------------------------------------------------------------- + +const directions = [KeyboardCode.Down, KeyboardCode.Right, KeyboardCode.Up, KeyboardCode.Left]; + +export const coordinateGetter = ( + event, + { context: { active, droppableRects, droppableContainers, collisionRect } } +) => { + if (directions.includes(event.code)) { + event.preventDefault(); + + if (!active || !collisionRect) { + return; + } + + const filteredContainers = []; + + droppableContainers.getEnabled().forEach((entry) => { + if (!entry || entry?.disabled) { + return; + } + + const rect = droppableRects.get(entry.id); + + if (!rect) { + return; + } + + const data = entry.data.current; + + if (data) { + const { type, children } = data; + + if (type === 'container' && children?.length > 0) { + if (active.data.current?.type !== 'container') { + return; + } + } + } + + switch (event.code) { + case KeyboardCode.Down: + if (collisionRect.top < rect.top) { + filteredContainers.push(entry); + } + break; + case KeyboardCode.Up: + if (collisionRect.top > rect.top) { + filteredContainers.push(entry); + } + break; + case KeyboardCode.Left: + if (collisionRect.left >= rect.left + rect.width) { + filteredContainers.push(entry); + } + break; + case KeyboardCode.Right: + if (collisionRect.left + collisionRect.width <= rect.left) { + filteredContainers.push(entry); + } + break; + } + }); + + const collisions = closestCorners({ + active, + collisionRect, + droppableRects, + droppableContainers: filteredContainers, + pointerCoordinates: null, + }); + const closestId = getFirstCollision(collisions, 'id'); + + if (closestId != null) { + const newDroppable = droppableContainers.get(closestId); + const newNode = newDroppable?.node.current; + const newRect = newDroppable?.rect.current; + + if (newNode && newRect) { + if (newDroppable.id === 'placeholder') { + return { + x: newRect.left + (newRect.width - collisionRect.width) / 2, + y: newRect.top + (newRect.height - collisionRect.height) / 2, + }; + } + + if (newDroppable.data.current?.type === 'container') { + return { x: newRect.left + 20, y: newRect.top + 74 }; + } + + return { x: newRect.left, y: newRect.top }; + } + } + } + + return undefined; +}; diff --git a/front_minimal/src/sections/kanban/view/index.js b/front_minimal/src/sections/kanban/view/index.js new file mode 100644 index 0000000..ae4a0c2 --- /dev/null +++ b/front_minimal/src/sections/kanban/view/index.js @@ -0,0 +1 @@ +export * from './kanban-view'; diff --git a/front_minimal/src/sections/kanban/view/kanban-view.jsx b/front_minimal/src/sections/kanban/view/kanban-view.jsx new file mode 100644 index 0000000..b307052 --- /dev/null +++ b/front_minimal/src/sections/kanban/view/kanban-view.jsx @@ -0,0 +1,376 @@ +'use client'; + +import { useRef, useState, useEffect, useCallback } from 'react'; +import { + arrayMove, + SortableContext, + verticalListSortingStrategy, + horizontalListSortingStrategy, +} from '@dnd-kit/sortable'; +import { + useSensor, + DndContext, + useSensors, + MouseSensor, + TouchSensor, + closestCenter, + pointerWithin, + KeyboardSensor, + rectIntersection, + getFirstCollision, + MeasuringStrategy, +} from '@dnd-kit/core'; + +import Stack from '@mui/material/Stack'; +import Switch from '@mui/material/Switch'; +import Typography from '@mui/material/Typography'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { hideScrollY } from 'src/theme/styles'; +import { DashboardContent } from 'src/layouts/dashboard'; +import { moveTask, moveColumn, useGetBoard } from 'src/actions/kanban'; + +import { EmptyContent } from 'src/components/empty-content'; + +import { kanbanClasses } from '../classes'; +import { coordinateGetter } from '../utils'; +import { KanbanColumn } from '../column/kanban-column'; +import { KanbanTaskItem } from '../item/kanban-task-item'; +import { KanbanColumnAdd } from '../column/kanban-column-add'; +import { KanbanColumnSkeleton } from '../components/kanban-skeleton'; +import { KanbanDragOverlay } from '../components/kanban-drag-overlay'; + +// ---------------------------------------------------------------------- + +const PLACEHOLDER_ID = 'placeholder'; + +const cssVars = { + '--item-gap': '16px', + '--item-radius': '12px', + '--column-gap': '24px', + '--column-width': '336px', + '--column-radius': '16px', + '--column-padding': '20px 16px 16px 16px', +}; + +// ---------------------------------------------------------------------- + +export function KanbanView() { + const { board, boardLoading, boardEmpty } = useGetBoard(); + + const [columnFixed, setColumnFixed] = useState(true); + + const recentlyMovedToNewContainer = useRef(false); + + const lastOverId = useRef(null); + + const [activeId, setActiveId] = useState(null); + + const columnIds = board.columns.map((column) => column.id); + + const isSortingContainer = activeId ? columnIds.includes(activeId) : false; + + const sensors = useSensors( + useSensor(MouseSensor, { activationConstraint: { distance: 5 } }), + useSensor(TouchSensor, { activationConstraint: { distance: 5 } }), + useSensor(KeyboardSensor, { coordinateGetter }) + ); + + const collisionDetectionStrategy = useCallback( + (args) => { + if (activeId && activeId in board.tasks) { + return closestCenter({ + ...args, + droppableContainers: args.droppableContainers.filter( + (column) => column.id in board.tasks + ), + }); + } + + // Start by finding any intersecting droppable + const pointerIntersections = pointerWithin(args); + + const intersections = + pointerIntersections.length > 0 + ? // If there are droppables intersecting with the pointer, return those + pointerIntersections + : rectIntersection(args); + let overId = getFirstCollision(intersections, 'id'); + + if (overId != null) { + if (overId in board.tasks) { + const columnItems = board.tasks[overId].map((task) => task.id); + + // If a column is matched and it contains items (columns 'A', 'B', 'C') + if (columnItems.length > 0) { + // Return the closest droppable within that column + overId = closestCenter({ + ...args, + droppableContainers: args.droppableContainers.filter( + (column) => column.id !== overId && columnItems.includes(column.id) + ), + })[0]?.id; + } + } + + lastOverId.current = overId; + + return [{ id: overId }]; + } + + // When a draggable item moves to a new column, the layout may shift + // and the `overId` may become `null`. We manually set the cached `lastOverId` + // to the id of the draggable item that was moved to the new column, otherwise + // the previous `overId` will be returned which can cause items to incorrectly shift positions + if (recentlyMovedToNewContainer.current) { + lastOverId.current = activeId; + } + + // If no droppable is matched, return the last match + return lastOverId.current ? [{ id: lastOverId.current }] : []; + }, + [activeId, board?.tasks] + ); + + const findColumn = (id) => { + if (id in board.tasks) { + return id; + } + + return Object.keys(board.tasks).find((key) => + board.tasks[key].map((task) => task.id).includes(id) + ); + }; + + useEffect(() => { + requestAnimationFrame(() => { + recentlyMovedToNewContainer.current = false; + }); + }, []); + + /** + * onDragStart + */ + const onDragStart = ({ active }) => { + setActiveId(active.id); + }; + + /** + * onDragOver + */ + const onDragOver = ({ active, over }) => { + const overId = over?.id; + + if (overId == null || active.id in board.tasks) { + return; + } + + const overColumn = findColumn(overId); + + const activeColumn = findColumn(active.id); + + if (!overColumn || !activeColumn) { + return; + } + + if (activeColumn !== overColumn) { + const activeItems = board.tasks[activeColumn].map((task) => task.id); + const overItems = board.tasks[overColumn].map((task) => task.id); + const overIndex = overItems.indexOf(overId); + const activeIndex = activeItems.indexOf(active.id); + + let newIndex; + + if (overId in board.tasks) { + newIndex = overItems.length + 1; + } else { + const isBelowOverItem = + over && + active.rect.current.translated && + active.rect.current.translated.top > over.rect.top + over.rect.height; + + const modifier = isBelowOverItem ? 1 : 0; + + newIndex = overIndex >= 0 ? overIndex + modifier : overItems.length + 1; + } + + recentlyMovedToNewContainer.current = true; + + const updateTasks = { + ...board.tasks, + [activeColumn]: board.tasks[activeColumn].filter((task) => task.id !== active.id), + [overColumn]: [ + ...board.tasks[overColumn].slice(0, newIndex), + board.tasks[activeColumn][activeIndex], + ...board.tasks[overColumn].slice(newIndex, board.tasks[overColumn].length), + ], + }; + + moveTask(updateTasks); + } + }; + + /** + * onDragEnd + */ + const onDragEnd = ({ active, over }) => { + if (active.id in board.tasks && over?.id) { + const activeIndex = columnIds.indexOf(active.id); + const overIndex = columnIds.indexOf(over.id); + + const updateColumns = arrayMove(board.columns, activeIndex, overIndex); + + moveColumn(updateColumns); + } + + const activeColumn = findColumn(active.id); + + if (!activeColumn) { + setActiveId(null); + return; + } + + const overId = over?.id; + + if (overId == null) { + setActiveId(null); + return; + } + + const overColumn = findColumn(overId); + + if (overColumn) { + const activeContainerTaskIds = board.tasks[activeColumn].map((task) => task.id); + const overContainerTaskIds = board.tasks[overColumn].map((task) => task.id); + + const activeIndex = activeContainerTaskIds.indexOf(active.id); + const overIndex = overContainerTaskIds.indexOf(overId); + + if (activeIndex !== overIndex) { + const updateTasks = { + ...board.tasks, + [overColumn]: arrayMove(board.tasks[overColumn], activeIndex, overIndex), + }; + + moveTask(updateTasks); + } + } + + setActiveId(null); + }; + + const renderLoading = ( + + + + ); + + const renderEmpty = ; + + const renderList = ( + + + + + + {board?.columns.map((column) => ( + + + {board.tasks[column.id].map((task) => ( + + ))} + + + ))} + + + + + + + + + + ); + + return ( + + + Kanban + + { + setColumnFixed(event.target.checked); + }} + inputProps={{ id: 'column-fixed-switch' }} + /> + } + /> + + + {boardLoading ? renderLoading : <>{boardEmpty ? renderEmpty : renderList}} + + ); +} diff --git a/front_minimal/src/sections/mail/layout.jsx b/front_minimal/src/sections/mail/layout.jsx new file mode 100644 index 0000000..2618614 --- /dev/null +++ b/front_minimal/src/sections/mail/layout.jsx @@ -0,0 +1,47 @@ +import Stack from '@mui/material/Stack'; + +// ---------------------------------------------------------------------- + +export function Layout({ slots, sx, ...other }) { + return ( + + {slots.header} + + + + {slots.nav} + + + + {slots.list} + + + + {slots.details} + + + + ); +} diff --git a/front_minimal/src/sections/mail/mail-compose.jsx b/front_minimal/src/sections/mail/mail-compose.jsx new file mode 100644 index 0000000..11daf4b --- /dev/null +++ b/front_minimal/src/sections/mail/mail-compose.jsx @@ -0,0 +1,154 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Paper from '@mui/material/Paper'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Portal from '@mui/material/Portal'; +import Backdrop from '@mui/material/Backdrop'; +import InputBase from '@mui/material/InputBase'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useResponsive } from 'src/hooks/use-responsive'; + +import { varAlpha } from 'src/theme/styles'; + +import { Editor } from 'src/components/editor'; +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +const POSITION = 20; + +// ---------------------------------------------------------------------- + +export function MailCompose({ onCloseCompose }) { + const smUp = useResponsive('up', 'sm'); + + const fullScreen = useBoolean(); + + const [message, setMessage] = useState(''); + + const handleChangeMessage = useCallback((value) => { + setMessage(value); + }, []); + + return ( + + {(fullScreen.value || !smUp) && ( + theme.zIndex.modal - 1 }} /> + )} + + theme.zIndex.modal, + width: `calc(100% - ${POSITION * 2}px)`, + boxShadow: (theme) => theme.customShadows.dropdown, + ...(fullScreen.value && { + maxWidth: 1, + height: `calc(100% - ${POSITION * 2}px)`, + }), + }} + > + theme.spacing(1.5, 1, 1.5, 2) }} + > + + New message + + + + + + + + + + + + + Cc + Bcc + + } + sx={{ + px: 2, + height: 48, + borderBottom: (theme) => + `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.08)}`, + }} + /> + + + `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.08)}`, + }} + /> + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/mail/mail-details.jsx b/front_minimal/src/sections/mail/mail-details.jsx new file mode 100644 index 0000000..b8c9562 --- /dev/null +++ b/front_minimal/src/sections/mail/mail-details.jsx @@ -0,0 +1,285 @@ +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Tooltip from '@mui/material/Tooltip'; +import Collapse from '@mui/material/Collapse'; +import Checkbox from '@mui/material/Checkbox'; +import ButtonBase from '@mui/material/ButtonBase'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import { darken, lighten, useTheme, alpha as hexAlpha } from '@mui/material/styles'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { fDateTime } from 'src/utils/format-time'; + +import { CONFIG } from 'src/config-global'; +import { maxLine, stylesMode } from 'src/theme/styles'; + +import { Label } from 'src/components/label'; +import { Editor } from 'src/components/editor'; +import { Iconify } from 'src/components/iconify'; +import { Markdown } from 'src/components/markdown'; +import { Scrollbar } from 'src/components/scrollbar'; +import { EmptyContent } from 'src/components/empty-content'; +import { FileThumbnail } from 'src/components/file-thumbnail'; +import { LoadingScreen } from 'src/components/loading-screen'; + +// ---------------------------------------------------------------------- + +export function MailDetails({ mail, renderLabel, empty, loading }) { + const theme = useTheme(); + + const showAttachments = useBoolean(true); + + if (loading) { + return ; + } + + if (empty || !mail) { + return ( + + ); + } + + const renderHead = ( + <> + + {mail.labelIds.map((labelId) => { + const label = renderLabel(labelId); + + return label ? ( + + ) : null; + })} + + + + } + checkedIcon={} + checked={mail.isStarred} + inputProps={{ id: 'starred-checkbox', 'aria-label': 'Starred checkbox' }} + /> + + } + checkedIcon={} + checked={mail.isImportant} + inputProps={{ id: 'important-checkbox', 'aria-label': 'Important checkbox' }} + /> + + + + + + + + + + + + + + + + + + + + + + + + + ); + + const renderSubject = ( + <> + + Re: {mail.subject} + + + + + + + + + + + + + + + + + + + {fDateTime(mail.createdAt)} + + + + ); + + const renderSender = ( + <> + + {mail.from.name.charAt(0).toUpperCase()} + + + + + + {mail.from.name} + + + {`<${mail.from.email}>`} + + + + + {`To: `} + {mail.to.map((person) => ( + + {`${person.email}, `} + + ))} + + + + ); + + const renderAttachments = ( + + + + + {mail.attachments.length} attachments + + + + + Download + + + + + + {mail.attachments.map((attachment) => ( + console.info('DOWNLOAD')} + sx={{ width: 48, height: 48, backgroundColor: 'background.neutral' }} + slotProps={{ icon: { width: 24, height: 24 } }} + /> + ))} + + + + ); + + const renderContent = ( + + ); + + const renderEditor = ( + <> + + + + + + + + + + + + + + + + + ); + + return ( + <> + + {renderHead} + + + + {renderSubject} + + + + {renderSender} + + + {!!mail.attachments.length && {renderAttachments} } + + {renderContent} + + + {renderEditor} + + + ); +} diff --git a/front_minimal/src/sections/mail/mail-header.jsx b/front_minimal/src/sections/mail/mail-header.jsx new file mode 100644 index 0000000..07ff43f --- /dev/null +++ b/front_minimal/src/sections/mail/mail-header.jsx @@ -0,0 +1,38 @@ +import Stack from '@mui/material/Stack'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function MailHeader({ onOpenNav, onOpenMail, sx, ...other }) { + return ( + + + + + + {onOpenMail && ( + + + + )} + + + + + ), + }} + sx={{ ml: 2 }} + /> + + ); +} diff --git a/front_minimal/src/sections/mail/mail-item.jsx b/front_minimal/src/sections/mail/mail-item.jsx new file mode 100644 index 0000000..b04d607 --- /dev/null +++ b/front_minimal/src/sections/mail/mail-item.jsx @@ -0,0 +1,66 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { fToNow } from 'src/utils/format-time'; + +// ---------------------------------------------------------------------- + +export function MailItem({ mail, selected, sx, ...other }) { + return ( + + + + {mail.from.name.charAt(0).toUpperCase()} + + + + + + + {fToNow(mail.createdAt)} + + + {!!mail.isUnread && ( + + )} + + + + ); +} diff --git a/front_minimal/src/sections/mail/mail-list.jsx b/front_minimal/src/sections/mail/mail-list.jsx new file mode 100644 index 0000000..f14fd98 --- /dev/null +++ b/front_minimal/src/sections/mail/mail-list.jsx @@ -0,0 +1,116 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Drawer from '@mui/material/Drawer'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +import { CONFIG } from 'src/config-global'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { EmptyContent } from 'src/components/empty-content'; + +import { MailItem } from './mail-item'; +import { MailItemSkeleton } from './mail-skeleton'; + +// ---------------------------------------------------------------------- + +export function MailList({ + empty, + mails, + loading, + openMail, + onCloseMail, + onClickMail, + selectedMailId, + selectedLabelId, +}) { + const mdUp = useResponsive('up', 'md'); + + const renderLoading = ( + + + + ); + + const renderEmpty = ( + + + + ); + + const renderList = ( + + + + ); + + const renderContent = ( + <> + + {mdUp ? ( + + + + ), + }} + /> + ) : ( + + {selectedLabelId} + + )} + + + {loading ? renderLoading : <>{empty ? renderEmpty : renderList}} + + ); + + return ( + <> + {renderContent} + + + {renderContent} + + + ); +} diff --git a/front_minimal/src/sections/mail/mail-nav-item.jsx b/front_minimal/src/sections/mail/mail-nav-item.jsx new file mode 100644 index 0000000..f3fdb64 --- /dev/null +++ b/front_minimal/src/sections/mail/mail-nav-item.jsx @@ -0,0 +1,63 @@ +import Box from '@mui/material/Box'; +import ListItemButton from '@mui/material/ListItemButton'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +const LABEL_ICONS = { + all: 'fluent:mail-24-filled', + inbox: 'solar:inbox-bold', + trash: 'solar:trash-bin-trash-bold', + drafts: 'solar:file-text-bold', + spam: 'solar:danger-bold', + sent: 'iconamoon:send-fill', + starred: 'eva:star-fill', + important: 'material-symbols:label-important-rounded', + social: 'solar:tag-horizontal-bold-duotone', + promotions: 'solar:tag-horizontal-bold-duotone', + forums: 'solar:tag-horizontal-bold-duotone', +}; + +// ---------------------------------------------------------------------- + +export function MailNavItem({ selected, label, onClickNavItem, ...other }) { + const labelIcon = LABEL_ICONS[label.id]; + + return ( + + + + + + {label.name} + + + {!!label.unreadCount && ( + + {label.unreadCount} + + )} + + + ); +} diff --git a/front_minimal/src/sections/mail/mail-nav.jsx b/front_minimal/src/sections/mail/mail-nav.jsx new file mode 100644 index 0000000..3225be7 --- /dev/null +++ b/front_minimal/src/sections/mail/mail-nav.jsx @@ -0,0 +1,102 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Drawer from '@mui/material/Drawer'; +import Button from '@mui/material/Button'; +import { useTheme } from '@mui/material/styles'; + +import { CONFIG } from 'src/config-global'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { EmptyContent } from 'src/components/empty-content'; + +import { MailNavItem } from './mail-nav-item'; +import { MailNavItemSkeleton } from './mail-skeleton'; + +// ---------------------------------------------------------------------- + +export function MailNav({ + empty, + labels, + loading, + openNav, + onCloseNav, + selectedLabelId, + onToggleCompose, + handleClickLabel, +}) { + const theme = useTheme(); + + const renderLoading = ( + + + + ); + + const renderEmpty = ( + + + + ); + + const renderList = ( + + + + ); + + const renderContent = ( + <> + + + + + {loading ? renderLoading : <>{empty ? renderEmpty : renderList}} + + ); + + return ( + <> + {renderContent} + + + {renderContent} + + + ); +} diff --git a/front_minimal/src/sections/mail/mail-skeleton.jsx b/front_minimal/src/sections/mail/mail-skeleton.jsx new file mode 100644 index 0000000..663844d --- /dev/null +++ b/front_minimal/src/sections/mail/mail-skeleton.jsx @@ -0,0 +1,45 @@ +import Stack from '@mui/material/Stack'; +import Skeleton from '@mui/material/Skeleton'; + +import { varAlpha } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +export function MailNavItemSkeleton({ amount = 6, sx, ...other }) { + return [...Array(amount)].map((_, index) => ( + varAlpha(theme.vars.palette.grey['500Channel'], 0.24), ...sx }} + {...other} + > + + + + + )); +} + +// ---------------------------------------------------------------------- + +export function MailItemSkeleton({ amount = 6, sx, ...other }) { + return [...Array(amount)].map((_, index) => ( + + + + + + + + + )); +} diff --git a/front_minimal/src/sections/mail/view/index.js b/front_minimal/src/sections/mail/view/index.js new file mode 100644 index 0000000..dad204b --- /dev/null +++ b/front_minimal/src/sections/mail/view/index.js @@ -0,0 +1 @@ +export * from './mail-view'; diff --git a/front_minimal/src/sections/mail/view/mail-view.jsx b/front_minimal/src/sections/mail/view/mail-view.jsx new file mode 100644 index 0000000..006e5e9 --- /dev/null +++ b/front_minimal/src/sections/mail/view/mail-view.jsx @@ -0,0 +1,178 @@ +'use client'; + +import { useEffect, useCallback } from 'react'; + +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; +import { useRouter, useSearchParams } from 'src/routes/hooks'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useResponsive } from 'src/hooks/use-responsive'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { useGetMail, useGetMails, useGetLabels } from 'src/actions/mail'; + +import { Layout } from '../layout'; +import { MailNav } from '../mail-nav'; +import { MailList } from '../mail-list'; +import { MailHeader } from '../mail-header'; +import { MailCompose } from '../mail-compose'; +import { MailDetails } from '../mail-details'; + +// ---------------------------------------------------------------------- + +const LABEL_INDEX = 'inbox'; + +// ---------------------------------------------------------------------- + +export function MailView() { + const router = useRouter(); + + const searchParams = useSearchParams(); + + const selectedLabelId = searchParams.get('label') ?? LABEL_INDEX; + + const selectedMailId = searchParams.get('id') ?? ''; + + const mdUp = useResponsive('up', 'md'); + + const openNav = useBoolean(); + + const openMail = useBoolean(); + + const openCompose = useBoolean(); + + const { labels, labelsLoading, labelsEmpty } = useGetLabels(); + + const { mails, mailsLoading, mailsError, mailsEmpty } = useGetMails(selectedLabelId); + + const { mail, mailLoading, mailError } = useGetMail(selectedMailId); + + const firstMailId = mails.allIds[0] || ''; + + const handleToggleCompose = useCallback(() => { + if (openNav.value) { + openNav.onFalse(); + } + openCompose.onToggle(); + }, [openCompose, openNav]); + + const handleClickLabel = useCallback( + (labelId) => { + if (!mdUp) { + openNav.onFalse(); + } + + if (labelId) { + const href = + labelId !== LABEL_INDEX + ? `${paths.dashboard.mail}?label=${labelId}` + : paths.dashboard.mail; + router.push(href); + } + }, + [openNav, router, mdUp] + ); + + const handleClickMail = useCallback( + (mailId) => { + if (!mdUp) { + openMail.onFalse(); + } + + const href = + selectedLabelId !== LABEL_INDEX + ? `${paths.dashboard.mail}?id=${mailId}&label=${selectedLabelId}` + : `${paths.dashboard.mail}?id=${mailId}`; + + router.push(href); + }, + [openMail, router, selectedLabelId, mdUp] + ); + + useEffect(() => { + if (mailsError || mailError) { + router.push(paths.dashboard.mail); + } + }, [mailError, mailsError, router]); + + useEffect(() => { + if (!selectedMailId && firstMailId) { + handleClickMail(firstMailId); + } + }, [firstMailId, handleClickMail, selectedMailId]); + + useEffect(() => { + if (openCompose.value) { + document.body.style.overflow = 'hidden'; + } else { + document.body.style.overflow = ''; + } + }, [openCompose.value]); + + return ( + <> + + + Mail + + + + ), + nav: ( + + ), + list: ( + + ), + details: ( + labels.filter((label) => label.id === id)[0]} + /> + ), + }} + /> + + + {openCompose.value && } + + ); +} diff --git a/front_minimal/src/sections/maintenance/view.jsx b/front_minimal/src/sections/maintenance/view.jsx new file mode 100644 index 0000000..c5e50ea --- /dev/null +++ b/front_minimal/src/sections/maintenance/view.jsx @@ -0,0 +1,31 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import Typography from '@mui/material/Typography'; + +import { RouterLink } from 'src/routes/components'; + +import { MaintenanceIllustration } from 'src/assets/illustrations'; + +// ---------------------------------------------------------------------- + +export function MaintenanceView() { + return ( + + + Website currently under maintenance + + + + We are currently working hard on this page! + + + + + + + ); +} diff --git a/front_minimal/src/sections/order/order-details-history.jsx b/front_minimal/src/sections/order/order-details-history.jsx new file mode 100644 index 0000000..8ad3c5b --- /dev/null +++ b/front_minimal/src/sections/order/order-details-history.jsx @@ -0,0 +1,97 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Paper from '@mui/material/Paper'; +import Stack from '@mui/material/Stack'; +import Timeline from '@mui/lab/Timeline'; +import TimelineDot from '@mui/lab/TimelineDot'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import TimelineContent from '@mui/lab/TimelineContent'; +import TimelineSeparator from '@mui/lab/TimelineSeparator'; +import TimelineConnector from '@mui/lab/TimelineConnector'; +import TimelineItem, { timelineItemClasses } from '@mui/lab/TimelineItem'; + +import { fDateTime } from 'src/utils/format-time'; + +// ---------------------------------------------------------------------- + +export function OrderDetailsHistory({ history }) { + const renderSummary = ( + + + Order time + {fDateTime(history?.orderTime)} + + + Payment time + {fDateTime(history?.orderTime)} + + + Delivery time for the carrier + {fDateTime(history?.orderTime)} + + + Completion time + {fDateTime(history?.orderTime)} + + + ); + + const renderTimeline = ( + + {history?.timeline.map((item, index) => { + const firstTimeline = index === 0; + + const lastTimeline = index === history.timeline.length - 1; + + return ( + + + + {lastTimeline ? null : } + + + + {item.title} + + + {fDateTime(item.time)} + + + + ); + })} + + ); + + return ( + + + + {renderTimeline} + + {renderSummary} + + + ); +} diff --git a/front_minimal/src/sections/order/order-details-info.jsx b/front_minimal/src/sections/order/order-details-info.jsx new file mode 100644 index 0000000..5956ba0 --- /dev/null +++ b/front_minimal/src/sections/order/order-details-info.jsx @@ -0,0 +1,161 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import IconButton from '@mui/material/IconButton'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function OrderDetailsInfo({ customer, delivery, payment, shippingAddress }) { + const renderCustomer = ( + <> + + + + } + /> + + + + + {customer?.name} + + {customer?.email} + +
    + IP address: + + {customer?.ipAddress} + +
    + + +
    +
    + + ); + + const renderDelivery = ( + <> + + + + } + /> + + + + Ship by + + {delivery?.shipBy} + + + + Speedy + + {delivery?.speedy} + + + + Tracking No. + + + {delivery?.trackingNumber} + + + + + ); + + const renderShipping = ( + <> + + + + } + /> + + + + Address + + {shippingAddress?.fullAddress} + + + + + Phone number + + {shippingAddress?.phoneNumber} + + + + ); + + const renderPayment = ( + <> + + + + } + /> + + {payment?.cardNumber} + + + + ); + + return ( + + {renderCustomer} + + + + {renderDelivery} + + + + {renderShipping} + + + + {renderPayment} + + ); +} diff --git a/front_minimal/src/sections/order/order-details-item.jsx b/front_minimal/src/sections/order/order-details-item.jsx new file mode 100644 index 0000000..76f42c2 --- /dev/null +++ b/front_minimal/src/sections/order/order-details-item.jsx @@ -0,0 +1,105 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import CardHeader from '@mui/material/CardHeader'; +import IconButton from '@mui/material/IconButton'; +import ListItemText from '@mui/material/ListItemText'; + +import { fCurrency } from 'src/utils/format-number'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; + +// ---------------------------------------------------------------------- + +export function OrderDetailsItems({ + taxes, + shipping, + discount, + subtotal, + items = [], + totalAmount, +}) { + const renderTotal = ( + + + Subtotal + {fCurrency(subtotal) || '-'} + + + + Shipping + + {shipping ? `- ${fCurrency(shipping)}` : '-'} + + + + + Discount + + {discount ? `- ${fCurrency(discount)}` : '-'} + + + + + Taxes + {taxes ? fCurrency(taxes) : '-'} + + + +
    Total
    + {fCurrency(totalAmount) || '-'} +
    +
    + ); + + return ( + + + + + } + /> + + + {items.map((item) => ( + `dashed 2px ${theme.vars.palette.background.neutral}`, + }} + > + + + + + x{item.quantity} + + + {fCurrency(item.price)} + + + ))} + + + {renderTotal} + + ); +} diff --git a/front_minimal/src/sections/order/order-details-toolbar.jsx b/front_minimal/src/sections/order/order-details-toolbar.jsx new file mode 100644 index 0000000..5884b95 --- /dev/null +++ b/front_minimal/src/sections/order/order-details-toolbar.jsx @@ -0,0 +1,112 @@ +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { RouterLink } from 'src/routes/components'; + +import { fDateTime } from 'src/utils/format-time'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function OrderDetailsToolbar({ + status, + backLink, + createdAt, + orderNumber, + statusOptions, + onChangeStatus, +}) { + const popover = usePopover(); + + return ( + <> + + + + + + + + + Order {orderNumber} + + + + + {fDateTime(createdAt)} + + + + + + + + + + + + + + + + {statusOptions.map((option) => ( + { + popover.onClose(); + onChangeStatus(option.value); + }} + > + {option.label} + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/order/order-table-filters-result.jsx b/front_minimal/src/sections/order/order-table-filters-result.jsx new file mode 100644 index 0000000..dc37b41 --- /dev/null +++ b/front_minimal/src/sections/order/order-table-filters-result.jsx @@ -0,0 +1,59 @@ +import { useCallback } from 'react'; + +import Chip from '@mui/material/Chip'; + +import { fDateRangeShortLabel } from 'src/utils/format-time'; + +import { chipProps, FiltersBlock, FiltersResult } from 'src/components/filters-result'; + +// ---------------------------------------------------------------------- + +export function OrderTableFiltersResult({ filters, totalResults, onResetPage, sx }) { + const handleRemoveKeyword = useCallback(() => { + onResetPage(); + filters.setState({ name: '' }); + }, [filters, onResetPage]); + + const handleRemoveStatus = useCallback(() => { + onResetPage(); + filters.setState({ status: 'all' }); + }, [filters, onResetPage]); + + const handleRemoveDate = useCallback(() => { + onResetPage(); + filters.setState({ startDate: null, endDate: null }); + }, [filters, onResetPage]); + + const handleReset = useCallback(() => { + onResetPage(); + filters.onResetState(); + }, [filters, onResetPage]); + + return ( + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/order/order-table-row.jsx b/front_minimal/src/sections/order/order-table-row.jsx new file mode 100644 index 0000000..df8a6a9 --- /dev/null +++ b/front_minimal/src/sections/order/order-table-row.jsx @@ -0,0 +1,216 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Paper from '@mui/material/Paper'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import MenuList from '@mui/material/MenuList'; +import Collapse from '@mui/material/Collapse'; +import MenuItem from '@mui/material/MenuItem'; +import TableRow from '@mui/material/TableRow'; +import Checkbox from '@mui/material/Checkbox'; +import TableCell from '@mui/material/TableCell'; +import IconButton from '@mui/material/IconButton'; +import ListItemText from '@mui/material/ListItemText'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { fCurrency } from 'src/utils/format-number'; +import { fDate, fTime } from 'src/utils/format-time'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function OrderTableRow({ row, selected, onViewRow, onSelectRow, onDeleteRow }) { + const confirm = useBoolean(); + + const collapse = useBoolean(); + + const popover = usePopover(); + + const renderPrimary = ( + + + + + + + + {row.orderNumber} + + + + + + + + + {row.customer.name} + + {row.customer.email} + + + + + + + + + + {row.totalQuantity} + + {fCurrency(row.subtotal)} + + + + + + + + + + + + + + + + ); + + const renderSecondary = ( + + + + + {row.items.map((item) => ( + theme.spacing(1.5, 2, 1.5, 1.5), + '&:not(:last-of-type)': { + borderBottom: (theme) => `solid 2px ${theme.vars.palette.background.neutral}`, + }, + }} + > + + + + +
    x{item.quantity}
    + + {fCurrency(item.price)} +
    + ))} +
    +
    +
    +
    + ); + + return ( + <> + {renderPrimary} + + {renderSecondary} + + + + { + confirm.onTrue(); + popover.onClose(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + { + onViewRow(); + popover.onClose(); + }} + > + + View + + + + + + Delete + + } + /> + + ); +} diff --git a/front_minimal/src/sections/order/order-table-toolbar.jsx b/front_minimal/src/sections/order/order-table-toolbar.jsx new file mode 100644 index 0000000..100fb0f --- /dev/null +++ b/front_minimal/src/sections/order/order-table-toolbar.jsx @@ -0,0 +1,138 @@ +import { useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import InputAdornment from '@mui/material/InputAdornment'; +import { DatePicker } from '@mui/x-date-pickers/DatePicker'; +import { formHelperTextClasses } from '@mui/material/FormHelperText'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function OrderTableToolbar({ filters, onResetPage, dateError }) { + const popover = usePopover(); + + const handleFilterName = useCallback( + (event) => { + onResetPage(); + filters.setState({ name: event.target.value }); + }, + [filters, onResetPage] + ); + + const handleFilterStartDate = useCallback( + (newValue) => { + onResetPage(); + filters.setState({ startDate: newValue }); + }, + [filters, onResetPage] + ); + + const handleFilterEndDate = useCallback( + (newValue) => { + onResetPage(); + filters.setState({ endDate: newValue }); + }, + [filters, onResetPage] + ); + + return ( + <> + + + + + + + + + + ), + }} + /> + + + + + + + + + + { + popover.onClose(); + }} + > + + Print + + + { + popover.onClose(); + }} + > + + Import + + + { + popover.onClose(); + }} + > + + Export + + + + + ); +} diff --git a/front_minimal/src/sections/order/view/index.js b/front_minimal/src/sections/order/view/index.js new file mode 100644 index 0000000..b51bcd6 --- /dev/null +++ b/front_minimal/src/sections/order/view/index.js @@ -0,0 +1,3 @@ +export * from './order-list-view'; + +export * from './order-details-view'; diff --git a/front_minimal/src/sections/order/view/order-details-view.jsx b/front_minimal/src/sections/order/view/order-details-view.jsx new file mode 100644 index 0000000..edc19fb --- /dev/null +++ b/front_minimal/src/sections/order/view/order-details-view.jsx @@ -0,0 +1,65 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Grid from '@mui/material/Unstable_Grid2'; + +import { paths } from 'src/routes/paths'; + +import { ORDER_STATUS_OPTIONS } from 'src/_mock'; +import { DashboardContent } from 'src/layouts/dashboard'; + +import { OrderDetailsInfo } from '../order-details-info'; +import { OrderDetailsItems } from '../order-details-item'; +import { OrderDetailsToolbar } from '../order-details-toolbar'; +import { OrderDetailsHistory } from '../order-details-history'; + +// ---------------------------------------------------------------------- + +export function OrderDetailsView({ order }) { + const [status, setStatus] = useState(order?.status); + + const handleChangeStatus = useCallback((newValue) => { + setStatus(newValue); + }, []); + + return ( + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/order/view/order-list-view.jsx b/front_minimal/src/sections/order/view/order-list-view.jsx new file mode 100644 index 0000000..7a592b5 --- /dev/null +++ b/front_minimal/src/sections/order/view/order-list-view.jsx @@ -0,0 +1,347 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Tab from '@mui/material/Tab'; +import Box from '@mui/material/Box'; +import Tabs from '@mui/material/Tabs'; +import Card from '@mui/material/Card'; +import Table from '@mui/material/Table'; +import Button from '@mui/material/Button'; +import Tooltip from '@mui/material/Tooltip'; +import TableBody from '@mui/material/TableBody'; +import IconButton from '@mui/material/IconButton'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useSetState } from 'src/hooks/use-set-state'; + +import { fIsAfter, fIsBetween } from 'src/utils/format-time'; + +import { varAlpha } from 'src/theme/styles'; +import { DashboardContent } from 'src/layouts/dashboard'; +import { _orders, ORDER_STATUS_OPTIONS } from 'src/_mock'; + +import { Label } from 'src/components/label'; +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; +import { + useTable, + emptyRows, + rowInPage, + TableNoData, + getComparator, + TableEmptyRows, + TableHeadCustom, + TableSelectedAction, + TablePaginationCustom, +} from 'src/components/table'; + +import { OrderTableRow } from '../order-table-row'; +import { OrderTableToolbar } from '../order-table-toolbar'; +import { OrderTableFiltersResult } from '../order-table-filters-result'; + +// ---------------------------------------------------------------------- + +const STATUS_OPTIONS = [{ value: 'all', label: 'All' }, ...ORDER_STATUS_OPTIONS]; + +const TABLE_HEAD = [ + { id: 'orderNumber', label: 'Order', width: 88 }, + { id: 'name', label: 'Customer' }, + { id: 'createdAt', label: 'Date', width: 140 }, + { + id: 'totalQuantity', + label: 'Items', + width: 120, + align: 'center', + }, + { id: 'totalAmount', label: 'Price', width: 140 }, + { id: 'status', label: 'Status', width: 110 }, + { id: '', width: 88 }, +]; + +// ---------------------------------------------------------------------- + +export function OrderListView() { + const table = useTable({ defaultOrderBy: 'orderNumber' }); + + const router = useRouter(); + + const confirm = useBoolean(); + + const [tableData, setTableData] = useState(_orders); + + const filters = useSetState({ + name: '', + status: 'all', + startDate: null, + endDate: null, + }); + + const dateError = fIsAfter(filters.state.startDate, filters.state.endDate); + + const dataFiltered = applyFilter({ + inputData: tableData, + comparator: getComparator(table.order, table.orderBy), + filters: filters.state, + dateError, + }); + + const dataInPage = rowInPage(dataFiltered, table.page, table.rowsPerPage); + + const canReset = + !!filters.state.name || + filters.state.status !== 'all' || + (!!filters.state.startDate && !!filters.state.endDate); + + const notFound = (!dataFiltered.length && canReset) || !dataFiltered.length; + + const handleDeleteRow = useCallback( + (id) => { + const deleteRow = tableData.filter((row) => row.id !== id); + + toast.success('Delete success!'); + + setTableData(deleteRow); + + table.onUpdatePageDeleteRow(dataInPage.length); + }, + [dataInPage.length, table, tableData] + ); + + const handleDeleteRows = useCallback(() => { + const deleteRows = tableData.filter((row) => !table.selected.includes(row.id)); + + toast.success('Delete success!'); + + setTableData(deleteRows); + + table.onUpdatePageDeleteRows({ + totalRowsInPage: dataInPage.length, + totalRowsFiltered: dataFiltered.length, + }); + }, [dataFiltered.length, dataInPage.length, table, tableData]); + + const handleViewRow = useCallback( + (id) => { + router.push(paths.dashboard.order.details(id)); + }, + [router] + ); + + const handleFilterStatus = useCallback( + (event, newValue) => { + table.onResetPage(); + filters.setState({ status: newValue }); + }, + [filters, table] + ); + + return ( + <> + + + + + + `inset 0 -2px 0 0 ${varAlpha(theme.vars.palette.grey['500Channel'], 0.08)}`, + }} + > + {STATUS_OPTIONS.map((tab) => ( + + {['completed', 'pending', 'cancelled', 'refunded'].includes(tab.value) + ? tableData.filter((user) => user.status === tab.value).length + : tableData.length} + + } + /> + ))} + + + + + {canReset && ( + + )} + + + + table.onSelectAllRows( + checked, + dataFiltered.map((row) => row.id) + ) + } + action={ + + + + + + } + /> + + + + + table.onSelectAllRows( + checked, + dataFiltered.map((row) => row.id) + ) + } + /> + + + {dataFiltered + .slice( + table.page * table.rowsPerPage, + table.page * table.rowsPerPage + table.rowsPerPage + ) + .map((row) => ( + table.onSelectRow(row.id)} + onDeleteRow={() => handleDeleteRow(row.id)} + onViewRow={() => handleViewRow(row.id)} + /> + ))} + + + + + +
    +
    +
    + + +
    +
    + + + Are you sure want to delete {table.selected.length} items? + + } + action={ + + } + /> + + ); +} + +function applyFilter({ inputData, comparator, filters, dateError }) { + const { status, name, startDate, endDate } = filters; + + const stabilizedThis = inputData.map((el, index) => [el, index]); + + stabilizedThis.sort((a, b) => { + const order = comparator(a[0], b[0]); + if (order !== 0) return order; + return a[1] - b[1]; + }); + + inputData = stabilizedThis.map((el) => el[0]); + + if (name) { + inputData = inputData.filter( + (order) => + order.orderNumber.toLowerCase().indexOf(name.toLowerCase()) !== -1 || + order.customer.name.toLowerCase().indexOf(name.toLowerCase()) !== -1 || + order.customer.email.toLowerCase().indexOf(name.toLowerCase()) !== -1 + ); + } + + if (status !== 'all') { + inputData = inputData.filter((order) => order.status === status); + } + + if (!dateError) { + if (startDate && endDate) { + inputData = inputData.filter((order) => fIsBetween(order.createdAt, startDate, endDate)); + } + } + + return inputData; +} diff --git a/front_minimal/src/sections/overview/analytics/analytics-conversion-rates.jsx b/front_minimal/src/sections/overview/analytics/analytics-conversion-rates.jsx new file mode 100644 index 0000000..76b4502 --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/analytics-conversion-rates.jsx @@ -0,0 +1,61 @@ +import Card from '@mui/material/Card'; +import CardHeader from '@mui/material/CardHeader'; +import { useTheme, alpha as hexAlpha } from '@mui/material/styles'; + +import { fNumber } from 'src/utils/format-number'; + +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function AnalyticsConversionRates({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [ + theme.palette.primary.dark, + hexAlpha(theme.palette.primary.dark, 0.24), + ]; + + const chartOptions = useChart({ + colors: chartColors, + stroke: { width: 2, colors: ['transparent'] }, + tooltip: { + shared: true, + intersect: false, + y: { + formatter: (value) => fNumber(value), + title: { formatter: (seriesName) => `${seriesName}: ` }, + }, + }, + xaxis: { categories: chart.categories }, + dataLabels: { + enabled: true, + offsetX: -6, + style: { fontSize: '10px', colors: ['#FFFFFF', theme.palette.text.primary] }, + }, + plotOptions: { + bar: { + horizontal: true, + borderRadius: 2, + barHeight: '48%', + dataLabels: { position: 'top' }, + }, + }, + ...chart.options, + }); + + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/analytics/analytics-current-subject.jsx b/front_minimal/src/sections/overview/analytics/analytics-current-subject.jsx new file mode 100644 index 0000000..f0ae223 --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/analytics-current-subject.jsx @@ -0,0 +1,53 @@ +import Card from '@mui/material/Card'; +import Divider from '@mui/material/Divider'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; + +import { Chart, useChart, ChartLegends } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function AnalyticsCurrentSubject({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [ + theme.palette.primary.main, + theme.palette.warning.main, + theme.palette.info.main, + ]; + + const chartOptions = useChart({ + colors: chartColors, + stroke: { width: 2 }, + fill: { opacity: 0.48 }, + xaxis: { + categories: chart.categories, + labels: { style: { colors: [...Array(6)].map(() => theme.palette.text.secondary) } }, + }, + ...chart.options, + }); + + return ( + + + + + + + + item.name)} + colors={chartOptions?.colors} + sx={{ p: 3, justifyContent: 'center' }} + /> + + ); +} diff --git a/front_minimal/src/sections/overview/analytics/analytics-current-visits.jsx b/front_minimal/src/sections/overview/analytics/analytics-current-visits.jsx new file mode 100644 index 0000000..1d7e986 --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/analytics-current-visits.jsx @@ -0,0 +1,62 @@ +import Card from '@mui/material/Card'; +import Divider from '@mui/material/Divider'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; + +import { fNumber } from 'src/utils/format-number'; + +import { Chart, useChart, ChartLegends } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function AnalyticsCurrentVisits({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const chartSeries = chart.series.map((item) => item.value); + + const chartColors = chart.colors ?? [ + theme.palette.primary.main, + theme.palette.warning.light, + theme.palette.info.dark, + theme.palette.error.main, + ]; + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + colors: chartColors, + labels: chart.series.map((item) => item.label), + stroke: { width: 0 }, + dataLabels: { enabled: true, dropShadow: { enabled: false } }, + tooltip: { + y: { + formatter: (value) => fNumber(value), + title: { formatter: (seriesName) => `${seriesName}` }, + }, + }, + plotOptions: { pie: { donut: { labels: { show: false } } } }, + ...chart.options, + }); + + return ( + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/analytics/analytics-news.jsx b/front_minimal/src/sections/overview/analytics/analytics-news.jsx new file mode 100644 index 0000000..71fd0ce --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/analytics-news.jsx @@ -0,0 +1,74 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import CardHeader from '@mui/material/CardHeader'; +import ListItemText from '@mui/material/ListItemText'; + +import { fToNow } from 'src/utils/format-time'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; + +// ---------------------------------------------------------------------- + +export function AnalyticsNews({ title, subheader, list, ...other }) { + return ( + + + + + + {list.map((item) => ( + + ))} + + + + + + + + ); +} + +function Item({ item, sx, ...other }) { + return ( + `dashed 1px ${theme.vars.palette.divider}`, + ...sx, + }} + {...other} + > + + + + + + {fToNow(item.postedAt)} + + + ); +} diff --git a/front_minimal/src/sections/overview/analytics/analytics-order-timeline.jsx b/front_minimal/src/sections/overview/analytics/analytics-order-timeline.jsx new file mode 100644 index 0000000..70a0f84 --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/analytics-order-timeline.jsx @@ -0,0 +1,63 @@ +import Card from '@mui/material/Card'; +import Timeline from '@mui/lab/Timeline'; +import TimelineDot from '@mui/lab/TimelineDot'; +import Typography from '@mui/material/Typography'; +import CardHeader from '@mui/material/CardHeader'; +import TimelineContent from '@mui/lab/TimelineContent'; +import TimelineSeparator from '@mui/lab/TimelineSeparator'; +import TimelineConnector from '@mui/lab/TimelineConnector'; +import TimelineItem, { timelineItemClasses } from '@mui/lab/TimelineItem'; + +import { fDateTime } from 'src/utils/format-time'; + +// ---------------------------------------------------------------------- + +export function AnalyticsOrderTimeline({ title, subheader, list, ...other }) { + return ( + + + + + {list.map((item, index) => ( + + ))} + + + ); +} + +function Item({ item, lastItem, ...other }) { + return ( + + + + {lastItem ? null : } + + + + {item.title} + + + {fDateTime(item.time)} + + + + ); +} diff --git a/front_minimal/src/sections/overview/analytics/analytics-tasks.jsx b/front_minimal/src/sections/overview/analytics/analytics-tasks.jsx new file mode 100644 index 0000000..fece485 --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/analytics-tasks.jsx @@ -0,0 +1,140 @@ +import { useState } from 'react'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import Checkbox from '@mui/material/Checkbox'; +import IconButton from '@mui/material/IconButton'; +import CardHeader from '@mui/material/CardHeader'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function AnalyticsTasks({ title, subheader, list, ...other }) { + const [selected, setSelected] = useState(['2']); + + const handleClickComplete = (taskId) => { + const tasksCompleted = selected.includes(taskId) + ? selected.filter((value) => value !== taskId) + : [...selected, taskId]; + + setSelected(tasksCompleted); + }; + + return ( + + + + + } sx={{ minWidth: 560 }}> + {list.map((item) => ( + handleClickComplete(item.id)} + /> + ))} + + + + ); +} + +function Item({ item, checked, onChange, sx, ...other }) { + const popover = usePopover(); + + const handleMarkComplete = () => { + popover.onClose(); + console.info('MARK COMPLETE', item.id); + }; + + const handleShare = () => { + popover.onClose(); + console.info('SHARE', item.id); + }; + + const handleEdit = () => { + popover.onClose(); + console.info('EDIT', item.id); + }; + + const handleDelete = () => { + popover.onClose(); + console.info('DELETE', item.id); + }; + + return ( + <> + + + } + label={item.name} + sx={{ flexGrow: 1, m: 0 }} + /> + + + + + + + + + + + Mark Complete + + + + + Edit + + + + + Share + + + + + + + Delete + + + + + ); +} diff --git a/front_minimal/src/sections/overview/analytics/analytics-traffic-by-site.jsx b/front_minimal/src/sections/overview/analytics/analytics-traffic-by-site.jsx new file mode 100644 index 0000000..df06dff --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/analytics-traffic-by-site.jsx @@ -0,0 +1,50 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; + +import { fShortenNumber } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +import { SocialIcon } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function AnalyticsTrafficBySite({ title, subheader, list, ...other }) { + const theme = useTheme(); + + return ( + + + + + {list.map((site) => ( + + + + + {fShortenNumber(site.total)} + + + + {site.label} + + + ))} + + + ); +} diff --git a/front_minimal/src/sections/overview/analytics/analytics-website-visits.jsx b/front_minimal/src/sections/overview/analytics/analytics-website-visits.jsx new file mode 100644 index 0000000..7689205 --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/analytics-website-visits.jsx @@ -0,0 +1,51 @@ +import Card from '@mui/material/Card'; +import CardHeader from '@mui/material/CardHeader'; +import { useTheme, alpha as hexAlpha } from '@mui/material/styles'; + +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function AnalyticsWebsiteVisits({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [ + hexAlpha(theme.palette.primary.dark, 0.8), + hexAlpha(theme.palette.warning.main, 0.8), + ]; + + const chartOptions = useChart({ + colors: chartColors, + stroke: { + width: 2, + colors: ['transparent'], + }, + xaxis: { + categories: chart.categories, + }, + legend: { + show: true, + }, + tooltip: { + y: { + formatter: (value) => `${value} visits`, + }, + }, + ...chart.options, + }); + + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/analytics/analytics-widget-summary.jsx b/front_minimal/src/sections/overview/analytics/analytics-widget-summary.jsx new file mode 100644 index 0000000..ec339f2 --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/analytics-widget-summary.jsx @@ -0,0 +1,123 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; + +import { fNumber, fPercent, fShortenNumber } from 'src/utils/format-number'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, bgGradient } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { SvgColor } from 'src/components/svg-color'; +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function AnalyticsWidgetSummary({ + icon, + title, + total, + chart, + percent, + color = 'primary', + sx, + ...other +}) { + const theme = useTheme(); + + const chartColors = [theme.palette[color].dark]; + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + colors: chartColors, + xaxis: { categories: chart.categories }, + grid: { + padding: { + top: 6, + left: 6, + right: 6, + bottom: 6, + }, + }, + tooltip: { + y: { formatter: (value) => fNumber(value), title: { formatter: () => '' } }, + }, + ...chart.options, + }); + + const renderTrending = ( + + + + {percent > 0 && '+'} + {fPercent(percent)} + + + ); + + return ( + + {icon} + + {renderTrending} + + + + {title} + {fShortenNumber(total)} + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/analytics/view/index.js b/front_minimal/src/sections/overview/analytics/view/index.js new file mode 100644 index 0000000..fb212b4 --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/view/index.js @@ -0,0 +1 @@ +export * from './overview-analytics-view'; diff --git a/front_minimal/src/sections/overview/analytics/view/overview-analytics-view.jsx b/front_minimal/src/sections/overview/analytics/view/overview-analytics-view.jsx new file mode 100644 index 0000000..8c5fe85 --- /dev/null +++ b/front_minimal/src/sections/overview/analytics/view/overview-analytics-view.jsx @@ -0,0 +1,178 @@ +'use client'; + +import Grid from '@mui/material/Unstable_Grid2'; +import Typography from '@mui/material/Typography'; + +import { CONFIG } from 'src/config-global'; +import { DashboardContent } from 'src/layouts/dashboard'; +import { + _analyticTasks, + _analyticPosts, + _analyticTraffic, + _analyticOrderTimeline, +} from 'src/_mock'; + +import { AnalyticsNews } from '../analytics-news'; +import { AnalyticsTasks } from '../analytics-tasks'; +import { AnalyticsCurrentVisits } from '../analytics-current-visits'; +import { AnalyticsOrderTimeline } from '../analytics-order-timeline'; +import { AnalyticsWebsiteVisits } from '../analytics-website-visits'; +import { AnalyticsWidgetSummary } from '../analytics-widget-summary'; +import { AnalyticsTrafficBySite } from '../analytics-traffic-by-site'; +import { AnalyticsCurrentSubject } from '../analytics-current-subject'; +import { AnalyticsConversionRates } from '../analytics-conversion-rates'; + +// ---------------------------------------------------------------------- + +export function OverviewAnalyticsView() { + return ( + + + Hi, Welcome back 👋 + + + + + + } + chart={{ + categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug'], + series: [22, 8, 35, 50, 82, 84, 77, 12], + }} + /> + + + + + } + chart={{ + categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug'], + series: [56, 47, 40, 62, 73, 30, 23, 54], + }} + /> + + + + + } + chart={{ + categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug'], + series: [40, 70, 50, 28, 70, 75, 7, 64], + }} + /> + + + + + } + chart={{ + categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug'], + series: [56, 30, 23, 54, 47, 40, 62, 73], + }} + /> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/app/app-area-installed.jsx b/front_minimal/src/sections/overview/app/app-area-installed.jsx new file mode 100644 index 0000000..45c9702 --- /dev/null +++ b/front_minimal/src/sections/overview/app/app-area-installed.jsx @@ -0,0 +1,76 @@ +import { useState, useCallback } from 'react'; + +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; + +import { fNumber, fShortenNumber } from 'src/utils/format-number'; + +import { Chart, useChart, ChartSelect, ChartLegends } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function AppAreaInstalled({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const [selectedSeries, setSelectedSeries] = useState('2023'); + + const chartColors = chart.colors ?? [ + theme.palette.primary.dark, + theme.palette.warning.main, + theme.palette.info.main, + ]; + + const chartOptions = useChart({ + chart: { stacked: true }, + colors: chartColors, + stroke: { width: 0 }, + xaxis: { categories: chart.categories }, + tooltip: { y: { formatter: (value) => fNumber(value) } }, + plotOptions: { bar: { columnWidth: '40%' } }, + ...chart.options, + }); + + const handleChangeSeries = useCallback((newValue) => { + setSelectedSeries(newValue); + }, []); + + const currentSeries = chart.series.find((i) => i.name === selectedSeries); + + return ( + + item.name)} + value={selectedSeries} + onChange={handleChangeSeries} + /> + } + sx={{ mb: 3 }} + /> + + item.name)} + values={[fShortenNumber(1234), fShortenNumber(6789), fShortenNumber(1012)]} + sx={{ + px: 3, + gap: 3, + }} + /> + + + + ); +} diff --git a/front_minimal/src/sections/overview/app/app-current-download.jsx b/front_minimal/src/sections/overview/app/app-current-download.jsx new file mode 100644 index 0000000..5009d0c --- /dev/null +++ b/front_minimal/src/sections/overview/app/app-current-download.jsx @@ -0,0 +1,76 @@ +import Card from '@mui/material/Card'; +import Divider from '@mui/material/Divider'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; + +import { fNumber } from 'src/utils/format-number'; + +import { Chart, useChart, ChartLegends } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function AppCurrentDownload({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [ + theme.palette.primary.lighter, + theme.palette.primary.light, + theme.palette.primary.dark, + theme.palette.primary.darker, + ]; + + const chartSeries = chart.series.map((item) => item.value); + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + colors: chartColors, + labels: chart.series.map((item) => item.label), + stroke: { width: 0 }, + tooltip: { + y: { + formatter: (value) => fNumber(value), + title: { formatter: (seriesName) => `${seriesName}` }, + }, + }, + plotOptions: { + pie: { + donut: { + size: '72%', + labels: { + value: { formatter: (value) => fNumber(value) }, + total: { + formatter: (w) => { + const sum = w.globals.seriesTotals.reduce((a, b) => a + b, 0); + return fNumber(sum); + }, + }, + }, + }, + }, + }, + ...chart.options, + }); + + return ( + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/app/app-featured.jsx b/front_minimal/src/sections/overview/app/app-featured.jsx new file mode 100644 index 0000000..86e18b9 --- /dev/null +++ b/front_minimal/src/sections/overview/app/app-featured.jsx @@ -0,0 +1,94 @@ +import Autoplay from 'embla-carousel-autoplay'; + +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Typography from '@mui/material/Typography'; + +import { varAlpha } from 'src/theme/styles'; + +import { Image } from 'src/components/image'; +import { + Carousel, + useCarousel, + CarouselDotButtons, + CarouselArrowBasicButtons, +} from 'src/components/carousel'; + +// ---------------------------------------------------------------------- + +export function AppFeatured({ list, sx, ...other }) { + const carousel = useCarousel({ loop: true }, [Autoplay({ playOnInit: true, delay: 8000 })]); + + return ( + + + + + + + {list.map((item) => ( + + ))} + + + ); +} + +// ---------------------------------------------------------------------- + +function CarouselItem({ item, ...other }) { + return ( + + + + Featured App + + + + {item.title} + + + + {item.description} + + + + {item.title} + `linear-gradient(to bottom, ${varAlpha(theme.vars.palette.common.blackChannel, 0)} 0%, ${theme.vars.palette.common.black} 75%)`, + }, + }} + sx={{ + width: 1, + height: { xs: 288, xl: 320 }, + }} + /> + + ); +} diff --git a/front_minimal/src/sections/overview/app/app-new-invoice.jsx b/front_minimal/src/sections/overview/app/app-new-invoice.jsx new file mode 100644 index 0000000..bf80038 --- /dev/null +++ b/front_minimal/src/sections/overview/app/app-new-invoice.jsx @@ -0,0 +1,140 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Table from '@mui/material/Table'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import TableRow from '@mui/material/TableRow'; +import TableBody from '@mui/material/TableBody'; +import TableCell from '@mui/material/TableCell'; +import CardHeader from '@mui/material/CardHeader'; +import IconButton from '@mui/material/IconButton'; + +import { fCurrency } from 'src/utils/format-number'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { TableHeadCustom } from 'src/components/table'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function AppNewInvoice({ title, subheader, tableData, headLabel, ...other }) { + return ( + + + + + + + + + {tableData.map((row) => ( + + ))} + +
    +
    + + + + + + +
    + ); +} + +function RowItem({ row }) { + const popover = usePopover(); + + const handleDownload = () => { + popover.onClose(); + console.info('DOWNLOAD', row.id); + }; + + const handlePrint = () => { + popover.onClose(); + console.info('PRINT', row.id); + }; + + const handleShare = () => { + popover.onClose(); + console.info('SHARE', row.id); + }; + + const handleDelete = () => { + popover.onClose(); + console.info('DELETE', row.id); + }; + + return ( + <> + + {row.invoiceNumber} + + {row.category} + + {fCurrency(row.price)} + + + + + + + + + + + + + + + + + Download + + + + + Print + + + + + Share + + + + + + + Delete + + + + + ); +} diff --git a/front_minimal/src/sections/overview/app/app-top-authors.jsx b/front_minimal/src/sections/overview/app/app-top-authors.jsx new file mode 100644 index 0000000..78dd53f --- /dev/null +++ b/front_minimal/src/sections/overview/app/app-top-authors.jsx @@ -0,0 +1,90 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Avatar from '@mui/material/Avatar'; +import CardHeader from '@mui/material/CardHeader'; + +import { orderBy } from 'src/utils/helper'; +import { fShortenNumber } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function AppTopAuthors({ title, subheader, list, ...other }) { + return ( + + + + + {orderBy(list, ['totalFavorites'], ['desc']).map((item, index) => ( + + ))} + + + ); +} + +function Item({ item, index, sx, ...other }) { + return ( + + + + + {item.name} + + + {fShortenNumber(item.totalFavorites)} + + + + varAlpha(theme.vars.palette.primary.mainChannel, 0.08), + ...(index === 1 && { + color: 'info.main', + bgcolor: (theme) => varAlpha(theme.vars.palette.info.mainChannel, 0.08), + }), + ...(index === 2 && { + color: 'error.main', + bgcolor: (theme) => varAlpha(theme.vars.palette.error.mainChannel, 0.08), + }), + }} + > + + + + ); +} diff --git a/front_minimal/src/sections/overview/app/app-top-installed-countries.jsx b/front_minimal/src/sections/overview/app/app-top-installed-countries.jsx new file mode 100644 index 0000000..e1c830c --- /dev/null +++ b/front_minimal/src/sections/overview/app/app-top-installed-countries.jsx @@ -0,0 +1,79 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; + +import { fShortenNumber } from 'src/utils/format-number'; + +import { Scrollbar } from 'src/components/scrollbar'; +import { Iconify, FlagIcon } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function AppTopInstalledCountries({ title, subheader, list, ...other }) { + return ( + + + + + + {list.map((item) => ( + + ))} + + + + ); +} + +// ---------------------------------------------------------------------- + +function Item({ item, sx, ...other }) { + const largeItem = ( + + + + {item.countryName} + + + ); + + const smallItem = (icon, system) => ( + + + {fShortenNumber(system)} + + ); + + return ( + + {largeItem} + {smallItem('ant-design:android-filled', item.android)} + {smallItem('mingcute:windows-fill', item.windows)} + {smallItem('mingcute:apple-fill', item.apple)} + + ); +} diff --git a/front_minimal/src/sections/overview/app/app-top-related.jsx b/front_minimal/src/sections/overview/app/app-top-related.jsx new file mode 100644 index 0000000..7e6c2bd --- /dev/null +++ b/front_minimal/src/sections/overview/app/app-top-related.jsx @@ -0,0 +1,123 @@ +import Box from '@mui/material/Box'; +import Tab from '@mui/material/Tab'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Rating from '@mui/material/Rating'; +import Avatar from '@mui/material/Avatar'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import { svgIconClasses } from '@mui/material/SvgIcon'; + +import { useTabs } from 'src/hooks/use-tabs'; + +import { fData, fCurrency, fShortenNumber } from 'src/utils/format-number'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { CustomTabs } from 'src/components/custom-tabs'; + +// ---------------------------------------------------------------------- + +const TABS = [ + { value: '7days', label: 'Top 7 days' }, + { value: '30days', label: 'Top 30 days' }, + { value: 'all', label: 'All times' }, +]; + +// ---------------------------------------------------------------------- + +export function AppTopRelated({ title, subheader, list, ...other }) { + const tabs = useTabs('7days'); + + const renderTabs = ( + + {TABS.map((tab) => ( + + ))} + + ); + + return ( + + + + {renderTabs} + + + + {list.map((item) => ( + + ))} + + + + ); +} + +function Item({ item, sx, ...other }) { + return ( + + + +
    + + + {item.name} + + + + + + + } + sx={{ typography: 'caption' }} + > + + + {fShortenNumber(item.downloaded)} + + + + + {fData(item.size)} + + + + + {fShortenNumber(item.totalReviews)} + + +
    +
    + ); +} diff --git a/front_minimal/src/sections/overview/app/app-welcome.jsx b/front_minimal/src/sections/overview/app/app-welcome.jsx new file mode 100644 index 0000000..4a27e48 --- /dev/null +++ b/front_minimal/src/sections/overview/app/app-welcome.jsx @@ -0,0 +1,63 @@ +import Box from '@mui/material/Box'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, bgGradient } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +export function AppWelcome({ title, description, action, img, sx, ...other }) { + const theme = useTheme(); + + return ( + + + + {title} + + + + {description} + + + {action && action} + + + {img && {img}} + + ); +} diff --git a/front_minimal/src/sections/overview/app/app-widget-summary.jsx b/front_minimal/src/sections/overview/app/app-widget-summary.jsx new file mode 100644 index 0000000..5317a05 --- /dev/null +++ b/front_minimal/src/sections/overview/app/app-widget-summary.jsx @@ -0,0 +1,76 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; + +import { fNumber, fPercent } from 'src/utils/format-number'; + +import { Iconify } from 'src/components/iconify'; +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function AppWidgetSummary({ title, percent, total, chart, sx, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [theme.palette.primary.main]; + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + colors: chartColors, + stroke: { width: 0 }, + xaxis: { categories: chart.categories }, + tooltip: { + y: { formatter: (value) => fNumber(value), title: { formatter: () => '' } }, + }, + plotOptions: { bar: { borderRadius: 1.5, columnWidth: '64%' } }, + ...chart.options, + }); + + const renderTrending = ( + + + + + {percent > 0 && '+'} + {fPercent(percent)} + + + last 7 days + + + ); + + return ( + + + {title} + {fNumber(total)} + {renderTrending} + + + + + ); +} diff --git a/front_minimal/src/sections/overview/app/app-widget.jsx b/front_minimal/src/sections/overview/app/app-widget.jsx new file mode 100644 index 0000000..f4527cb --- /dev/null +++ b/front_minimal/src/sections/overview/app/app-widget.jsx @@ -0,0 +1,108 @@ +import Box from '@mui/material/Box'; +import { useTheme } from '@mui/material/styles'; + +import { fNumber } from 'src/utils/format-number'; + +import { CONFIG } from 'src/config-global'; + +import { Iconify } from 'src/components/iconify'; +import { SvgColor } from 'src/components/svg-color'; +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function AppWidget({ title, total, icon, chart, sx, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [theme.palette.primary.light, theme.palette.primary.main]; + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + stroke: { width: 0 }, + fill: { + type: 'gradient', + gradient: { + colorStops: [ + { offset: 0, color: chartColors[0], opacity: 1 }, + { offset: 100, color: chartColors[1], opacity: 1 }, + ], + }, + }, + plotOptions: { + radialBar: { + dataLabels: { + name: { show: false }, + value: { + offsetY: 6, + color: theme.vars.palette.common.white, + fontSize: theme.typography.subtitle2.fontSize, + }, + }, + }, + }, + ...chart.options, + }); + + return ( + + + + + + + +
    + {fNumber(total)} + {title} +
    + + +
    + ); +} diff --git a/front_minimal/src/sections/overview/app/view/index.js b/front_minimal/src/sections/overview/app/view/index.js new file mode 100644 index 0000000..3a99597 --- /dev/null +++ b/front_minimal/src/sections/overview/app/view/index.js @@ -0,0 +1 @@ +export * from './overview-app-view'; diff --git a/front_minimal/src/sections/overview/app/view/overview-app-view.jsx b/front_minimal/src/sections/overview/app/view/overview-app-view.jsx new file mode 100644 index 0000000..212363d --- /dev/null +++ b/front_minimal/src/sections/overview/app/view/overview-app-view.jsx @@ -0,0 +1,206 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import { useTheme } from '@mui/material/styles'; +import Grid from '@mui/material/Unstable_Grid2'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { SeoIllustration } from 'src/assets/illustrations'; +import { _appAuthors, _appRelated, _appFeatured, _appInvoices, _appInstalled } from 'src/_mock'; + +import { svgColorClasses } from 'src/components/svg-color'; + +import { useMockedUser } from 'src/auth/hooks'; + +import { AppWidget } from '../app-widget'; +import { AppWelcome } from '../app-welcome'; +import { AppFeatured } from '../app-featured'; +import { AppNewInvoice } from '../app-new-invoice'; +import { AppTopAuthors } from '../app-top-authors'; +import { AppTopRelated } from '../app-top-related'; +import { AppAreaInstalled } from '../app-area-installed'; +import { AppWidgetSummary } from '../app-widget-summary'; +import { AppCurrentDownload } from '../app-current-download'; +import { AppTopInstalledCountries } from '../app-top-installed-countries'; + +// ---------------------------------------------------------------------- + +export function OverviewAppView() { + const { user } = useMockedUser(); + + const theme = useTheme(); + + return ( + + + + } + action={ + + } + /> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/banking/banking-balance-statistics.jsx b/front_minimal/src/sections/overview/banking/banking-balance-statistics.jsx new file mode 100644 index 0000000..da26bed --- /dev/null +++ b/front_minimal/src/sections/overview/banking/banking-balance-statistics.jsx @@ -0,0 +1,71 @@ +import { useState, useCallback } from 'react'; + +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; + +import { fPercent, fCurrency } from 'src/utils/format-number'; + +import { Chart, useChart, ChartSelect, ChartLegends } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function BankingBalanceStatistics({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const [selectedSeries, setSelectedSeries] = useState('Yearly'); + + const currentSeries = chart.series.find((i) => i.name === selectedSeries); + + const chartColors = chart.colors ?? [ + theme.palette.primary.dark, + theme.palette.warning.main, + theme.palette.info.main, + ]; + + const chartOptions = useChart({ + stroke: { width: 2, colors: ['transparent'] }, + colors: chartColors, + xaxis: { categories: currentSeries?.categories }, + tooltip: { y: { formatter: (value) => fCurrency(value) } }, + ...chart.options, + }); + + const handleChangeSeries = useCallback((newValue) => { + setSelectedSeries(newValue); + }, []); + + return ( + + item.name)} + value={selectedSeries} + onChange={handleChangeSeries} + /> + } + sx={{ mb: 3 }} + /> + + item.name)} + sublabels={[`+${fPercent(43)}`, `+${fPercent(3)}`, `+${fPercent(8)}`]} + values={[fCurrency(6789), fCurrency(1234), fCurrency(1012)]} + sx={{ px: 3, gap: 3 }} + /> + + + + ); +} diff --git a/front_minimal/src/sections/overview/banking/banking-contacts.jsx b/front_minimal/src/sections/overview/banking/banking-contacts.jsx new file mode 100644 index 0000000..af7f545 --- /dev/null +++ b/front_minimal/src/sections/overview/banking/banking-contacts.jsx @@ -0,0 +1,65 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Tooltip from '@mui/material/Tooltip'; +import IconButton from '@mui/material/IconButton'; +import CardHeader from '@mui/material/CardHeader'; +import ListItemText from '@mui/material/ListItemText'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; + +// ---------------------------------------------------------------------- + +export function BankingContacts({ title, subheader, list, ...other }) { + return ( + + } + > + View all + + } + /> + + + + {list.map((item) => ( + + ))} + + + + ); +} + +function Item({ item, sx, ...other }) { + return ( + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/banking/banking-current-balance.jsx b/front_minimal/src/sections/overview/banking/banking-current-balance.jsx new file mode 100644 index 0000000..d8f040a --- /dev/null +++ b/front_minimal/src/sections/overview/banking/banking-current-balance.jsx @@ -0,0 +1,172 @@ +import { useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { fCurrency } from 'src/utils/format-number'; + +import { CONFIG } from 'src/config-global'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; +import { Carousel, useCarousel, CarouselDotButtons } from 'src/components/carousel'; + +// ---------------------------------------------------------------------- + +export function BankingCurrentBalance({ list, sx, ...other }) { + const currency = useBoolean(); + + const carousel = useCarousel(); + + return ( + + + + + {list.map((item) => ( + + ))} + + + ); +} + +// ---------------------------------------------------------------------- + +function Item({ item, showCurrency, onToggleCurrency }) { + const popover = usePopover(); + + const handleDelete = useCallback(() => { + popover.onClose(); + console.info('DELETE', item.id); + }, [item.id, popover]); + + const handleEdit = useCallback(() => { + popover.onClose(); + console.info('EDIT', item.id); + }, [item.id, popover]); + + return ( + <> + + + + + +
    + Current balance + + + + {showCurrency ? '********' : fCurrency(item.balance)} + + + + + + +
    + + + + {item.cardType === 'mastercard' && } + {item.cardType === 'visa' && } + + {item.cardNumber} + + + +
    + Card holder + {item.cardHolder} +
    +
    + Expiration date + {item.cardValid} +
    +
    +
    + + + + + + Delete + + + + + Edit + + + + + ); +} diff --git a/front_minimal/src/sections/overview/banking/banking-expenses-categories.jsx b/front_minimal/src/sections/overview/banking/banking-expenses-categories.jsx new file mode 100644 index 0000000..e0590ae --- /dev/null +++ b/front_minimal/src/sections/overview/banking/banking-expenses-categories.jsx @@ -0,0 +1,92 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Divider from '@mui/material/Divider'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; + +import { fCurrency } from 'src/utils/format-number'; + +import { Chart, useChart, ChartLegends } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function BankingExpensesCategories({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [ + theme.palette.secondary.dark, + theme.palette.error.main, + theme.palette.primary.main, + theme.palette.warning.main, + theme.palette.info.dark, + theme.palette.info.main, + theme.palette.success.main, + theme.palette.warning.dark, + ]; + + const chartSeries = chart.series.map((item) => item.value); + + const chartOptions = useChart({ + chart: { offsetY: 12 }, + colors: chartColors, + labels: chart.series.map((item) => item.label), + stroke: { width: 1, colors: [theme.palette.background.paper] }, + fill: { opacity: 0.88 }, + tooltip: { y: { formatter: (value) => fCurrency(value) } }, + plotOptions: { pie: { donut: { labels: { show: false } } } }, + ...chart.options, + }); + + return ( + + + + + + + fCurrency(item.value))} + sx={{ gap: 2.5, display: 'grid', gridTemplateColumns: 'repeat(2, 1fr)' }} + /> + + + + + + + Categories9 + + + + Categories + $18,765 + + + + ); +} diff --git a/front_minimal/src/sections/overview/banking/banking-invite-friends.jsx b/front_minimal/src/sections/overview/banking/banking-invite-friends.jsx new file mode 100644 index 0000000..f0b9b09 --- /dev/null +++ b/front_minimal/src/sections/overview/banking/banking-invite-friends.jsx @@ -0,0 +1,71 @@ +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import InputBase from '@mui/material/InputBase'; +import { useTheme } from '@mui/material/styles'; + +import { varAlpha, bgGradient } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +export function BankingInviteFriends({ price, title, imgUrl, description, sx, ...other }) { + const theme = useTheme(); + + return ( + + + + {title} + {price} + + {description} + + + Invite + + } + inputProps={{ + id: 'input-email', + sx: { + color: 'common.white', + '&::placeholder': { opacity: 0.48, color: 'inherit' }, + }, + }} + sx={{ + pl: 1.5, + height: 40, + borderRadius: 1, + bgcolor: varAlpha(theme.vars.palette.common.blackChannel, 0.12), + }} + /> + + ); +} diff --git a/front_minimal/src/sections/overview/banking/banking-overview.jsx b/front_minimal/src/sections/overview/banking/banking-overview.jsx new file mode 100644 index 0000000..de67d90 --- /dev/null +++ b/front_minimal/src/sections/overview/banking/banking-overview.jsx @@ -0,0 +1,221 @@ +import Box from '@mui/material/Box'; +import Tab from '@mui/material/Tab'; +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; +import Tooltip from '@mui/material/Tooltip'; +import { useTheme } from '@mui/material/styles'; + +import { useTabs } from 'src/hooks/use-tabs'; + +import { fPercent, fCurrency } from 'src/utils/format-number'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { Chart, useChart } from 'src/components/chart'; +import { CustomTabs } from 'src/components/custom-tabs'; + +// ---------------------------------------------------------------------- + +const TABS = [ + { + value: 'income', + label: 'Income', + percent: 8.2, + total: 9990, + chart: { series: [{ data: [5, 31, 33, 50, 100, 76, 72, 76, 89] }] }, + }, + { + value: 'expenses', + label: 'Expenses', + percent: -6.6, + total: 1989, + chart: { series: [{ data: [10, 41, 35, 51, 49, 62, 69, 91, 148] }] }, + }, +]; + +// ---------------------------------------------------------------------- + +export function BankingOverview({ sx, ...other }) { + const theme = useTheme(); + + const tabs = useTabs('income'); + + const chartColors = + tabs.value === 'income' ? [theme.palette.primary.dark] : [theme.palette.warning.dark]; + + const chartOptions = useChart({ + colors: chartColors, + xaxis: { categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep'] }, + stroke: { width: 3 }, + tooltip: { + y: { formatter: (value) => fCurrency(value), title: { formatter: () => '' } }, + }, + }); + + const renderBalance = ( + + + Total balance + + + + + {fCurrency(49990)} + + ); + + const renderActions = ( + + + + + + ); + + const renderTabs = ( + + {TABS.map((tab) => ( + + + + + +
    + + {tab.label} + + + + + + {fCurrency(tab.total)} +
    + + +
    + } + /> + ))} + + ); + + return ( + + + {renderBalance} + {renderActions} + + + {renderTabs} + + + + ); +} diff --git a/front_minimal/src/sections/overview/banking/banking-quick-transfer.jsx b/front_minimal/src/sections/overview/banking/banking-quick-transfer.jsx new file mode 100644 index 0000000..4442a75 --- /dev/null +++ b/front_minimal/src/sections/overview/banking/banking-quick-transfer.jsx @@ -0,0 +1,300 @@ +import { useState, useEffect, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Slider from '@mui/material/Slider'; +import Dialog from '@mui/material/Dialog'; +import Tooltip from '@mui/material/Tooltip'; +import TextField from '@mui/material/TextField'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import DialogTitle from '@mui/material/DialogTitle'; +import ListItemText from '@mui/material/ListItemText'; +import DialogActions from '@mui/material/DialogActions'; +import Input, { inputClasses } from '@mui/material/Input'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { fCurrency } from 'src/utils/format-number'; + +import { varAlpha, stylesMode } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { Carousel, useCarousel, CarouselArrowFloatButtons } from 'src/components/carousel'; + +// ---------------------------------------------------------------------- + +const STEP = 50; + +const MIN_AMOUNT = 0; + +const MAX_AMOUNT = 1000; + +// ---------------------------------------------------------------------- + +export function BankingQuickTransfer({ title, subheader, list, sx, ...other }) { + const theme = useTheme(); + + const carousel = useCarousel({ + loop: true, + dragFree: true, + slidesToShow: 'auto', + slideSpacing: '20px', + }); + + const confirm = useBoolean(); + + const [amount, setAmount] = useState(0); + + const [autoWidth, setAutoWidth] = useState(24); + + const contactInfo = list.find((_, index) => index === carousel.dots.selectedIndex); + + useEffect(() => { + if (amount) { + handleAutoWidth(); + } + // eslint-disable-next-line react-hooks/exhaustive-deps + }, [amount]); + + const handleAutoWidth = useCallback(() => { + const getNumberLength = amount.toString().length; + setAutoWidth(getNumberLength * 24); + }, [amount]); + + const handleChangeSlider = useCallback((event, newValue) => { + setAmount(newValue); + }, []); + + const handleChangeInput = useCallback((event) => { + setAmount(Number(event.target.value)); + }, []); + + const handleBlur = useCallback(() => { + if (amount < 0) { + setAmount(0); + } else if (amount > MAX_AMOUNT) { + setAmount(MAX_AMOUNT); + } + }, [amount]); + + const renderCarousel = ( + + + + + {list.map((contact, index) => ( + + carousel.dots.onClickDot(index)} + sx={{ + mx: 'auto', + opacity: 0.48, + cursor: 'pointer', + transition: theme.transitions.create('all'), + ...(index === carousel.dots.selectedIndex && { + opacity: 1, + transform: 'scale(1.25)', + boxShadow: `-4px 12px 24px 0 ${varAlpha(theme.vars.palette.common.blackChannel, 0.12)}`, + [stylesMode.dark]: { + boxShadow: `-4px 12px 24px 0 ${varAlpha(theme.vars.palette.common.blackChannel, 0.24)}`, + }, + }), + }} + /> + + ))} + + + ); + + const renderInput = ( + <> + + insert amount + + + + + + + + + Your balance + + {fCurrency(34212)} + + + + + ); + + return ( + <> + + + + + + + Recent + + + + + + {renderCarousel} + + {renderInput} + + + + + + ); +} + +function InputAmount({ autoWidth, amount, onBlur, onChange, sx, ...other }) { + return ( + + + $ + + + + + ); +} + +function ConfirmTransferDialog({ + open, + amount, + onBlur, + onClose, + onChange, + autoWidth, + contactInfo, +}) { + return ( + + Transfer to + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/banking/banking-recent-transitions.jsx b/front_minimal/src/sections/overview/banking/banking-recent-transitions.jsx new file mode 100644 index 0000000..76e457c --- /dev/null +++ b/front_minimal/src/sections/overview/banking/banking-recent-transitions.jsx @@ -0,0 +1,198 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Table from '@mui/material/Table'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import TableRow from '@mui/material/TableRow'; +import { useTheme } from '@mui/material/styles'; +import TableCell from '@mui/material/TableCell'; +import TableBody from '@mui/material/TableBody'; +import IconButton from '@mui/material/IconButton'; +import CardHeader from '@mui/material/CardHeader'; +import ListItemText from '@mui/material/ListItemText'; +import Badge, { badgeClasses } from '@mui/material/Badge'; + +import { fCurrency } from 'src/utils/format-number'; +import { fDate, fTime } from 'src/utils/format-time'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { TableHeadCustom } from 'src/components/table'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function BankingRecentTransitions({ title, subheader, tableData, headLabel, ...other }) { + return ( + + + + + + + + + {tableData.map((row) => ( + + ))} + +
    +
    + + + + + + +
    + ); +} + +// ---------------------------------------------------------------------- + +function RowItem({ row }) { + const theme = useTheme(); + + const popover = usePopover(); + + const lightMode = theme.palette.mode === 'light'; + + const handleDownload = () => { + popover.onClose(); + console.info('DOWNLOAD', row.id); + }; + + const handlePrint = () => { + popover.onClose(); + console.info('PRINT', row.id); + }; + + const handleShare = () => { + popover.onClose(); + console.info('SHARE', row.id); + }; + + const handleDelete = () => { + popover.onClose(); + console.info('DELETE', row.id); + }; + + const renderAvatar = ( + + + } + sx={{ [`& .${badgeClasses.badge}`]: { p: 0, width: 20 } }} + > + + {row.category === 'Fast food' && } + {row.category === 'Fitness' && } + + + + ); + + return ( + <> + + + + {renderAvatar} + + + + + + + + + {fCurrency(row.amount)} + + + + + + + + + + + + + + + + + Download + + + + + Print + + + + + Share + + + + + + + Delete + + + + + ); +} diff --git a/front_minimal/src/sections/overview/banking/view/index.js b/front_minimal/src/sections/overview/banking/view/index.js new file mode 100644 index 0000000..3552335 --- /dev/null +++ b/front_minimal/src/sections/overview/banking/view/index.js @@ -0,0 +1 @@ +export * from './overview-banking-view'; diff --git a/front_minimal/src/sections/overview/banking/view/overview-banking-view.jsx b/front_minimal/src/sections/overview/banking/view/overview-banking-view.jsx new file mode 100644 index 0000000..e295ede --- /dev/null +++ b/front_minimal/src/sections/overview/banking/view/overview-banking-view.jsx @@ -0,0 +1,130 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Grid from '@mui/material/Unstable_Grid2'; + +import { CONFIG } from 'src/config-global'; +import { DashboardContent } from 'src/layouts/dashboard'; +import { _bankingContacts, _bankingCreditCard, _bankingRecentTransitions } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify/iconify'; + +import { BankingContacts } from '../banking-contacts'; +import { BankingOverview } from '../banking-overview'; +import { BankingQuickTransfer } from '../banking-quick-transfer'; +import { BankingInviteFriends } from '../banking-invite-friends'; +import { BankingCurrentBalance } from '../banking-current-balance'; +import { BankingBalanceStatistics } from '../banking-balance-statistics'; +import { BankingRecentTransitions } from '../banking-recent-transitions'; +import { BankingExpensesCategories } from '../banking-expenses-categories'; + +// ---------------------------------------------------------------------- + +export function OverviewBankingView() { + return ( + + + + + + + + + , + , + , + , + , + , + , + , + ], + }} + /> + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/booking/booking-available.jsx b/front_minimal/src/sections/overview/booking/booking-available.jsx new file mode 100644 index 0000000..d1e055c --- /dev/null +++ b/front_minimal/src/sections/overview/booking/booking-available.jsx @@ -0,0 +1,92 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; + +import { sumBy } from 'src/utils/helper'; +import { fNumber } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function BookingAvailable({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const total = sumBy(chart.series, (series) => series.value); + + const chartSeries = (chart.series.filter((i) => i.label === 'Sold out')[0].value / total) * 100; + + const chartColors = chart.colors ?? [theme.palette.primary.light, theme.palette.primary.main]; + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + stroke: { width: 0 }, + fill: { + type: 'gradient', + gradient: { + colorStops: [ + { offset: 0, color: chartColors[0], opacity: 1 }, + { offset: 100, color: chartColors[1], opacity: 1 }, + ], + }, + }, + plotOptions: { + radialBar: { + hollow: { margin: -20 }, + track: { margin: -20, background: varAlpha(theme.vars.palette.grey['500Channel'], 0.08) }, + dataLabels: { + name: { offsetY: -12 }, + value: { offsetY: 6 }, + total: { label: 'Tours', formatter: () => fNumber(total) }, + }, + }, + }, + ...chart.options, + }); + + return ( + + + + + + + {chart.series.map((item) => ( + + + {item.label} + {item.value} tours + + ))} + + + ); +} diff --git a/front_minimal/src/sections/overview/booking/booking-booked.jsx b/front_minimal/src/sections/overview/booking/booking-booked.jsx new file mode 100644 index 0000000..786b9e9 --- /dev/null +++ b/front_minimal/src/sections/overview/booking/booking-booked.jsx @@ -0,0 +1,50 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import CardHeader from '@mui/material/CardHeader'; +import LinearProgress, { linearProgressClasses } from '@mui/material/LinearProgress'; + +import { fShortenNumber } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +export function BookingBooked({ title, subheader, data, ...other }) { + return ( + + + + + {data.map((progress) => ( +
  • + + {progress.status} + {fShortenNumber(progress.quantity)} + + + varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + [`& .${linearProgressClasses.bar}`]: { + background: (theme) => + `linear-gradient(135deg, ${theme.vars.palette.success.light} 0%, ${theme.vars.palette.success.main} 100%)`, + ...(progress.status === 'Pending' && { + background: (theme) => + `linear-gradient(135deg, ${theme.vars.palette.warning.light} 0%, ${theme.vars.palette.warning.main} 100%)`, + }), + ...(progress.status === 'Canceled' && { + background: (theme) => + `linear-gradient(135deg, ${theme.vars.palette.error.light} 0%, ${theme.vars.palette.error.main} 100%)`, + }), + }, + }} + /> +
  • + ))} +
    +
    + ); +} diff --git a/front_minimal/src/sections/overview/booking/booking-check-in-widgets.jsx b/front_minimal/src/sections/overview/booking/booking-check-in-widgets.jsx new file mode 100644 index 0000000..57051db --- /dev/null +++ b/front_minimal/src/sections/overview/booking/booking-check-in-widgets.jsx @@ -0,0 +1,107 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import { useTheme } from '@mui/material/styles'; + +import { useResponsive } from 'src/hooks/use-responsive'; + +import { fNumber } from 'src/utils/format-number'; + +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function BookingCheckInWidgets({ chart, ...other }) { + const theme = useTheme(); + + const smUp = useResponsive('up', 'sm'); + + const chartColors = chart.colors ?? [ + [theme.palette.primary.light, theme.palette.primary.main], + [theme.palette.warning.light, theme.palette.warning.main], + ]; + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + stroke: { width: 0 }, + fill: { + type: 'gradient', + gradient: { + colorStops: [ + { offset: 0, color: chartColors[0][0], opacity: 1 }, + { offset: 100, color: chartColors[0][1], opacity: 1 }, + ], + }, + }, + plotOptions: { + radialBar: { + dataLabels: { + name: { show: false }, + value: { + offsetY: 6, + fontSize: theme.typography.subtitle2.fontSize, + fontWeight: theme.typography.subtitle2.fontWeight, + }, + }, + }, + }, + ...chart.options, + }); + + return ( + + + } + > + {chart.series.map((item) => ( + + + +
    + {fNumber(item.total)} + {item.label} +
    +
    + ))} +
    +
    + ); +} diff --git a/front_minimal/src/sections/overview/booking/booking-customer-reviews.jsx b/front_minimal/src/sections/overview/booking/booking-customer-reviews.jsx new file mode 100644 index 0000000..6a59cef --- /dev/null +++ b/front_minimal/src/sections/overview/booking/booking-customer-reviews.jsx @@ -0,0 +1,109 @@ +import AutoHeight from 'embla-carousel-auto-height'; + +import Box from '@mui/material/Box'; +import Chip from '@mui/material/Chip'; +import Card from '@mui/material/Card'; +import Rating from '@mui/material/Rating'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { fDateTime } from 'src/utils/format-time'; + +import { Carousel, useCarousel, CarouselArrowBasicButtons } from 'src/components/carousel'; + +// ---------------------------------------------------------------------- + +export function BookingCustomerReviews({ title, subheader, list, ...other }) { + const carousel = useCarousel({ align: 'start' }, [AutoHeight()]); + + const customerInfo = list.find((_, index) => index === carousel.dots.selectedIndex); + + return ( + + } + /> + + + {list.map((item) => ( + + ))} + + + + + + + + + + + ); +} + +function Item({ item, sx, ...other }) { + return ( + + + + + + + + + + {item.description} + + + {item.tags.map((tag) => ( + + ))} + + + ); +} diff --git a/front_minimal/src/sections/overview/booking/booking-details.jsx b/front_minimal/src/sections/overview/booking/booking-details.jsx new file mode 100644 index 0000000..b389de3 --- /dev/null +++ b/front_minimal/src/sections/overview/booking/booking-details.jsx @@ -0,0 +1,182 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Table from '@mui/material/Table'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import TableRow from '@mui/material/TableRow'; +import { useTheme } from '@mui/material/styles'; +import TableCell from '@mui/material/TableCell'; +import TableBody from '@mui/material/TableBody'; +import IconButton from '@mui/material/IconButton'; +import CardHeader from '@mui/material/CardHeader'; +import ListItemText from '@mui/material/ListItemText'; + +import { fDate, fTime } from 'src/utils/format-time'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { TableHeadCustom } from 'src/components/table'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function BookingDetails({ title, subheader, headLabel, tableData, ...other }) { + return ( + + + + + + + + + {tableData.map((row) => ( + + ))} + +
    +
    + + + + + + +
    + ); +} + +// ---------------------------------------------------------------------- + +function RowItem({ row }) { + const theme = useTheme(); + + const popover = usePopover(); + + const lightMode = theme.palette.mode === 'light'; + + const handleDownload = () => { + popover.onClose(); + console.info('DOWNLOAD', row.id); + }; + + const handlePrint = () => { + popover.onClose(); + console.info('PRINT', row.id); + }; + + const handleShare = () => { + popover.onClose(); + console.info('SHARE', row.id); + }; + + const handleDelete = () => { + popover.onClose(); + console.info('DELETE', row.id); + }; + + return ( + <> + + + + + {row.destination.name} + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Download + + + + + Print + + + + + Share + + + + + + + Delete + + + + + ); +} diff --git a/front_minimal/src/sections/overview/booking/booking-newest.jsx b/front_minimal/src/sections/overview/booking/booking-newest.jsx new file mode 100644 index 0000000..b6a14df --- /dev/null +++ b/front_minimal/src/sections/overview/booking/booking-newest.jsx @@ -0,0 +1,107 @@ +import Box from '@mui/material/Box'; +import Avatar from '@mui/material/Avatar'; +import CardHeader from '@mui/material/CardHeader'; +import ListItemText from '@mui/material/ListItemText'; + +import { fDateTime } from 'src/utils/format-time'; + +import { Label } from 'src/components/label'; +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; +import { Carousel, useCarousel, CarouselArrowBasicButtons } from 'src/components/carousel'; + +// ---------------------------------------------------------------------- + +export function BookingNewest({ title, subheader, list, sx, ...other }) { + const carousel = useCarousel({ + align: 'start', + slideSpacing: '24px', + slidesToShow: { xs: 1, sm: 2, md: 3, lg: 4 }, + }); + + return ( + + } + sx={{ p: 0, mb: 3 }} + /> + + + {list.map((item) => ( + + ))} + + + ); +} + +function Item({ item, sx, ...other }) { + return ( + + + + + + + + + + + {item.duration} + + + + + {item.guests} guests + + + + + + + + {item.coverUrl} + + + ); +} diff --git a/front_minimal/src/sections/overview/booking/booking-statistics.jsx b/front_minimal/src/sections/overview/booking/booking-statistics.jsx new file mode 100644 index 0000000..a6e2613 --- /dev/null +++ b/front_minimal/src/sections/overview/booking/booking-statistics.jsx @@ -0,0 +1,66 @@ +import { useState, useCallback } from 'react'; + +import Card from '@mui/material/Card'; +import CardHeader from '@mui/material/CardHeader'; +import { useTheme, alpha as hexAlpha } from '@mui/material/styles'; + +import { fShortenNumber } from 'src/utils/format-number'; + +import { Chart, useChart, ChartSelect, ChartLegends } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function BookingStatistics({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const [selectedSeries, setSelectedSeries] = useState('Yearly'); + + const currentSeries = chart.series.find((i) => i.name === selectedSeries); + + const chartColors = [theme.palette.primary.dark, hexAlpha(theme.palette.error.main, 0.48)]; + + const chartOptions = useChart({ + colors: chartColors, + stroke: { width: 2, colors: ['transparent'] }, + xaxis: { categories: currentSeries?.categories }, + tooltip: { y: { formatter: (value) => `${value}` } }, + ...chart.options, + }); + + const handleChangeSeries = useCallback((newValue) => { + setSelectedSeries(newValue); + }, []); + + return ( + + item.name)} + value={selectedSeries} + onChange={handleChangeSeries} + /> + } + sx={{ mb: 3 }} + /> + + item.name)} + values={[fShortenNumber(6789), fShortenNumber(1234)]} + sx={{ px: 3, gap: 3 }} + /> + + + + ); +} diff --git a/front_minimal/src/sections/overview/booking/booking-total-incomes.jsx b/front_minimal/src/sections/overview/booking/booking-total-incomes.jsx new file mode 100644 index 0000000..2b7a3a2 --- /dev/null +++ b/front_minimal/src/sections/overview/booking/booking-total-incomes.jsx @@ -0,0 +1,93 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import { useTheme, alpha as hexAlpha } from '@mui/material/styles'; + +import { fPercent, fCurrency } from 'src/utils/format-number'; + +import { CONFIG } from 'src/config-global'; + +import { Iconify } from 'src/components/iconify'; +import { SvgColor } from 'src/components/svg-color'; +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function BookingTotalIncomes({ title, total, percent, chart, sx, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [hexAlpha(theme.palette.primary.lighter, 0.64)]; + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + colors: chartColors, + stroke: { width: 3 }, + grid: { + padding: { + top: 6, + left: 6, + right: 6, + bottom: 6, + }, + }, + xaxis: { categories: chart.categories }, + tooltip: { + y: { formatter: (value) => fCurrency(value), title: { formatter: () => '' } }, + }, + ...chart.options, + }); + + const renderTrending = ( + + + = 0 ? 'eva:trending-up-fill' : 'eva:trending-down-fill'} /> + + {percent > 0 && '+'} + {fPercent(percent)} + + + + last month + + + ); + + return ( + + +
    + {title} + {fCurrency(total)} +
    + + {renderTrending} +
    + + + + +
    + ); +} diff --git a/front_minimal/src/sections/overview/booking/booking-widget-summary.jsx b/front_minimal/src/sections/overview/booking/booking-widget-summary.jsx new file mode 100644 index 0000000..6810d01 --- /dev/null +++ b/front_minimal/src/sections/overview/booking/booking-widget-summary.jsx @@ -0,0 +1,65 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; + +import { fPercent, fShortenNumber } from 'src/utils/format-number'; + +// ---------------------------------------------------------------------- + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function BookingWidgetSummary({ title, percent, total, icon, sx, ...other }) { + const renderTrending = ( + + + + {percent > 0 && '+'} + {fPercent(percent)} + + + ); + + return ( + + + {title} + {fShortenNumber(total)} + {renderTrending} + + + + {icon} + + + ); +} diff --git a/front_minimal/src/sections/overview/booking/view/index.js b/front_minimal/src/sections/overview/booking/view/index.js new file mode 100644 index 0000000..2f11f27 --- /dev/null +++ b/front_minimal/src/sections/overview/booking/view/index.js @@ -0,0 +1 @@ +export * from './overview-booking-view'; diff --git a/front_minimal/src/sections/overview/booking/view/overview-booking-view.jsx b/front_minimal/src/sections/overview/booking/view/overview-booking-view.jsx new file mode 100644 index 0000000..99e2958 --- /dev/null +++ b/front_minimal/src/sections/overview/booking/view/overview-booking-view.jsx @@ -0,0 +1,187 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Grid from '@mui/material/Unstable_Grid2'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { _bookings, _bookingNew, _bookingReview, _bookingsOverview } from 'src/_mock'; +import { + BookingIllustration, + CheckInIllustration, + CheckoutIllustration, +} from 'src/assets/illustrations'; + +import { BookingBooked } from '../booking-booked'; +import { BookingNewest } from '../booking-newest'; +import { BookingDetails } from '../booking-details'; +import { BookingAvailable } from '../booking-available'; +import { BookingStatistics } from '../booking-statistics'; +import { BookingTotalIncomes } from '../booking-total-incomes'; +import { BookingWidgetSummary } from '../booking-widget-summary'; +import { BookingCheckInWidgets } from '../booking-check-in-widgets'; +import { BookingCustomerReviews } from '../booking-customer-reviews'; + +// ---------------------------------------------------------------------- + +export function OverviewBookingView() { + return ( + + + + } + /> + + + + } + /> + + + + } + /> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/course/course-continue.jsx b/front_minimal/src/sections/overview/course/course-continue.jsx new file mode 100644 index 0000000..0e99020 --- /dev/null +++ b/front_minimal/src/sections/overview/course/course-continue.jsx @@ -0,0 +1,76 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Avatar from '@mui/material/Avatar'; +import CardHeader from '@mui/material/CardHeader'; +import LinearProgress, { linearProgressClasses } from '@mui/material/LinearProgress'; + +import { fPercent } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +export function CourseContinue({ title, subheader, list, ...other }) { + return ( + + + + + {list.map((item) => ( + + ))} + + + ); +} + +function Item({ item, sx, ...other }) { + const percent = (item.currentLesson / item.totalLesson) * 100; + + return ( + + + + + + {item.title} + + + + Lessons: {item.currentLesson}/{item.totalLesson} + + + + varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + [` .${linearProgressClasses.bar}`]: { opacity: 0.8 }, + }} + /> + + {fPercent(percent)} + + + + + ); +} diff --git a/front_minimal/src/sections/overview/course/course-featured.jsx b/front_minimal/src/sections/overview/course/course-featured.jsx new file mode 100644 index 0000000..de03e8a --- /dev/null +++ b/front_minimal/src/sections/overview/course/course-featured.jsx @@ -0,0 +1,122 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { fCurrency, fShortenNumber } from 'src/utils/format-number'; + +import { maxLine } from 'src/theme/styles'; + +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; +import { Label, labelClasses } from 'src/components/label'; +import { Carousel, useCarousel, CarouselArrowBasicButtons } from 'src/components/carousel'; + +// ---------------------------------------------------------------------- + +export function CourseFeatured({ title, list, ...other }) { + const carousel = useCarousel({ + align: 'start', + slideSpacing: '24px', + slidesToShow: { xs: 1, sm: 2, md: 3, lg: '40%', xl: '30%' }, + }); + + return ( + + + + {title} + + + + + + + {list.map((item) => ( + + ))} + + + ); +} + +function CarouselItem({ item, ...other }) { + const theme = useTheme(); + + const renderImage = ( + + {item.title} + + ); + + const renderLabels = ( + + + + + + ); + + const renderFooter = ( + + + {fCurrency(item.price)} + + + / year + + + + ); + + return ( + + {renderImage} + + + {renderLabels} + + + {item.title} + + + {renderFooter} + + + ); +} diff --git a/front_minimal/src/sections/overview/course/course-hours-spent.jsx b/front_minimal/src/sections/overview/course/course-hours-spent.jsx new file mode 100644 index 0000000..471678a --- /dev/null +++ b/front_minimal/src/sections/overview/course/course-hours-spent.jsx @@ -0,0 +1,67 @@ +import { useState, useCallback, useEffect } from 'react'; + +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; + +import { Chart, useChart, ChartSelect } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function CourseHoursSpent({ title, subheader, chart, onValueChange, value, ...other }) { + const theme = useTheme(); + + // Если пропс value передан, используем его, иначе внутреннее состояние + const [internalSeries, setInternalSeries] = useState(chart.series[0]?.name || 'Месяц'); + + const selectedSeries = value !== undefined ? value : internalSeries; + + const currentSeries = chart.series.find((i) => i.name === selectedSeries) || chart.series[0]; + + const chartColors = chart.colors ?? [theme.palette.text.primary, theme.palette.info.main]; + + const chartOptions = useChart({ + grid: { padding: { left: 24 } }, + stroke: { width: 3, curve: 'smooth' }, + colors: chartColors, + xaxis: { + categories: currentSeries?.data[0]?.categories || [] + }, + ...chart.options, + }); + + const handleChangeSeries = useCallback((newValue) => { + if (value === undefined) { + setInternalSeries(newValue); + } + if (onValueChange) { + onValueChange(newValue); + } + }, [onValueChange, value]); + + return ( + + s.name !== '').map((item) => item.name)} + value={selectedSeries} + onChange={handleChangeSeries} + /> + } + sx={{ mb: 3 }} + /> + + + + ); +} diff --git a/front_minimal/src/sections/overview/course/course-my-account.jsx b/front_minimal/src/sections/overview/course/course-my-account.jsx new file mode 100644 index 0000000..d97062f --- /dev/null +++ b/front_minimal/src/sections/overview/course/course-my-account.jsx @@ -0,0 +1,64 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { AnimateAvatar } from 'src/components/animate'; + +// ---------------------------------------------------------------------- + +export function CourseMyAccount({ user, ...other }) { + const theme = useTheme(); + + const displayName = user?.first_name + ? `${user.first_name} ${user.last_name || ''}`.trim() + : user?.name || 'Пользователь'; + + const renderAvatar = ( + + {displayName.charAt(0).toUpperCase()} + + ); + + return ( + + + {renderAvatar} + + + {displayName} + + + + ID: {user?.id?.toString().slice(-6) || '---'} + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/course/course-my-strength.jsx b/front_minimal/src/sections/overview/course/course-my-strength.jsx new file mode 100644 index 0000000..6cc1286 --- /dev/null +++ b/front_minimal/src/sections/overview/course/course-my-strength.jsx @@ -0,0 +1,49 @@ +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function CourseMyStrength({ title, chart, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [theme.palette.primary.main]; + + const chartOptions = useChart({ + colors: chartColors, + stroke: { width: 2 }, + fill: { opacity: 0.48 }, + xaxis: { + categories: chart.categories, + labels: { + style: { + colors: [ + theme.palette.text.disabled, + theme.palette.text.disabled, + theme.palette.text.disabled, + theme.palette.text.disabled, + theme.palette.text.disabled, + theme.palette.text.disabled, + ], + }, + }, + }, + }); + + return ( + + {title} + + + ); +} diff --git a/front_minimal/src/sections/overview/course/course-progress.jsx b/front_minimal/src/sections/overview/course/course-progress.jsx new file mode 100644 index 0000000..3a24b4f --- /dev/null +++ b/front_minimal/src/sections/overview/course/course-progress.jsx @@ -0,0 +1,75 @@ +import Card from '@mui/material/Card'; +import Divider from '@mui/material/Divider'; +import CardHeader from '@mui/material/CardHeader'; +import { useTheme, alpha as hexAlpha } from '@mui/material/styles'; + +import { fNumber } from 'src/utils/format-number'; + +import { Chart, useChart, ChartLegends } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function CourseProgress({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [ + hexAlpha(theme.palette.grey[500], 0.24), + theme.palette.success.dark, + theme.palette.warning.main, + ]; + + const chartSeries = chart.series.map((item) => item.value); + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + colors: chartColors, + labels: chart.series.map((item) => item.label), + stroke: { width: 0 }, + tooltip: { + y: { + formatter: (value) => fNumber(value), + title: { formatter: (seriesName) => `${seriesName}` }, + }, + }, + plotOptions: { + pie: { + donut: { + size: '72%', + labels: { + value: { formatter: (value) => fNumber(value) }, + total: { + formatter: (w) => { + const sum = w.globals.seriesTotals.reduce((a, b) => a + b, 0); + return fNumber(sum); + }, + }, + }, + }, + }, + }, + ...chart.options, + }); + + return ( + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/course/course-reminders.jsx b/front_minimal/src/sections/overview/course/course-reminders.jsx new file mode 100644 index 0000000..8d312f7 --- /dev/null +++ b/front_minimal/src/sections/overview/course/course-reminders.jsx @@ -0,0 +1,112 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; +import LinearProgress, { linearProgressClasses } from '@mui/material/LinearProgress'; + +import { fDateTime } from 'src/utils/format-time'; +import { fPercent } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function CourseReminders({ title, list, ...other }) { + const theme = useTheme(); + + const colors = [ + theme.vars.palette.info.main, + theme.vars.palette.error.main, + theme.vars.palette.secondary.main, + theme.vars.palette.success.main, + ]; + + return ( + + + {title} + + + + {list.map((item, index) => ( + + ))} + + + ); +} + +function Item({ item, sx, ...other }) { + const percent = (item.currentLesson / item.totalLesson) * 100; + + return ( + + + + + + {item.title} + + + + + {fDateTime(item.reminderAt)} + + + + varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + [` .${linearProgressClasses.bar}`]: { bgcolor: 'currentColor' }, + }} + /> + + {fPercent(percent)} + + + + + ); +} diff --git a/front_minimal/src/sections/overview/course/course-widget-summary.jsx b/front_minimal/src/sections/overview/course/course-widget-summary.jsx new file mode 100644 index 0000000..82d5801 --- /dev/null +++ b/front_minimal/src/sections/overview/course/course-widget-summary.jsx @@ -0,0 +1,58 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { fNumber } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +import { SvgColor } from 'src/components/svg-color'; + +// ---------------------------------------------------------------------- + +export function CourseWidgetSummary({ sx, icon, title, total, color = 'warning', ...other }) { + const theme = useTheme(); + + // Если total - строка (содержит разделитель /), то выводим как есть + // Если число - форматируем через fNumber + const renderTotal = typeof total === 'string' ? total : fNumber(total); + + return ( + + + {renderTotal} + + {title} + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/course/view/index.js b/front_minimal/src/sections/overview/course/view/index.js new file mode 100644 index 0000000..e7390bf --- /dev/null +++ b/front_minimal/src/sections/overview/course/view/index.js @@ -0,0 +1 @@ +export * from './overview-course-view'; diff --git a/front_minimal/src/sections/overview/course/view/overview-course-view.jsx b/front_minimal/src/sections/overview/course/view/overview-course-view.jsx new file mode 100644 index 0000000..16ac280 --- /dev/null +++ b/front_minimal/src/sections/overview/course/view/overview-course-view.jsx @@ -0,0 +1,210 @@ +'use client'; + +import { useState, useEffect, useMemo, useCallback } from 'react'; +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Stack from '@mui/material/Stack'; +import { useTheme } from '@mui/material/styles'; +import { cardClasses } from '@mui/material/Card'; +import Typography from '@mui/material/Typography'; +import CircularProgress from '@mui/material/CircularProgress'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha } from 'src/theme/styles'; +import { DashboardContent } from 'src/layouts/dashboard'; +import { useAuthContext } from 'src/auth/hooks'; +import { fDateTime } from 'src/utils/format-time'; +import { fNumber } from 'src/utils/format-number'; +import { AvatarShape } from 'src/assets/illustrations'; +import { Image } from 'src/components/image'; + +// Статический импорт API +import { getMentorDashboard, getMentorIncome } from 'src/utils/dashboard-api'; + +import { CourseProgress } from '../course-progress'; +import { CourseMyAccount } from '../course-my-account'; +import { CourseHoursSpent } from '../course-hours-spent'; +import { CourseWidgetSummary } from '../course-widget-summary'; + +// ---------------------------------------------------------------------- + +export function OverviewCourseView() { + const theme = useTheme(); + const { user } = useAuthContext(); + + const [stats, setStats] = useState(null); + const [incomeStats, setIncomeStats] = useState(null); + const [loading, setLoading] = useState(true); + const [period, setPeriod] = useState('Месяц'); + + // Фильтр активных уроков + const activeLessons = useMemo(() => { + const upcoming = stats?.upcoming_lessons || []; + const NOW = new Date(); + return upcoming.filter((lesson) => { + const startTime = new Date(lesson.start_time); + const diffInMinutes = (startTime.getTime() - NOW.getTime()) / 60000; + return diffInMinutes <= 10 && diffInMinutes > -60; + }); + }, [stats]); + + // Последние сданные ДЗ + const recentSubmissions = stats?.recent_submissions || []; + + // Данные для графиков + const prepareChart = useCallback((dataKey, label) => { + if (!incomeStats?.chart_data) return null; + const data = incomeStats.chart_data; + const categories = data.map(d => d.date); + const seriesData = data.map(d => Number(d[dataKey] || 0)); + + const options = ['День', 'Неделя', 'Месяц']; + return { + series: options.map(opt => ({ + name: opt, + data: [{ name: label, categories, data: seriesData }] + })) + }; + }, [incomeStats]); + + const incomeChart = useMemo(() => prepareChart('income', 'Сумма'), [prepareChart]); + const lessonsChart = useMemo(() => prepareChart('lessons', 'Занятия'), [prepareChart]); + + const fetchData = useCallback(async (currentPeriod) => { + try { + const periodMap = { 'День': 'day', 'Неделя': 'week', 'Месяц': 'month' }; + const [dData, iData] = await Promise.all([ + getMentorDashboard(), + getMentorIncome(periodMap[currentPeriod] || 'month') + ]); + if (dData) setStats(dData); + if (iData) setIncomeStats(iData); + } catch (err) { + console.error('Fetch error:', err); + } finally { + setLoading(false); + } + }, []); + + useEffect(() => { + fetchData(period); + }, [period, fetchData]); + + if (loading && !stats) { + return ( + + + + ); + } + + // Форматирование сумм для виджетов + const revenueDisplay = `${fNumber(stats?.summary?.revenue_this_month || 0)} / ${fNumber(stats?.summary?.total_revenue || 0)} ₽`; + const lessonsDisplay = `${stats?.summary?.lessons_this_month || 0} / ${stats?.summary?.total_lessons || 0}`; + + // Общий рендер карточки (урок или ДЗ) + const renderCard = (item, type) => { + const isLesson = type === 'lesson'; + const title = isLesson ? item.title : item.homework?.title; + const subTitle = isLesson ? item.client?.name : item.student?.name; + const avatar = isLesson ? item.client?.avatar : item.student?.avatar; + const timeLabel = isLesson ? 'Начало:' : 'Сдано:'; + const timeValue = isLesson ? fDateTime(item.start_time) : fDateTime(item.submitted_at); + const buttonLabel = isLesson ? 'Подключиться' : 'Проверить'; + const link = isLesson ? `/dashboard/room/${item.id}` : `/dashboard/homework/submissions/${item.id}`; + + return ( + theme.customShadows.z8, + overflow: 'hidden', + borderRadius: 2, + mb: 2 + }} + > + + + + Banner varAlpha(theme.vars.palette.grey['900Channel'], 0.48) } }} /> + + + + {title} + + {isLesson ? `Ученик: ${subTitle || '---'}` : `Студент: ${subTitle || '---'}`} + + + {timeLabel} + {timeValue} + + + + + ); + }; + + return ( + + + {/* ЛЕВАЯ ЧАСТЬ */} + + + Привет, {user?.first_name || 'Ментор'}! 🦾 + Ваша активность и доходы. + + + + + + + + + + + + {incomeChart && `${val} ₽` } } } }} onValueChange={(val) => setPeriod(val)} />} + + + + {lessonsChart && `${val} занятий` } } } }} onValueChange={(val) => setPeriod(val)} />} + + + + + + + {/* ПРАВАЯ ЧАСТЬ */} + + + + + + {/* Активные уроки */} + + Активные уроки + {activeLessons.length > 0 ? activeLessons.slice(0, 2).map((l) => renderCard(l, 'lesson')) : ( + Нет текущих уроков + )} + + + {/* Сданные ДЗ */} + + Проверка ДЗ + {recentSubmissions.length > 0 ? recentSubmissions.slice(0, 2).map((s) => renderCard(s, 'homework')) : ( + Нет новых работ + )} + + + + + ); +} diff --git a/front_minimal/src/sections/overview/e-commerce/ecommerce-best-salesman.jsx b/front_minimal/src/sections/overview/e-commerce/ecommerce-best-salesman.jsx new file mode 100644 index 0000000..cce8d16 --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/ecommerce-best-salesman.jsx @@ -0,0 +1,75 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Table from '@mui/material/Table'; +import Avatar from '@mui/material/Avatar'; +import TableRow from '@mui/material/TableRow'; +import TableCell from '@mui/material/TableCell'; +import TableBody from '@mui/material/TableBody'; +import CardHeader from '@mui/material/CardHeader'; + +import { fCurrency } from 'src/utils/format-number'; + +import { Label } from 'src/components/label'; +import { FlagIcon } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { TableHeadCustom } from 'src/components/table'; + +// ---------------------------------------------------------------------- + +export function EcommerceBestSalesman({ title, subheader, tableData, headLabel, ...other }) { + return ( + + + + + + + + + {tableData.map((row) => ( + + ))} + +
    +
    +
    + ); +} + +// ---------------------------------------------------------------------- + +function RowItem({ row }) { + return ( + + + + + {row.name} + + + + {row.category} + + + + + + {fCurrency(row.totalAmount)} + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/e-commerce/ecommerce-current-balance.jsx b/front_minimal/src/sections/overview/e-commerce/ecommerce-current-balance.jsx new file mode 100644 index 0000000..c345e3d --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/ecommerce-current-balance.jsx @@ -0,0 +1,50 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; + +import { fCurrency } from 'src/utils/format-number'; + +// ---------------------------------------------------------------------- + +export function EcommerceCurrentBalance({ + sx, + title, + earning, + refunded, + orderTotal, + currentBalance, + ...other +}) { + const row = (label, value) => ( + + + {label} + + {fCurrency(value)} + + ); + + return ( + + {title} + + + {fCurrency(currentBalance)} + + {row('Order total', orderTotal)} + {row('Earning', earning)} + {row('Refunded', refunded)} + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/e-commerce/ecommerce-latest-products.jsx b/front_minimal/src/sections/overview/e-commerce/ecommerce-latest-products.jsx new file mode 100644 index 0000000..1f0c79c --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/ecommerce-latest-products.jsx @@ -0,0 +1,79 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Avatar from '@mui/material/Avatar'; +import CardHeader from '@mui/material/CardHeader'; + +import { fCurrency } from 'src/utils/format-number'; + +import { Scrollbar } from 'src/components/scrollbar'; +import { ColorPreview } from 'src/components/color-utils'; + +// ---------------------------------------------------------------------- + +export function EcommerceLatestProducts({ title, subheader, list, ...other }) { + return ( + + + + + + {list.map((item) => ( + + ))} + + + + ); +} + +function Item({ item, sx, ...other }) { + return ( + + + + + + {item.name} + + + + {!!item.priceSale && ( + + {fCurrency(item.priceSale)} + + )} + + + {fCurrency(item.price)} + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/e-commerce/ecommerce-new-products.jsx b/front_minimal/src/sections/overview/e-commerce/ecommerce-new-products.jsx new file mode 100644 index 0000000..aebe7ab --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/ecommerce-new-products.jsx @@ -0,0 +1,86 @@ +import Autoplay from 'embla-carousel-autoplay'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Link from '@mui/material/Link'; +import Button from '@mui/material/Button'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { varAlpha } from 'src/theme/styles'; + +import { Image } from 'src/components/image'; +import { Carousel, useCarousel, CarouselDotButtons } from 'src/components/carousel'; + +// ---------------------------------------------------------------------- + +export function EcommerceNewProducts({ list, sx, ...other }) { + const carousel = useCarousel({ loop: true }, [Autoplay({ playOnInit: true, delay: 8000 })]); + + return ( + + + + + {list.map((item) => ( + + ))} + + + ); +} + +// ---------------------------------------------------------------------- + +function CarouselItem({ item, ...other }) { + const theme = useTheme(); + + return ( + + + + New + + + + {item.name} + + + + + + {item.name} + + ); +} diff --git a/front_minimal/src/sections/overview/e-commerce/ecommerce-sale-by-gender.jsx b/front_minimal/src/sections/overview/e-commerce/ecommerce-sale-by-gender.jsx new file mode 100644 index 0000000..468eff6 --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/ecommerce-sale-by-gender.jsx @@ -0,0 +1,77 @@ +import Card from '@mui/material/Card'; +import Divider from '@mui/material/Divider'; +import CardHeader from '@mui/material/CardHeader'; +import { useTheme, alpha as hexAlpha } from '@mui/material/styles'; + +import { fNumber } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +import { Chart, useChart, ChartLegends } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function EcommerceSaleByGender({ title, subheader, total, chart, ...other }) { + const theme = useTheme(); + + const chartSeries = chart.series.map((item) => item.value); + + const chartColors = chart.colors ?? [ + [theme.palette.primary.light, theme.palette.primary.main], + [hexAlpha(theme.palette.warning.light, 0.8), hexAlpha(theme.palette.warning.main, 0.8)], + [hexAlpha(theme.palette.error.light, 0.8), hexAlpha(theme.palette.error.main, 0.8)], + ]; + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + colors: chartColors.map((color) => color[1]), + labels: chart.series.map((item) => item.label), + stroke: { width: 0 }, + fill: { + type: 'gradient', + gradient: { + colorStops: chartColors.map((color) => [ + { offset: 0, color: color[0], opacity: 1 }, + { offset: 100, color: color[1], opacity: 1 }, + ]), + }, + }, + grid: { padding: { top: -40, bottom: -40 } }, + plotOptions: { + radialBar: { + hollow: { margin: 10, size: '32%' }, + track: { margin: 10, background: varAlpha(theme.vars.palette.grey['500Channel'], 0.08) }, + dataLabels: { + total: { formatter: () => fNumber(total) }, + value: { offsetY: 2, fontSize: theme.typography.h5.fontSize }, + name: { offsetY: -10 }, + }, + }, + }, + ...chart.options, + }); + + return ( + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/e-commerce/ecommerce-sales-overview.jsx b/front_minimal/src/sections/overview/e-commerce/ecommerce-sales-overview.jsx new file mode 100644 index 0000000..d99d1ff --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/ecommerce-sales-overview.jsx @@ -0,0 +1,54 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import CardHeader from '@mui/material/CardHeader'; +import LinearProgress from '@mui/material/LinearProgress'; + +import { fPercent, fCurrency } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +export function EcommerceSalesOverview({ title, subheader, data, ...other }) { + return ( + + + + + {data.map((progress) => ( + + ))} + + + ); +} + +function Item({ progress }) { + return ( +
    + + + {progress.label} + + {fCurrency(progress.totalAmount)} + + ({fPercent(progress.value)}) + + + + varAlpha(theme.vars.palette.grey['500Channel'], 0.12), + }} + /> +
    + ); +} diff --git a/front_minimal/src/sections/overview/e-commerce/ecommerce-welcome.jsx b/front_minimal/src/sections/overview/e-commerce/ecommerce-welcome.jsx new file mode 100644 index 0000000..4cce705 --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/ecommerce-welcome.jsx @@ -0,0 +1,63 @@ +import Box from '@mui/material/Box'; +import { useTheme } from '@mui/material/styles'; +import Typography from '@mui/material/Typography'; + +import { CONFIG } from 'src/config-global'; +import { varAlpha, bgGradient } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +export function EcommerceWelcome({ title, description, action, img, sx, ...other }) { + const theme = useTheme(); + + return ( + + + + {title} + + + + {description} + + + {action && action} + + + {img && {img}} + + ); +} diff --git a/front_minimal/src/sections/overview/e-commerce/ecommerce-widget-summary.jsx b/front_minimal/src/sections/overview/e-commerce/ecommerce-widget-summary.jsx new file mode 100644 index 0000000..a3aa0c8 --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/ecommerce-widget-summary.jsx @@ -0,0 +1,109 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; + +import { fNumber, fPercent } from 'src/utils/format-number'; + +import { varAlpha, stylesMode } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { Chart, useChart } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function EcommerceWidgetSummary({ title, percent, total, chart, sx, ...other }) { + const theme = useTheme(); + + const chartColors = chart.colors ?? [theme.palette.primary.light, theme.palette.primary.main]; + + const chartOptions = useChart({ + chart: { sparkline: { enabled: true } }, + colors: [chartColors[1]], + xaxis: { categories: chart.categories }, + grid: { + padding: { + top: 6, + left: 6, + right: 6, + bottom: 6, + }, + }, + fill: { + type: 'gradient', + gradient: { + colorStops: [ + { offset: 0, color: chartColors[0], opacity: 1 }, + { offset: 100, color: chartColors[1], opacity: 1 }, + ], + }, + }, + tooltip: { + y: { formatter: (value) => fNumber(value), title: { formatter: () => '' } }, + }, + ...chart.options, + }); + + const renderTrending = ( + + + + + + + {percent > 0 && '+'} + {fPercent(percent)} + + + last week + + + ); + + return ( + + + {title} + {fNumber(total)} + {renderTrending} + + + + + ); +} diff --git a/front_minimal/src/sections/overview/e-commerce/ecommerce-yearly-sales.jsx b/front_minimal/src/sections/overview/e-commerce/ecommerce-yearly-sales.jsx new file mode 100644 index 0000000..2feba1e --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/ecommerce-yearly-sales.jsx @@ -0,0 +1,64 @@ +import { useState, useCallback } from 'react'; + +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import CardHeader from '@mui/material/CardHeader'; + +import { fShortenNumber } from 'src/utils/format-number'; + +import { Chart, useChart, ChartSelect, ChartLegends } from 'src/components/chart'; + +// ---------------------------------------------------------------------- + +export function EcommerceYearlySales({ title, subheader, chart, ...other }) { + const theme = useTheme(); + + const [selectedSeries, setSelectedSeries] = useState('2023'); + + const chartColors = chart.colors ?? [theme.palette.primary.main, theme.palette.warning.main]; + + const chartOptions = useChart({ + colors: chartColors, + xaxis: { categories: chart.categories }, + ...chart.options, + }); + + const handleChangeSeries = useCallback((newValue) => { + setSelectedSeries(newValue); + }, []); + + const currentSeries = chart.series.find((i) => i.name === selectedSeries); + + return ( + + item.name)} + value={selectedSeries} + onChange={handleChangeSeries} + /> + } + sx={{ mb: 3 }} + /> + + item.name)} + values={[fShortenNumber(1234), fShortenNumber(6789)]} + sx={{ px: 3, gap: 3 }} + /> + + + + ); +} diff --git a/front_minimal/src/sections/overview/e-commerce/view/index.js b/front_minimal/src/sections/overview/e-commerce/view/index.js new file mode 100644 index 0000000..54dbb40 --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/view/index.js @@ -0,0 +1 @@ +export * from './overview-ecommerce-view'; diff --git a/front_minimal/src/sections/overview/e-commerce/view/overview-ecommerce-view.jsx b/front_minimal/src/sections/overview/e-commerce/view/overview-ecommerce-view.jsx new file mode 100644 index 0000000..e7402f9 --- /dev/null +++ b/front_minimal/src/sections/overview/e-commerce/view/overview-ecommerce-view.jsx @@ -0,0 +1,192 @@ +'use client'; + +import Button from '@mui/material/Button'; +import { useTheme } from '@mui/material/styles'; +import Grid from '@mui/material/Unstable_Grid2'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { MotivationIllustration } from 'src/assets/illustrations'; +import { + _ecommerceNewProducts, + _ecommerceBestSalesman, + _ecommerceSalesOverview, + _ecommerceLatestProducts, +} from 'src/_mock'; + +import { useMockedUser } from 'src/auth/hooks'; + +import { EcommerceWelcome } from '../ecommerce-welcome'; +import { EcommerceNewProducts } from '../ecommerce-new-products'; +import { EcommerceYearlySales } from '../ecommerce-yearly-sales'; +import { EcommerceBestSalesman } from '../ecommerce-best-salesman'; +import { EcommerceSaleByGender } from '../ecommerce-sale-by-gender'; +import { EcommerceSalesOverview } from '../ecommerce-sales-overview'; +import { EcommerceWidgetSummary } from '../ecommerce-widget-summary'; +import { EcommerceLatestProducts } from '../ecommerce-latest-products'; +import { EcommerceCurrentBalance } from '../ecommerce-current-balance'; + +// ---------------------------------------------------------------------- + +export function OverviewEcommerceView() { + const { user } = useMockedUser(); + + const theme = useTheme(); + + return ( + + + + } + action={ + + } + /> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/overview/file/view/index.js b/front_minimal/src/sections/overview/file/view/index.js new file mode 100644 index 0000000..9f92a5b --- /dev/null +++ b/front_minimal/src/sections/overview/file/view/index.js @@ -0,0 +1 @@ +export * from './overview-file-view'; diff --git a/front_minimal/src/sections/overview/file/view/overview-file-view.jsx b/front_minimal/src/sections/overview/file/view/overview-file-view.jsx new file mode 100644 index 0000000..a502c0a --- /dev/null +++ b/front_minimal/src/sections/overview/file/view/overview-file-view.jsx @@ -0,0 +1,264 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Grid from '@mui/material/Unstable_Grid2'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { CONFIG } from 'src/config-global'; +import { _files, _folders } from 'src/_mock'; +import { DashboardContent } from 'src/layouts/dashboard'; + +import { Iconify } from 'src/components/iconify'; +import { UploadBox } from 'src/components/upload'; +import { Scrollbar } from 'src/components/scrollbar'; + +import { FileWidget } from '../../../file-manager/file-widget'; +import { FileUpgrade } from '../../../file-manager/file-upgrade'; +import { FileRecentItem } from '../../../file-manager/file-recent-item'; +import { FileDataActivity } from '../../../file-manager/file-data-activity'; +import { FileManagerPanel } from '../../../file-manager/file-manager-panel'; +import { FileStorageOverview } from '../../../file-manager/file-storage-overview'; +import { FileManagerFolderItem } from '../../../file-manager/file-manager-folder-item'; +import { FileManagerNewFolderDialog } from '../../../file-manager/file-manager-new-folder-dialog'; + +// ---------------------------------------------------------------------- + +const GB = 1000000000 * 24; + +// ---------------------------------------------------------------------- + +export function OverviewFileView() { + const [folderName, setFolderName] = useState(''); + + const [files, setFiles] = useState([]); + + const upload = useBoolean(); + + const newFolder = useBoolean(); + + const handleChangeFolderName = useCallback((event) => { + setFolderName(event.target.value); + }, []); + + const handleCreateNewFolder = useCallback(() => { + newFolder.onFalse(); + setFolderName(''); + console.info('CREATE NEW FOLDER'); + }, [newFolder]); + + const handleDrop = useCallback( + (acceptedFiles) => { + setFiles([...files, ...acceptedFiles]); + }, + [files] + ); + + const renderStorageOverview = ( + + ), + }, + { + name: 'Media', + usedStorage: GB / 5, + filesCount: 223, + icon: ( + + ), + }, + { + name: 'Documents', + usedStorage: GB / 5, + filesCount: 223, + icon: ( + + ), + }, + { + name: 'Other', + usedStorage: GB / 10, + filesCount: 223, + icon: ( + + ), + }, + ]} + /> + ); + + return ( + <> + + + + {renderStorageOverview} + + + + + + + + + + + + + + + + + + + + + + + {_folders.map((folder) => ( + console.info('DELETE', folder.id)} + sx={{ ...(_folders.length > 3 && { width: 240, flexShrink: 0 }) }} + /> + ))} + + + + + + + {_files.slice(0, 5).map((file) => ( + console.info('DELETE', file.id)} + /> + ))} + + + + + + + + + Upload file + + } + sx={{ + py: 2.5, + width: 'auto', + height: 'auto', + borderRadius: 1.5, + }} + /> + + {renderStorageOverview} + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/payment/payment-billing-address.jsx b/front_minimal/src/sections/payment/payment-billing-address.jsx new file mode 100644 index 0000000..622648d --- /dev/null +++ b/front_minimal/src/sections/payment/payment-billing-address.jsx @@ -0,0 +1,20 @@ +import Stack from '@mui/material/Stack'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; + +// ---------------------------------------------------------------------- + +export function PaymentBillingAddress() { + return ( +
    + Billing address + + + + + + + +
    + ); +} diff --git a/front_minimal/src/sections/payment/payment-card-item.jsx b/front_minimal/src/sections/payment/payment-card-item.jsx new file mode 100644 index 0000000..e250ca7 --- /dev/null +++ b/front_minimal/src/sections/payment/payment-card-item.jsx @@ -0,0 +1,56 @@ +import Box from '@mui/material/Box'; +import Paper from '@mui/material/Paper'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function PaymentCardItem({ card, sx, ...other }) { + const popover = usePopover(); + + return ( + <> + + + + + {card.primary && } + + + {card.cardNumber} + + + + + + + + + + + Set as primary + + + + + Edit + + + + + Delete + + + + + ); +} diff --git a/front_minimal/src/sections/payment/payment-card-list-dialog.jsx b/front_minimal/src/sections/payment/payment-card-list-dialog.jsx new file mode 100644 index 0000000..6540636 --- /dev/null +++ b/front_minimal/src/sections/payment/payment-card-list-dialog.jsx @@ -0,0 +1,102 @@ +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { Iconify } from 'src/components/iconify'; +import { SearchNotFound } from 'src/components/search-not-found'; + +import { PaymentCardItem } from './payment-card-item'; + +// ---------------------------------------------------------------------- + +export function PaymentCardListDialog({ open, list, onClose, selected, onSelect }) { + const [searchCard, setSearchCard] = useState(''); + + const dataFiltered = applyFilter({ inputData: list, query: searchCard }); + + const notFound = !dataFiltered.length && !!searchCard; + + const handleSearchAddress = useCallback((event) => { + setSearchCard(event.target.value); + }, []); + + const handleSelectCard = useCallback( + (card) => { + onSelect(card); + setSearchCard(''); + onClose(); + }, + [onClose, onSelect] + ); + + const renderList = ( + + {list.map((card) => ( + handleSelectCard(card)} + sx={{ + cursor: 'pointer', + ...(selected(card.id) && { + boxShadow: (theme) => `0 0 0 2px ${theme.vars.palette.text.primary}`, + }), + }} + /> + ))} + + ); + + return ( + + + Cards + + + + + + + + + ), + }} + /> + + + {notFound ? : renderList} + + ); +} + +function applyFilter({ inputData, query }) { + if (query) { + return inputData.filter( + (card) => card.cardNumber.toLowerCase().indexOf(query.toLowerCase()) !== -1 + ); + } + + return inputData; +} diff --git a/front_minimal/src/sections/payment/payment-methods.jsx b/front_minimal/src/sections/payment/payment-methods.jsx new file mode 100644 index 0000000..7a559a4 --- /dev/null +++ b/front_minimal/src/sections/payment/payment-methods.jsx @@ -0,0 +1,132 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Paper from '@mui/material/Paper'; +import Button from '@mui/material/Button'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Iconify } from 'src/components/iconify'; + +import { PaymentNewCardDialog } from './payment-new-card-dialog'; + +// ---------------------------------------------------------------------- + +const PAYMENT_OPTIONS = [ + { value: 'paypal', label: 'Paypal' }, + { value: 'credit', label: 'Credit / Debit card' }, +]; + +const CARD_OPTIONS = [ + { value: 'visa1', label: '**** **** **** 1212 - Jimmy Holland' }, + { value: 'visa2', label: '**** **** **** 2424 - Shawn Stokes' }, + { value: 'mastercard', label: '**** **** **** 4545 - Cole Armstrong' }, +]; + +// ---------------------------------------------------------------------- + +export function PaymentMethods() { + const newCard = useBoolean(); + + const [method, setMethod] = useState('paypal'); + + const handleChangeMethod = useCallback((newValue) => { + setMethod(newValue); + }, []); + + return ( + <> + + Payment method + + + {PAYMENT_OPTIONS.map((option) => ( + handleChangeMethod(option.value)} + /> + ))} + + + + + + ); +} + +function OptionItem({ option, selected, isCredit, onOpen, ...other }) { + const { value, label } = option; + + return ( + `0 0 0 2px ${theme.vars.palette.text.primary}` }), + }} + {...other} + > + + + + + {label} + + + + {value === 'credit' && ( + <> + + , + + + )} + {value === 'paypal' && } + {value === 'cash' && } + +
    + } + primaryTypographyProps={{ typography: 'subtitle2' }} + /> + + {isCredit && ( + + + {CARD_OPTIONS.map((card) => ( + + ))} + + + + + )} + + ); +} diff --git a/front_minimal/src/sections/payment/payment-new-card-dialog.jsx b/front_minimal/src/sections/payment/payment-new-card-dialog.jsx new file mode 100644 index 0000000..a73c363 --- /dev/null +++ b/front_minimal/src/sections/payment/payment-new-card-dialog.jsx @@ -0,0 +1,84 @@ +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import Tooltip from '@mui/material/Tooltip'; +import TextField from '@mui/material/TextField'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function PaymentNewCardDialog({ onClose, ...other }) { + return ( + + New card + + + + + + + + + + + + + + + ), + }} + /> + + + + + Your transaction is secured with SSL encryption + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/payment/payment-summary.jsx b/front_minimal/src/sections/payment/payment-summary.jsx new file mode 100644 index 0000000..0f3f481 --- /dev/null +++ b/front_minimal/src/sections/payment/payment-summary.jsx @@ -0,0 +1,97 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Switch from '@mui/material/Switch'; +import Divider from '@mui/material/Divider'; +import Typography from '@mui/material/Typography'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function PaymentSummary({ sx, ...other }) { + const renderPrice = ( + + $ + + 9.99 + + + / mo + + + ); + + return ( + + + Summary + + + + + + Subscription + + + + + + + + Billed monthly + + + + + {renderPrice} + + + + + Total billed + + $9.99* + + + + + + + * Plus applicable taxes + + + + + + + + Secure credit card payment + + + + This is a secure 128-bit SSL encrypted payment + + + + ); +} diff --git a/front_minimal/src/sections/payment/view/index.js b/front_minimal/src/sections/payment/view/index.js new file mode 100644 index 0000000..b890618 --- /dev/null +++ b/front_minimal/src/sections/payment/view/index.js @@ -0,0 +1 @@ +export * from './payment-view'; diff --git a/front_minimal/src/sections/payment/view/payment-view.jsx b/front_minimal/src/sections/payment/view/payment-view.jsx new file mode 100644 index 0000000..75b6c88 --- /dev/null +++ b/front_minimal/src/sections/payment/view/payment-view.jsx @@ -0,0 +1,49 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Container from '@mui/material/Container'; +import Grid from '@mui/material/Unstable_Grid2'; +import Typography from '@mui/material/Typography'; + +import { PaymentSummary } from '../payment-summary'; +import { PaymentMethods } from '../payment-methods'; +import { PaymentBillingAddress } from '../payment-billing-address'; + +// ---------------------------------------------------------------------- + +export function PaymentView() { + return ( + + + {`Let's finish powering you up!`} + + + + Professional plan is right for you. + + + + + ({ md: `dashed 1px ${theme.vars.palette.divider}` }), + }} + > + + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/permission/view.jsx b/front_minimal/src/sections/permission/view.jsx new file mode 100644 index 0000000..bccceb5 --- /dev/null +++ b/front_minimal/src/sections/permission/view.jsx @@ -0,0 +1,74 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import ToggleButton from '@mui/material/ToggleButton'; +import ToggleButtonGroup from '@mui/material/ToggleButtonGroup'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { useMockedUser } from 'src/auth/hooks'; +import { RoleBasedGuard } from 'src/auth/guard'; + +// ---------------------------------------------------------------------- + +export function PermissionDeniedView() { + const [role, setRole] = useState('admin'); + + const { user } = useMockedUser(); + + const handleChangeRole = useCallback((event, newRole) => { + if (newRole !== null) { + setRole(newRole); + } + }, []); + + return ( + + + + + + Admin role + + + User role + + + + + + {[...Array(8)].map((_, index) => ( + + + + + Aliquam lorem ante, dapibus in, viverra quis, feugiat a, tellus. In enim justo, + rhoncus ut, imperdiet a, venenatis vitae, justo. Vestibulum fringilla pede sit amet + augue. + + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/pricing/pricing-card.jsx b/front_minimal/src/sections/pricing/pricing-card.jsx new file mode 100644 index 0000000..81792d4 --- /dev/null +++ b/front_minimal/src/sections/pricing/pricing-card.jsx @@ -0,0 +1,141 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import Typography from '@mui/material/Typography'; + +import { varAlpha, stylesMode } from 'src/theme/styles'; +import { PlanFreeIcon, PlanStarterIcon, PlanPremiumIcon } from 'src/assets/icons'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function PricingCard({ card, sx, ...other }) { + const { subscription, price, caption, lists, labelAction } = card; + + const basic = subscription === 'basic'; + + const starter = subscription === 'starter'; + + const premium = subscription === 'premium'; + + const renderIcon = ( + + {basic && } + {starter && } + {premium && } + + {starter && } + + ); + + const renderSubscription = ( + + + {subscription} + + {caption} + + ); + + const renderPrice = basic ? ( + Free + ) : ( + + $ + + {price} + + + / mo + + + ); + + const renderList = ( + + + + Features + + + All + + + + {lists.map((item) => ( + + + {item} + + ))} + + ); + + return ( + ({ xs: theme.customShadows.card, md: 'none' }), + ...((basic || starter) && { + borderTopRightRadius: { md: 0 }, + borderBottomRightRadius: { md: 0 }, + }), + ...((starter || premium) && { + boxShadow: (theme) => ({ + xs: theme.customShadows.card, + md: `-40px 40px 80px 0px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.16)}`, + }), + [stylesMode.dark]: { + boxShadow: (theme) => ({ + xs: theme.customShadows.card, + md: `-40px 40px 80px 0px ${varAlpha(theme.vars.palette.common.blackChannel, 0.16)}`, + }), + }, + }), + ...sx, + }} + {...other} + > + {renderIcon} + + {renderSubscription} + + {renderPrice} + + + + {renderList} + + + + ); +} diff --git a/front_minimal/src/sections/pricing/view/index.js b/front_minimal/src/sections/pricing/view/index.js new file mode 100644 index 0000000..f6ac0d4 --- /dev/null +++ b/front_minimal/src/sections/pricing/view/index.js @@ -0,0 +1 @@ +export * from './pricing-view'; diff --git a/front_minimal/src/sections/pricing/view/pricing-view.jsx b/front_minimal/src/sections/pricing/view/pricing-view.jsx new file mode 100644 index 0000000..5adffdb --- /dev/null +++ b/front_minimal/src/sections/pricing/view/pricing-view.jsx @@ -0,0 +1,78 @@ +'use client'; + +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Switch from '@mui/material/Switch'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { _pricingPlans } from 'src/_mock'; + +import { PricingCard } from '../pricing-card'; + +// ---------------------------------------------------------------------- + +const arrowIcon = ( + + + + +); + +// ---------------------------------------------------------------------- + +export function PricingView() { + return ( + + + Flexible plans for your +
    {`community's size and needs`} +
    + + + Choose your plan and make modern online conversation magic + + + + + MONTHLY + + + + + + {arrowIcon} + + save 10% + + + + YEARLY + + + + + + {_pricingPlans.map((card, index) => ( + + ))} + +
    + ); +} diff --git a/front_minimal/src/sections/product/components/cart-icon.jsx b/front_minimal/src/sections/product/components/cart-icon.jsx new file mode 100644 index 0000000..3fdb6b0 --- /dev/null +++ b/front_minimal/src/sections/product/components/cart-icon.jsx @@ -0,0 +1,38 @@ +import Box from '@mui/material/Box'; +import Badge from '@mui/material/Badge'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function CartIcon({ totalItems }) { + return ( + theme.spacing(1, 3, 1, 2), + boxShadow: (theme) => theme.customShadows.dropdown, + transition: (theme) => theme.transitions.create(['opacity']), + '&:hover': { opacity: 0.72 }, + }} + > + + + + + ); +} diff --git a/front_minimal/src/sections/product/components/incrementer-button.jsx b/front_minimal/src/sections/product/components/incrementer-button.jsx new file mode 100644 index 0000000..75f6dc3 --- /dev/null +++ b/front_minimal/src/sections/product/components/incrementer-button.jsx @@ -0,0 +1,49 @@ +import { forwardRef } from 'react'; + +import Stack from '@mui/material/Stack'; +import IconButton from '@mui/material/IconButton'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +export const IncrementerButton = forwardRef( + ({ quantity, onIncrease, onDecrease, disabledIncrease, disabledDecrease, sx, ...other }, ref) => ( + `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.2)}`, + ...sx, + }} + {...other} + > + + + + + {quantity} + + + + + + ) +); diff --git a/front_minimal/src/sections/product/product-details-carousel.jsx b/front_minimal/src/sections/product/product-details-carousel.jsx new file mode 100644 index 0000000..34846e0 --- /dev/null +++ b/front_minimal/src/sections/product/product-details-carousel.jsx @@ -0,0 +1,87 @@ +import { useEffect } from 'react'; + +import Box from '@mui/material/Box'; + +import { Image } from 'src/components/image'; +import { Lightbox, useLightBox } from 'src/components/lightbox'; +import { + Carousel, + useCarousel, + CarouselThumb, + CarouselThumbs, + CarouselArrowNumberButtons, +} from 'src/components/carousel'; + +// ---------------------------------------------------------------------- + +export function ProductDetailsCarousel({ images }) { + const carousel = useCarousel({ + thumbs: { + slidesToShow: 'auto', + }, + }); + + const slides = images?.map((img) => ({ src: img })) || []; + + const lightbox = useLightBox(slides); + + useEffect(() => { + if (lightbox.open) { + carousel.mainApi?.scrollTo(lightbox.selected, true); + } + }, [carousel.mainApi, lightbox.open, lightbox.selected]); + + return ( + <> +
    + + + + + {slides.map((slide) => ( + {slide.src} lightbox.onOpen(slide.src)} + sx={{ cursor: 'zoom-in', minWidth: 320 }} + /> + ))} + + + + + {slides.map((item, index) => ( + carousel.thumbs.onClickThumb(index)} + /> + ))} + +
    + + lightbox.setSelected(index)} + /> + + ); +} diff --git a/front_minimal/src/sections/product/product-details-description.jsx b/front_minimal/src/sections/product/product-details-description.jsx new file mode 100644 index 0000000..53ff91a --- /dev/null +++ b/front_minimal/src/sections/product/product-details-description.jsx @@ -0,0 +1,25 @@ +import { Markdown } from 'src/components/markdown'; + +// ---------------------------------------------------------------------- + +export function ProductDetailsDescription({ description }) { + return ( + + ); +} diff --git a/front_minimal/src/sections/product/product-details-review.jsx b/front_minimal/src/sections/product/product-details-review.jsx new file mode 100644 index 0000000..b72e9ee --- /dev/null +++ b/front_minimal/src/sections/product/product-details-review.jsx @@ -0,0 +1,116 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Rating from '@mui/material/Rating'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import Typography from '@mui/material/Typography'; +import LinearProgress from '@mui/material/LinearProgress'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { sumBy } from 'src/utils/helper'; +import { fShortenNumber } from 'src/utils/format-number'; + +import { Iconify } from 'src/components/iconify'; + +import { ProductReviewList } from './product-review-list'; +import { ProductReviewNewForm } from './product-review-new-form'; + +// ---------------------------------------------------------------------- + +export function ProductDetailsReview({ totalRatings, totalReviews, ratings = [], reviews = [] }) { + const review = useBoolean(); + + const total = sumBy(ratings, (star) => star.starCount); + + const renderSummary = ( + + Average rating + + + {totalRatings} + /5 + + + + + + ({fShortenNumber(totalReviews)} reviews) + + + ); + + const renderProgress = ( + ({ md: `dashed 1px ${theme.vars.palette.divider}` }), + borderRight: (theme) => ({ md: `dashed 1px ${theme.vars.palette.divider}` }), + }} + > + {ratings + .slice(0) + .reverse() + .map((rating) => ( + + + {rating.name} + + + + + + {fShortenNumber(rating.reviewCount)} + + + ))} + + ); + + const renderReviewButton = ( + + + + ); + + return ( + <> + + {renderSummary} + + {renderProgress} + + {renderReviewButton} + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/product/product-details-summary.jsx b/front_minimal/src/sections/product/product-details-summary.jsx new file mode 100644 index 0000000..c927eeb --- /dev/null +++ b/front_minimal/src/sections/product/product-details-summary.jsx @@ -0,0 +1,309 @@ +import { useEffect, useCallback } from 'react'; +import { useForm, Controller } from 'react-hook-form'; + +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Rating from '@mui/material/Rating'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import MenuItem from '@mui/material/MenuItem'; +import Typography from '@mui/material/Typography'; +import { formHelperTextClasses } from '@mui/material/FormHelperText'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { fCurrency, fShortenNumber } from 'src/utils/format-number'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { Form, Field } from 'src/components/hook-form'; +import { ColorPicker } from 'src/components/color-utils'; + +import { IncrementerButton } from './components/incrementer-button'; + +// ---------------------------------------------------------------------- + +export function ProductDetailsSummary({ + items, + product, + onAddCart, + onGotoStep, + disableActions, + ...other +}) { + const router = useRouter(); + + const { + id, + name, + sizes, + price, + coverUrl, + colors, + newLabel, + available, + priceSale, + saleLabel, + totalRatings, + totalReviews, + inventoryType, + subDescription, + } = product; + + const existProduct = !!items?.length && items.map((item) => item.id).includes(id); + + const isMaxQuantity = + !!items?.length && + items.filter((item) => item.id === id).map((item) => item.quantity)[0] >= available; + + const defaultValues = { + id, + name, + coverUrl, + available, + price, + colors: colors[0], + size: sizes[4], + quantity: available < 1 ? 0 : 1, + }; + + const methods = useForm({ defaultValues }); + + const { reset, watch, control, setValue, handleSubmit } = methods; + + const values = watch(); + + useEffect(() => { + if (product) { + reset(defaultValues); + } + // eslint-disable-next-line react-hooks/exhaustive-deps + }, [product]); + + const onSubmit = handleSubmit(async (data) => { + try { + if (!existProduct) { + onAddCart?.({ ...data, colors: [values.colors], subtotal: data.price * data.quantity }); + } + onGotoStep?.(0); + router.push(paths.product.checkout); + } catch (error) { + console.error(error); + } + }); + + const handleAddCart = useCallback(() => { + try { + onAddCart?.({ ...values, colors: [values.colors], subtotal: values.price * values.quantity }); + } catch (error) { + console.error(error); + } + }, [onAddCart, values]); + + const renderPrice = ( + + {priceSale && ( + + {fCurrency(priceSale)} + + )} + + {fCurrency(price)} + + ); + + const renderShare = ( + + + + Compare + + + + + Favorite + + + + + Share + + + ); + + const renderColorOptions = ( + + + Color + + + ( + field.onChange(color)} + limit={4} + /> + )} + /> + + ); + + const renderSizeOptions = ( + + + Size + + + + Size chart + + } + sx={{ + maxWidth: 88, + [`& .${formHelperTextClasses.root}`]: { mx: 0, mt: 1, textAlign: 'right' }, + }} + > + {sizes.map((size) => ( + + {size} + + ))} + + + ); + + const renderQuantity = ( + + + Quantity + + + + = available} + onIncrease={() => setValue('quantity', values.quantity + 1)} + onDecrease={() => setValue('quantity', values.quantity - 1)} + /> + + + Available: {available} + + + + ); + + const renderActions = ( + + + + + + ); + + const renderSubDescription = ( + + {subDescription} + + ); + + const renderRating = ( + + + {`(${fShortenNumber(totalReviews)} reviews)`} + + ); + + const renderLabels = (newLabel.enabled || saleLabel.enabled) && ( + + {newLabel.enabled && } + {saleLabel.enabled && } + + ); + + const renderInventoryType = ( + + {inventoryType} + + ); + + return ( +
    + + + {renderLabels} + + {renderInventoryType} + + {name} + + {renderRating} + + {renderPrice} + + {renderSubDescription} + + + + + {renderColorOptions} + + {renderSizeOptions} + + {renderQuantity} + + + + {renderActions} + + {renderShare} + +
    + ); +} diff --git a/front_minimal/src/sections/product/product-details-toolbar.jsx b/front_minimal/src/sections/product/product-details-toolbar.jsx new file mode 100644 index 0000000..0070d58 --- /dev/null +++ b/front_minimal/src/sections/product/product-details-toolbar.jsx @@ -0,0 +1,94 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Tooltip from '@mui/material/Tooltip'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { RouterLink } from 'src/routes/components'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function ProductDetailsToolbar({ + publish, + backLink, + editLink, + liveLink, + publishOptions, + onChangePublish, + sx, + ...other +}) { + const popover = usePopover(); + + return ( + <> + + + + + + {publish === 'published' && ( + + + + + + )} + + + + + + + + } + onClick={popover.onOpen} + sx={{ textTransform: 'capitalize' }} + > + {publish} + + + + + + {publishOptions.map((option) => ( + { + popover.onClose(); + onChangePublish(option.value); + }} + > + {option.value === 'published' && } + {option.value === 'draft' && } + {option.label} + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/product/product-filters-result.jsx b/front_minimal/src/sections/product/product-filters-result.jsx new file mode 100644 index 0000000..ffaeaf6 --- /dev/null +++ b/front_minimal/src/sections/product/product-filters-result.jsx @@ -0,0 +1,86 @@ +import Box from '@mui/material/Box'; +import Chip from '@mui/material/Chip'; + +import { varAlpha } from 'src/theme/styles'; + +import { chipProps, FiltersBlock, FiltersResult } from 'src/components/filters-result'; + +// ---------------------------------------------------------------------- + +export function ProductFiltersResult({ filters, totalResults, sx }) { + const handleRemoveGender = (inputValue) => { + const newValue = filters.state.gender.filter((item) => item !== inputValue); + + filters.setState({ gender: newValue }); + }; + + const handleRemoveCategory = () => { + filters.setState({ category: 'all' }); + }; + + const handleRemoveColor = (inputValue) => { + const newValue = filters.state.colors.filter((item) => item !== inputValue); + + filters.setState({ colors: newValue }); + }; + + const handleRemovePrice = () => { + filters.setState({ priceRange: [0, 200] }); + }; + + const handleRemoveRating = () => { + filters.setState({ rating: '' }); + }; + + return ( + + + {filters.state.gender.map((item) => ( + handleRemoveGender(item)} /> + ))} + + + + + + + + {filters.state.colors.map((item) => ( + + `solid 1px ${varAlpha(theme.vars.palette.common.whiteChannel, 0.24)}`, + }} + /> + } + onDelete={() => handleRemoveColor(item)} + /> + ))} + + + + + + + + + + + ); +} diff --git a/front_minimal/src/sections/product/product-filters.jsx b/front_minimal/src/sections/product/product-filters.jsx new file mode 100644 index 0000000..119515f --- /dev/null +++ b/front_minimal/src/sections/product/product-filters.jsx @@ -0,0 +1,313 @@ +import { useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Radio from '@mui/material/Radio'; +import Stack from '@mui/material/Stack'; +import Badge from '@mui/material/Badge'; +import Drawer from '@mui/material/Drawer'; +import Rating from '@mui/material/Rating'; +import Button from '@mui/material/Button'; +import Slider from '@mui/material/Slider'; +import Divider from '@mui/material/Divider'; +import Tooltip from '@mui/material/Tooltip'; +import Checkbox from '@mui/material/Checkbox'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import FormControlLabel from '@mui/material/FormControlLabel'; +import InputBase, { inputBaseClasses } from '@mui/material/InputBase'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { ColorPicker } from 'src/components/color-utils'; + +// ---------------------------------------------------------------------- + +export function ProductFilters({ open, onOpen, onClose, canReset, filters, options }) { + const marksLabel = [...Array(21)].map((_, index) => { + const value = index * 10; + + const firstValue = index === 0 ? `$${value}` : `${value}`; + + return { value, label: index % 4 ? '' : firstValue }; + }); + + const handleFilterGender = useCallback( + (newValue) => { + const checked = filters.state.gender.includes(newValue) + ? filters.state.gender.filter((value) => value !== newValue) + : [...filters.state.gender, newValue]; + + filters.setState({ gender: checked }); + }, + [filters] + ); + + const handleFilterCategory = useCallback( + (newValue) => { + filters.setState({ category: newValue }); + }, + [filters] + ); + + const handleFilterColors = useCallback( + (newValue) => { + filters.setState({ colors: newValue }); + }, + [filters] + ); + + const handleFilterPriceRange = useCallback( + (event, newValue) => { + filters.setState({ priceRange: newValue }); + }, + [filters] + ); + + const handleFilterRating = useCallback( + (newValue) => { + filters.setState({ rating: newValue }); + }, + [filters] + ); + + const renderHead = ( + <> + + + Filters + + + + + + + + + + + + + + + + + + ); + + const renderGender = ( + + + Gender + + {options.genders.map((option) => ( + handleFilterGender(option.label)} + /> + } + label={option.label} + /> + ))} + + ); + + const renderCategory = ( + + + Category + + {options.categories.map((option) => ( + handleFilterCategory(option)} + /> + } + label={option} + sx={{ ...(option === 'all' && { textTransform: 'capitalize' }) }} + /> + ))} + + ); + + const renderColor = ( + + + Color + + handleFilterColors(colors)} + colors={options.colors} + limit={6} + /> + + ); + + const renderPrice = ( + + Price + + + + + + + `$${value}`} + valueLabelFormat={(value) => `$${value}`} + sx={{ alignSelf: 'center', width: `calc(100% - 24px)` }} + /> + + ); + + const renderRating = ( + + + Rating + + + {options.ratings.map((item, index) => ( + handleFilterRating(item)} + sx={{ + mb: 1, + gap: 1, + ml: -1, + p: 0.5, + display: 'flex', + borderRadius: 1, + cursor: 'pointer', + typography: 'body2', + alignItems: 'center', + '&:hover': { opacity: 0.48 }, + ...(filters.state.rating === item && { + bgcolor: 'action.selected', + }), + }} + > + & Up + + ))} + + ); + + return ( + <> + + + + {renderHead} + + + + {renderGender} + {renderCategory} + {renderColor} + {renderPrice} + {renderRating} + + + + + ); +} + +// ---------------------------------------------------------------------- + +function InputRange({ type, value, onFilters }) { + const min = value[0]; + + const max = value[1]; + + const handleBlurInputRange = useCallback(() => { + if (min < 0) { + onFilters({ priceRange: [0, max] }); + } + if (min > 200) { + onFilters({ priceRange: [200, max] }); + } + if (max < 0) { + onFilters({ priceRange: [min, 0] }); + } + if (max > 200) { + onFilters({ priceRange: [min, 200] }); + } + }, [max, min, onFilters]); + + return ( + + + {`${type} ($)`} + + + + type === 'min' + ? onFilters({ priceRange: [Number(event.target.value), max] }) + : onFilters({ priceRange: [min, Number(event.target.value)] }) + } + onBlur={handleBlurInputRange} + inputProps={{ + step: 10, + min: 0, + max: 200, + type: 'number', + 'aria-labelledby': 'input-slider', + }} + sx={{ + maxWidth: 48, + borderRadius: 0.75, + bgcolor: (theme) => varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + [`& .${inputBaseClasses.input}`]: { + pr: 1, + py: 0.75, + textAlign: 'right', + typography: 'body2', + }, + }} + /> + + ); +} diff --git a/front_minimal/src/sections/product/product-item.jsx b/front_minimal/src/sections/product/product-item.jsx new file mode 100644 index 0000000..02704c1 --- /dev/null +++ b/front_minimal/src/sections/product/product-item.jsx @@ -0,0 +1,140 @@ +import Fab from '@mui/material/Fab'; +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Tooltip from '@mui/material/Tooltip'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { fCurrency } from 'src/utils/format-number'; + +import { Label } from 'src/components/label'; +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; +import { ColorPreview } from 'src/components/color-utils'; + +import { useCheckoutContext } from '../checkout/context'; + +// ---------------------------------------------------------------------- + +export function ProductItem({ product }) { + const checkout = useCheckoutContext(); + + const { id, name, coverUrl, price, colors, available, sizes, priceSale, newLabel, saleLabel } = + product; + + const linkTo = paths.product.details(id); + + const handleAddCart = async () => { + const newProduct = { + id, + name, + coverUrl, + available, + price, + colors: [colors[0]], + size: sizes[0], + quantity: 1, + }; + try { + checkout.onAddToCart(newProduct); + } catch (error) { + console.error(error); + } + }; + + const renderLabels = (newLabel.enabled || saleLabel.enabled) && ( + + {newLabel.enabled && ( + + )} + {saleLabel.enabled && ( + + )} + + ); + + const renderImg = ( + + {!!available && ( + + theme.transitions.create('all', { + easing: theme.transitions.easing.easeInOut, + duration: theme.transitions.duration.shorter, + }), + }} + > + + + )} + + + {name} + + + ); + + const renderContent = ( + + + {name} + + + + + + + {priceSale && ( + + {fCurrency(priceSale)} + + )} + + {fCurrency(price)} + + + + ); + + return ( + + {renderLabels} + + {renderImg} + + {renderContent} + + ); +} diff --git a/front_minimal/src/sections/product/product-list.jsx b/front_minimal/src/sections/product/product-list.jsx new file mode 100644 index 0000000..cbb6082 --- /dev/null +++ b/front_minimal/src/sections/product/product-list.jsx @@ -0,0 +1,41 @@ +import Box from '@mui/material/Box'; +import Pagination, { paginationClasses } from '@mui/material/Pagination'; + +import { ProductItem } from './product-item'; +import { ProductItemSkeleton } from './product-skeleton'; + +// ---------------------------------------------------------------------- + +export function ProductList({ products, loading, ...other }) { + const renderLoading = ; + + const renderList = products.map((product) => ); + + return ( + <> + + {loading ? renderLoading : renderList} + + + {products.length > 8 && ( + + )} + + ); +} diff --git a/front_minimal/src/sections/product/product-new-edit-form.jsx b/front_minimal/src/sections/product/product-new-edit-form.jsx new file mode 100644 index 0000000..22fa9fb --- /dev/null +++ b/front_minimal/src/sections/product/product-new-edit-form.jsx @@ -0,0 +1,381 @@ +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; +import { useMemo, useState, useEffect, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Chip from '@mui/material/Chip'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Switch from '@mui/material/Switch'; +import Divider from '@mui/material/Divider'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import InputAdornment from '@mui/material/InputAdornment'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { + _tags, + PRODUCT_SIZE_OPTIONS, + PRODUCT_GENDER_OPTIONS, + PRODUCT_COLOR_NAME_OPTIONS, + PRODUCT_CATEGORY_GROUP_OPTIONS, +} from 'src/_mock'; + +import { toast } from 'src/components/snackbar'; +import { Form, Field, schemaHelper } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const NewProductSchema = zod.object({ + name: zod.string().min(1, { message: 'Name is required!' }), + description: schemaHelper.editor({ message: { required_error: 'Description is required!' } }), + images: schemaHelper.files({ message: { required_error: 'Images is required!' } }), + code: zod.string().min(1, { message: 'Product code is required!' }), + sku: zod.string().min(1, { message: 'Product sku is required!' }), + quantity: zod.number().min(1, { message: 'Quantity is required!' }), + colors: zod.string().array().nonempty({ message: 'Choose at least one option!' }), + sizes: zod.string().array().nonempty({ message: 'Choose at least one option!' }), + tags: zod.string().array().min(2, { message: 'Must have at least 2 items!' }), + gender: zod.string().array().nonempty({ message: 'Choose at least one option!' }), + price: zod.number().min(1, { message: 'Price should not be $0.00' }), + // Not required + category: zod.string(), + priceSale: zod.number(), + subDescription: zod.string(), + taxes: zod.number(), + saleLabel: zod.object({ enabled: zod.boolean(), content: zod.string() }), + newLabel: zod.object({ enabled: zod.boolean(), content: zod.string() }), +}); + +// ---------------------------------------------------------------------- + +export function ProductNewEditForm({ currentProduct }) { + const router = useRouter(); + + const [includeTaxes, setIncludeTaxes] = useState(false); + + const defaultValues = useMemo( + () => ({ + name: currentProduct?.name || '', + description: currentProduct?.description || '', + subDescription: currentProduct?.subDescription || '', + images: currentProduct?.images || [], + // + code: currentProduct?.code || '', + sku: currentProduct?.sku || '', + price: currentProduct?.price || 0, + quantity: currentProduct?.quantity || 0, + priceSale: currentProduct?.priceSale || 0, + tags: currentProduct?.tags || [], + taxes: currentProduct?.taxes || 0, + gender: currentProduct?.gender || [], + category: currentProduct?.category || PRODUCT_CATEGORY_GROUP_OPTIONS[0].classify[1], + colors: currentProduct?.colors || [], + sizes: currentProduct?.sizes || [], + newLabel: currentProduct?.newLabel || { enabled: false, content: '' }, + saleLabel: currentProduct?.saleLabel || { enabled: false, content: '' }, + }), + [currentProduct] + ); + + const methods = useForm({ + resolver: zodResolver(NewProductSchema), + defaultValues, + }); + + const { + reset, + watch, + setValue, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const values = watch(); + + useEffect(() => { + if (currentProduct) { + reset(defaultValues); + } + }, [currentProduct, defaultValues, reset]); + + useEffect(() => { + if (includeTaxes) { + setValue('taxes', 0); + } else { + setValue('taxes', currentProduct?.taxes || 0); + } + }, [currentProduct?.taxes, includeTaxes, setValue]); + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + reset(); + toast.success(currentProduct ? 'Update success!' : 'Create success!'); + router.push(paths.dashboard.product.root); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const handleRemoveFile = useCallback( + (inputFile) => { + const filtered = values.images && values.images?.filter((file) => file !== inputFile); + setValue('images', filtered); + }, + [setValue, values.images] + ); + + const handleRemoveAllFiles = useCallback(() => { + setValue('images', [], { shouldValidate: true }); + }, [setValue]); + + const handleChangeIncludeTaxes = useCallback((event) => { + setIncludeTaxes(event.target.checked); + }, []); + + const renderDetails = ( + + + + + + + + + + + + Content + + + + + Images + console.info('ON UPLOAD')} + /> + + + + ); + + const renderProperties = ( + + + + + + + + + + + + + + + {PRODUCT_CATEGORY_GROUP_OPTIONS.map((category) => ( + + {category.classify.map((classify) => ( + + ))} + + ))} + + + + + + + + option)} + getOptionLabel={(option) => option} + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + /> + + + Gender + + + + + + + + + + + + + + +
    +
    + ); + + const renderPricing = ( + + + + + + + + + $ + + + ), + }} + /> + + + + $ + + + ), + }} + /> + + + } + label="Price includes taxes" + /> + + {!includeTaxes && ( + + + % + + + ), + }} + /> + )} + + + ); + + const renderActions = ( + + } + label="Publish" + sx={{ pl: 3, flexGrow: 1 }} + /> + + + {!currentProduct ? 'Create product' : 'Save changes'} + + + ); + + return ( +
    + + {renderDetails} + + {renderProperties} + + {renderPricing} + + {renderActions} + +
    + ); +} diff --git a/front_minimal/src/sections/product/product-review-item.jsx b/front_minimal/src/sections/product/product-review-item.jsx new file mode 100644 index 0000000..37d2e25 --- /dev/null +++ b/front_minimal/src/sections/product/product-review-item.jsx @@ -0,0 +1,93 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Rating from '@mui/material/Rating'; +import Avatar from '@mui/material/Avatar'; +import Typography from '@mui/material/Typography'; +import ButtonBase from '@mui/material/ButtonBase'; +import ListItemText from '@mui/material/ListItemText'; + +import { fDate } from 'src/utils/format-time'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function ProductReviewItem({ review }) { + const renderInfo = ( + + + + + + ); + + const renderContent = ( + + + + {review.isPurchased && ( + + + Verified purchase + + )} + + {review.comment} + + {!!review.attachments?.length && ( + + {review.attachments.map((attachment) => ( + + ))} + + )} + + + + + 123 + + + + + 34 + + + + ); + + return ( + + {renderInfo} + + {renderContent} + + ); +} diff --git a/front_minimal/src/sections/product/product-review-list.jsx b/front_minimal/src/sections/product/product-review-list.jsx new file mode 100644 index 0000000..b75c601 --- /dev/null +++ b/front_minimal/src/sections/product/product-review-list.jsx @@ -0,0 +1,23 @@ +import Pagination, { paginationClasses } from '@mui/material/Pagination'; + +import { ProductReviewItem } from './product-review-item'; + +// ---------------------------------------------------------------------- + +export function ProductReviewList({ reviews }) { + return ( + <> + {reviews.map((review) => ( + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/product/product-review-new-form.jsx b/front_minimal/src/sections/product/product-review-new-form.jsx new file mode 100644 index 0000000..ff1dbae --- /dev/null +++ b/front_minimal/src/sections/product/product-review-new-form.jsx @@ -0,0 +1,98 @@ +import { z as zod } from 'zod'; +import { useCallback } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; + +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; + +import { Form, Field } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const ReviewSchema = zod.object({ + rating: zod.number().min(1, 'Rating must be greater than or equal to 1!'), + name: zod.string().min(1, { message: 'Name is required!' }), + review: zod.string().min(1, { message: 'Review is required!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), +}); + +// ---------------------------------------------------------------------- + +export function ProductReviewNewForm({ onClose, ...other }) { + const defaultValues = { + rating: 0, + review: '', + name: '', + email: '', + }; + + const methods = useForm({ + mode: 'all', + resolver: zodResolver(ReviewSchema), + defaultValues, + }); + + const { + reset, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + reset(); + onClose(); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const onCancel = useCallback(() => { + onClose(); + reset(); + }, [onClose, reset]); + + return ( + +
    + Add Review + + +
    + + Your review about this product: + + +
    + + + + + + +
    + + + + + + Post + + +
    +
    + ); +} diff --git a/front_minimal/src/sections/product/product-search.jsx b/front_minimal/src/sections/product/product-search.jsx new file mode 100644 index 0000000..3c27344 --- /dev/null +++ b/front_minimal/src/sections/product/product-search.jsx @@ -0,0 +1,112 @@ +import parse from 'autosuggest-highlight/parse'; +import match from 'autosuggest-highlight/match'; + +import Box from '@mui/material/Box'; +import Avatar from '@mui/material/Avatar'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; +import Autocomplete, { autocompleteClasses } from '@mui/material/Autocomplete'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { Iconify } from 'src/components/iconify'; +import { SearchNotFound } from 'src/components/search-not-found'; + +// ---------------------------------------------------------------------- + +export function ProductSearch({ query, results, onSearch, loading }) { + const router = useRouter(); + + const handleClick = (id) => { + router.push(paths.product.details(id)); + }; + + const handleKeyUp = (event) => { + if (query) { + if (event.key === 'Enter') { + const selectItem = results.filter((product) => product.name === query)[0]; + + handleClick(selectItem.id); + } + } + }; + + return ( + onSearch(newValue)} + getOptionLabel={(option) => option.name} + noOptionsText={} + isOptionEqualToValue={(option, value) => option.id === value.id} + slotProps={{ + popper: { placement: 'bottom-start', sx: { minWidth: 320 } }, + paper: { sx: { [` .${autocompleteClasses.option}`]: { pl: 0.75 } } }, + }} + renderInput={(params) => ( + + + + ), + endAdornment: ( + <> + {loading ? : null} + {params.InputProps.endAdornment} + + ), + }} + /> + )} + renderOption={(props, product, { inputValue }) => { + const matches = match(product.name, inputValue); + const parts = parse(product.name, matches); + + return ( + handleClick(product.id)} key={product.id}> + + +
    + {parts.map((part, index) => ( + + {part.text} + + ))} +
    +
    + ); + }} + /> + ); +} diff --git a/front_minimal/src/sections/product/product-skeleton.jsx b/front_minimal/src/sections/product/product-skeleton.jsx new file mode 100644 index 0000000..9a0f991 --- /dev/null +++ b/front_minimal/src/sections/product/product-skeleton.jsx @@ -0,0 +1,70 @@ +'use client'; + +import Stack from '@mui/material/Stack'; +import Paper from '@mui/material/Paper'; +import Skeleton from '@mui/material/Skeleton'; +import Grid from '@mui/material/Unstable_Grid2'; + +// ---------------------------------------------------------------------- + +export function ProductItemSkeleton({ sx, amount = 16, ...other }) { + return [...Array(amount)].map((_, index) => ( + + + + + + + + + + + + + + + + + + )); +} + +// ---------------------------------------------------------------------- + +export function ProductDetailsSkeleton({ ...other }) { + return ( + + + + + + + + + + + + + + + + + + {[...Array(3)].map((_, index) => ( + + + + + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/product/product-sort.jsx b/front_minimal/src/sections/product/product-sort.jsx new file mode 100644 index 0000000..0fb2abb --- /dev/null +++ b/front_minimal/src/sections/product/product-sort.jsx @@ -0,0 +1,53 @@ +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function ProductSort({ sort, onSort, sortOptions }) { + const popover = usePopover(); + + const sortLabel = sortOptions.find((option) => option.value === sort)?.label; + + return ( + <> + + + + + {sortOptions.map((option) => ( + { + popover.onClose(); + onSort(option.value); + }} + > + {option.label} + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/product/product-table-filters-result.jsx b/front_minimal/src/sections/product/product-table-filters-result.jsx new file mode 100644 index 0000000..b67139a --- /dev/null +++ b/front_minimal/src/sections/product/product-table-filters-result.jsx @@ -0,0 +1,55 @@ +import { useCallback } from 'react'; + +import Chip from '@mui/material/Chip'; + +import { sentenceCase } from 'src/utils/change-case'; + +import { chipProps, FiltersBlock, FiltersResult } from 'src/components/filters-result'; + +// ---------------------------------------------------------------------- + +export function ProductTableFiltersResult({ filters, totalResults, sx }) { + const handleRemoveStock = useCallback( + (inputValue) => { + const newValue = filters.state.stock.filter((item) => item !== inputValue); + + filters.setState({ stock: newValue }); + }, + [filters] + ); + + const handleRemovePublish = useCallback( + (inputValue) => { + const newValue = filters.state.publish.filter((item) => item !== inputValue); + + filters.setState({ publish: newValue }); + }, + [filters] + ); + + return ( + + + {filters.state.stock.map((item) => ( + handleRemoveStock(item)} + /> + ))} + + + + {filters.state.publish.map((item) => ( + handleRemovePublish(item)} + /> + ))} + + + ); +} diff --git a/front_minimal/src/sections/product/product-table-row.jsx b/front_minimal/src/sections/product/product-table-row.jsx new file mode 100644 index 0000000..396bdfa --- /dev/null +++ b/front_minimal/src/sections/product/product-table-row.jsx @@ -0,0 +1,96 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import ListItemText from '@mui/material/ListItemText'; +import LinearProgress from '@mui/material/LinearProgress'; + +import { fCurrency } from 'src/utils/format-number'; +import { fTime, fDate } from 'src/utils/format-time'; + +import { Label } from 'src/components/label'; + +// ---------------------------------------------------------------------- + +export function RenderCellPrice({ params }) { + return fCurrency(params.row.price); +} + +// ---------------------------------------------------------------------- + +export function RenderCellPublish({ params }) { + return ( + + ); +} + +// ---------------------------------------------------------------------- + +export function RenderCellCreatedAt({ params }) { + return ( + + {fDate(params.row.createdAt)} + + {fTime(params.row.createdAt)} + + + ); +} + +// ---------------------------------------------------------------------- + +export function RenderCellStock({ params }) { + return ( + + + {!!params.row.available && params.row.available} {params.row.inventoryType} + + ); +} + +// ---------------------------------------------------------------------- + +export function RenderCellProduct({ params, onViewRow }) { + return ( + + + + + {params.row.name} + + } + secondary={ + + {params.row.category} + + } + sx={{ display: 'flex', flexDirection: 'column' }} + /> + + ); +} diff --git a/front_minimal/src/sections/product/product-table-toolbar.jsx b/front_minimal/src/sections/product/product-table-toolbar.jsx new file mode 100644 index 0000000..4d0fc70 --- /dev/null +++ b/front_minimal/src/sections/product/product-table-toolbar.jsx @@ -0,0 +1,175 @@ +import { useCallback } from 'react'; + +import Select from '@mui/material/Select'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import Checkbox from '@mui/material/Checkbox'; +import InputLabel from '@mui/material/InputLabel'; +import FormControl from '@mui/material/FormControl'; +import OutlinedInput from '@mui/material/OutlinedInput'; + +import { useSetState } from 'src/hooks/use-set-state'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function ProductTableToolbar({ filters, options }) { + const popover = usePopover(); + + const local = useSetState({ + stock: filters.state.stock, + publish: filters.state.publish, + }); + + const handleChangeStock = useCallback( + (event) => { + const { + target: { value }, + } = event; + + local.setState({ stock: typeof value === 'string' ? value.split(',') : value }); + }, + [local] + ); + + const handleChangePublish = useCallback( + (event) => { + const { + target: { value }, + } = event; + + local.setState({ publish: typeof value === 'string' ? value.split(',') : value }); + }, + [local] + ); + + const handleFilterStock = useCallback(() => { + filters.setState({ stock: local.state.stock }); + }, [filters, local.state.stock]); + + const handleFilterPublish = useCallback(() => { + filters.setState({ publish: local.state.publish }); + }, [filters, local.state.publish]); + + return ( + <> + + Stock + + + + + + Publish + + + + + + { + popover.onClose(); + }} + > + + Print + + + { + popover.onClose(); + }} + > + + Import + + + { + popover.onClose(); + }} + > + + Export + + + + + ); +} diff --git a/front_minimal/src/sections/product/view/index.js b/front_minimal/src/sections/product/view/index.js new file mode 100644 index 0000000..fc68bad --- /dev/null +++ b/front_minimal/src/sections/product/view/index.js @@ -0,0 +1,11 @@ +export * from './product-edit-view'; + +export * from './product-shop-view'; + +export * from './product-list-view'; + +export * from './product-create-view'; + +export * from './product-details-view'; + +export * from './product-shop-details-view'; diff --git a/front_minimal/src/sections/product/view/product-create-view.jsx b/front_minimal/src/sections/product/view/product-create-view.jsx new file mode 100644 index 0000000..8be141f --- /dev/null +++ b/front_minimal/src/sections/product/view/product-create-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ProductNewEditForm } from '../product-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function ProductCreateView() { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/product/view/product-details-view.jsx b/front_minimal/src/sections/product/view/product-details-view.jsx new file mode 100644 index 0000000..5064783 --- /dev/null +++ b/front_minimal/src/sections/product/view/product-details-view.jsx @@ -0,0 +1,140 @@ +'use client'; + +import { useState, useEffect, useCallback } from 'react'; + +import Tab from '@mui/material/Tab'; +import Box from '@mui/material/Box'; +import Tabs from '@mui/material/Tabs'; +import Card from '@mui/material/Card'; +import Grid from '@mui/material/Unstable_Grid2'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; + +import { useTabs } from 'src/hooks/use-tabs'; + +import { varAlpha } from 'src/theme/styles'; +import { PRODUCT_PUBLISH_OPTIONS } from 'src/_mock'; +import { DashboardContent } from 'src/layouts/dashboard'; + +import { Iconify } from 'src/components/iconify'; + +import { ProductDetailsReview } from '../product-details-review'; +import { ProductDetailsSummary } from '../product-details-summary'; +import { ProductDetailsToolbar } from '../product-details-toolbar'; +import { ProductDetailsCarousel } from '../product-details-carousel'; +import { ProductDetailsDescription } from '../product-details-description'; + +// ---------------------------------------------------------------------- + +const SUMMARY = [ + { + title: '100% original', + description: 'Chocolate bar candy canes ice cream toffee cookie halvah.', + icon: 'solar:verified-check-bold', + }, + { + title: '10 days replacement', + description: 'Marshmallow biscuit donut dragée fruitcake wafer.', + icon: 'solar:clock-circle-bold', + }, + { + title: 'Year warranty', + description: 'Cotton candy gingerbread cake I love sugar sweet.', + icon: 'solar:shield-check-bold', + }, +]; + +// ---------------------------------------------------------------------- + +export function ProductDetailsView({ product }) { + const tabs = useTabs('description'); + + const [publish, setPublish] = useState(''); + + useEffect(() => { + if (product) { + setPublish(product?.publish); + } + }, [product]); + + const handleChangePublish = useCallback((newValue) => { + setPublish(newValue); + }, []); + + return ( + + + + + + + + + + {product && } + + + + + {SUMMARY.map((item) => ( + + + + + {item.title} + + + + {item.description} + + + ))} + + + + + `inset 0 -2px 0 0 ${varAlpha(theme.vars.palette.grey['500Channel'], 0.08)}`, + }} + > + {[ + { value: 'description', label: 'Description' }, + { value: 'reviews', label: `Reviews (${product?.reviews.length})` }, + ].map((tab) => ( + + ))} + + + {tabs.value === 'description' && ( + + )} + + {tabs.value === 'reviews' && ( + + )} + + + ); +} diff --git a/front_minimal/src/sections/product/view/product-edit-view.jsx b/front_minimal/src/sections/product/view/product-edit-view.jsx new file mode 100644 index 0000000..4781f59 --- /dev/null +++ b/front_minimal/src/sections/product/view/product-edit-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ProductNewEditForm } from '../product-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function ProductEditView({ product }) { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/product/view/product-list-view.jsx b/front_minimal/src/sections/product/view/product-list-view.jsx new file mode 100644 index 0000000..e7a4674 --- /dev/null +++ b/front_minimal/src/sections/product/view/product-list-view.jsx @@ -0,0 +1,366 @@ +'use client'; + +import { useState, useEffect, useCallback } from 'react'; + +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import { + DataGrid, + gridClasses, + GridToolbarExport, + GridActionsCellItem, + GridToolbarContainer, + GridToolbarQuickFilter, + GridToolbarFilterButton, + GridToolbarColumnsButton, +} from '@mui/x-data-grid'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useSetState } from 'src/hooks/use-set-state'; + +import { PRODUCT_STOCK_OPTIONS } from 'src/_mock'; +import { useGetProducts } from 'src/actions/product'; +import { DashboardContent } from 'src/layouts/dashboard'; + +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { EmptyContent } from 'src/components/empty-content'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { ProductTableToolbar } from '../product-table-toolbar'; +import { ProductTableFiltersResult } from '../product-table-filters-result'; +import { + RenderCellStock, + RenderCellPrice, + RenderCellPublish, + RenderCellProduct, + RenderCellCreatedAt, +} from '../product-table-row'; + +// ---------------------------------------------------------------------- + +const PUBLISH_OPTIONS = [ + { value: 'published', label: 'Published' }, + { value: 'draft', label: 'Draft' }, +]; + +const HIDE_COLUMNS = { category: false }; + +const HIDE_COLUMNS_TOGGLABLE = ['category', 'actions']; + +// ---------------------------------------------------------------------- + +export function ProductListView() { + const confirmRows = useBoolean(); + + const router = useRouter(); + + const { products, productsLoading } = useGetProducts(); + + const filters = useSetState({ publish: [], stock: [] }); + + const [tableData, setTableData] = useState([]); + + const [selectedRowIds, setSelectedRowIds] = useState([]); + + const [filterButtonEl, setFilterButtonEl] = useState(null); + + const [columnVisibilityModel, setColumnVisibilityModel] = useState(HIDE_COLUMNS); + + useEffect(() => { + if (products.length) { + setTableData(products); + } + }, [products]); + + const canReset = filters.state.publish.length > 0 || filters.state.stock.length > 0; + + const dataFiltered = applyFilter({ inputData: tableData, filters: filters.state }); + + const handleDeleteRow = useCallback( + (id) => { + const deleteRow = tableData.filter((row) => row.id !== id); + + toast.success('Delete success!'); + + setTableData(deleteRow); + }, + [tableData] + ); + + const handleDeleteRows = useCallback(() => { + const deleteRows = tableData.filter((row) => !selectedRowIds.includes(row.id)); + + toast.success('Delete success!'); + + setTableData(deleteRows); + }, [selectedRowIds, tableData]); + + const handleEditRow = useCallback( + (id) => { + router.push(paths.dashboard.product.edit(id)); + }, + [router] + ); + + const handleViewRow = useCallback( + (id) => { + router.push(paths.dashboard.product.details(id)); + }, + [router] + ); + + const CustomToolbarCallback = useCallback( + () => ( + + ), + // eslint-disable-next-line react-hooks/exhaustive-deps + [filters.state, selectedRowIds] + ); + + const columns = [ + { field: 'category', headerName: 'Category', filterable: false }, + { + field: 'name', + headerName: 'Product', + flex: 1, + minWidth: 360, + hideable: false, + renderCell: (params) => ( + handleViewRow(params.row.id)} /> + ), + }, + { + field: 'createdAt', + headerName: 'Create at', + width: 160, + renderCell: (params) => , + }, + { + field: 'inventoryType', + headerName: 'Stock', + width: 160, + type: 'singleSelect', + valueOptions: PRODUCT_STOCK_OPTIONS, + renderCell: (params) => , + }, + { + field: 'price', + headerName: 'Price', + width: 140, + editable: true, + renderCell: (params) => , + }, + { + field: 'publish', + headerName: 'Publish', + width: 110, + type: 'singleSelect', + editable: true, + valueOptions: PUBLISH_OPTIONS, + renderCell: (params) => , + }, + { + type: 'actions', + field: 'actions', + headerName: ' ', + align: 'right', + headerAlign: 'right', + width: 80, + sortable: false, + filterable: false, + disableColumnMenu: true, + getActions: (params) => [ + } + label="View" + onClick={() => handleViewRow(params.row.id)} + />, + } + label="Edit" + onClick={() => handleEditRow(params.row.id)} + />, + } + label="Delete" + onClick={() => { + handleDeleteRow(params.row.id); + }} + sx={{ color: 'error.main' }} + />, + ], + }, + ]; + + const getTogglableColumns = () => + columns + .filter((column) => !HIDE_COLUMNS_TOGGLABLE.includes(column.field)) + .map((column) => column.field); + + return ( + <> + + } + > + New product + + } + sx={{ mb: { xs: 3, md: 5 } }} + /> + + + 'auto'} + pageSizeOptions={[5, 10, 25]} + initialState={{ pagination: { paginationModel: { pageSize: 10 } } }} + onRowSelectionModelChange={(newSelectionModel) => setSelectedRowIds(newSelectionModel)} + columnVisibilityModel={columnVisibilityModel} + onColumnVisibilityModelChange={(newModel) => setColumnVisibilityModel(newModel)} + slots={{ + toolbar: CustomToolbarCallback, + noRowsOverlay: () => , + noResultsOverlay: () => , + }} + slotProps={{ + panel: { anchorEl: filterButtonEl }, + toolbar: { setFilterButtonEl }, + columnsManagement: { getTogglableColumns }, + }} + sx={{ [`& .${gridClasses.cell}`]: { alignItems: 'center', display: 'inline-flex' } }} + /> + + + + + Are you sure want to delete {selectedRowIds.length} items? + + } + action={ + + } + /> + + ); +} + +function CustomToolbar({ + filters, + canReset, + selectedRowIds, + filteredResults, + setFilterButtonEl, + onOpenConfirmDeleteRows, +}) { + return ( + <> + + + + + + + {!!selectedRowIds.length && ( + + )} + + + + + + + + {canReset && ( + + )} + + ); +} + +function applyFilter({ inputData, filters }) { + const { stock, publish } = filters; + + if (stock.length) { + inputData = inputData.filter((product) => stock.includes(product.inventoryType)); + } + + if (publish.length) { + inputData = inputData.filter((product) => publish.includes(product.publish)); + } + + return inputData; +} diff --git a/front_minimal/src/sections/product/view/product-shop-details-view.jsx b/front_minimal/src/sections/product/view/product-shop-details-view.jsx new file mode 100644 index 0000000..7e9c5e1 --- /dev/null +++ b/front_minimal/src/sections/product/view/product-shop-details-view.jsx @@ -0,0 +1,139 @@ +'use client'; + +import Tab from '@mui/material/Tab'; +import Box from '@mui/material/Box'; +import Tabs from '@mui/material/Tabs'; +import Card from '@mui/material/Card'; +import Grid from '@mui/material/Unstable_Grid2'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { paths } from 'src/routes/paths'; + +import { useTabs } from 'src/hooks/use-tabs'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { CartIcon } from '../components/cart-icon'; +import { useCheckoutContext } from '../../checkout/context'; +import { ProductDetailsReview } from '../product-details-review'; +import { ProductDetailsSummary } from '../product-details-summary'; +import { ProductDetailsCarousel } from '../product-details-carousel'; +import { ProductDetailsDescription } from '../product-details-description'; + +// ---------------------------------------------------------------------- + +const SUMMARY = [ + { + title: '100% original', + description: 'Chocolate bar candy canes ice cream toffee cookie halvah.', + icon: 'solar:verified-check-bold', + }, + { + title: '10 days replacement', + description: 'Marshmallow biscuit donut dragée fruitcake wafer.', + icon: 'solar:clock-circle-bold', + }, + { + title: 'Year warranty', + description: 'Cotton candy gingerbread cake I love sugar sweet.', + icon: 'solar:shield-check-bold', + }, +]; + +// ---------------------------------------------------------------------- + +export function ProductShopDetailsView({ product }) { + const checkout = useCheckoutContext(); + + const tabs = useTabs('description'); + + return ( + + + + + + + + + + + + {product && ( + + )} + + + + + {SUMMARY.map((item) => ( + + + + + {item.title} + + + + {item.description} + + + ))} + + + + + `inset 0 -2px 0 0 ${varAlpha(theme.vars.palette.grey['500Channel'], 0.08)}`, + }} + > + {[ + { value: 'description', label: 'Description' }, + { value: 'reviews', label: `Reviews (${product?.reviews.length})` }, + ].map((tab) => ( + + ))} + + + {tabs.value === 'description' && ( + + )} + + {tabs.value === 'reviews' && ( + + )} + + + ); +} diff --git a/front_minimal/src/sections/product/view/product-shop-view.jsx b/front_minimal/src/sections/product/view/product-shop-view.jsx new file mode 100644 index 0000000..ac124f9 --- /dev/null +++ b/front_minimal/src/sections/product/view/product-shop-view.jsx @@ -0,0 +1,196 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Container from '@mui/material/Container'; +import Typography from '@mui/material/Typography'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useDebounce } from 'src/hooks/use-debounce'; +import { useSetState } from 'src/hooks/use-set-state'; + +import { orderBy } from 'src/utils/helper'; + +import { useSearchProducts } from 'src/actions/product'; +import { + PRODUCT_SORT_OPTIONS, + PRODUCT_COLOR_OPTIONS, + PRODUCT_GENDER_OPTIONS, + PRODUCT_RATING_OPTIONS, + PRODUCT_CATEGORY_OPTIONS, +} from 'src/_mock'; + +import { EmptyContent } from 'src/components/empty-content'; + +import { ProductList } from '../product-list'; +import { ProductSort } from '../product-sort'; +import { ProductSearch } from '../product-search'; +import { CartIcon } from '../components/cart-icon'; +import { ProductFilters } from '../product-filters'; +import { useCheckoutContext } from '../../checkout/context'; +import { ProductFiltersResult } from '../product-filters-result'; + +// ---------------------------------------------------------------------- + +export function ProductShopView({ products }) { + const checkout = useCheckoutContext(); + + const openFilters = useBoolean(); + + const [sortBy, setSortBy] = useState('featured'); + + const [searchQuery, setSearchQuery] = useState(''); + + const debouncedQuery = useDebounce(searchQuery); + + const filters = useSetState({ + gender: [], + colors: [], + rating: '', + category: 'all', + priceRange: [0, 200], + }); + + const { searchResults, searchLoading } = useSearchProducts(debouncedQuery); + + const dataFiltered = applyFilter({ inputData: products, filters: filters.state, sortBy }); + + const canReset = + filters.state.gender.length > 0 || + filters.state.colors.length > 0 || + filters.state.rating !== '' || + filters.state.category !== 'all' || + filters.state.priceRange[0] !== 0 || + filters.state.priceRange[1] !== 200; + + const notFound = !dataFiltered.length && canReset; + + const handleSortBy = useCallback((newValue) => { + setSortBy(newValue); + }, []); + + const handleSearch = useCallback((inputValue) => { + setSearchQuery(inputValue); + }, []); + + const productsEmpty = !products.length; + + const renderFilters = ( + + + + + + + + + + ); + + const renderResults = ( + + ); + + const renderNotFound = ; + + return ( + + + + + Shop + + + + {renderFilters} + + {canReset && renderResults} + + + {(notFound || productsEmpty) && renderNotFound} + + + + ); +} + +function applyFilter({ inputData, filters, sortBy }) { + const { gender, category, colors, priceRange, rating } = filters; + + const min = priceRange[0]; + + const max = priceRange[1]; + + // Sort by + if (sortBy === 'featured') { + inputData = orderBy(inputData, ['totalSold'], ['desc']); + } + + if (sortBy === 'newest') { + inputData = orderBy(inputData, ['createdAt'], ['desc']); + } + + if (sortBy === 'priceDesc') { + inputData = orderBy(inputData, ['price'], ['desc']); + } + + if (sortBy === 'priceAsc') { + inputData = orderBy(inputData, ['price'], ['asc']); + } + + // filters + if (gender.length) { + inputData = inputData.filter((product) => product.gender.some((i) => gender.includes(i))); + } + + if (category !== 'all') { + inputData = inputData.filter((product) => product.category === category); + } + + if (colors.length) { + inputData = inputData.filter((product) => + product.colors.some((color) => colors.includes(color)) + ); + } + + if (min !== 0 || max !== 200) { + inputData = inputData.filter((product) => product.price >= min && product.price <= max); + } + + if (rating) { + inputData = inputData.filter((product) => { + const convertRating = (value) => { + if (value === 'up4Star') return 4; + if (value === 'up3Star') return 3; + if (value === 'up2Star') return 2; + return 1; + }; + return product.totalRatings > convertRating(rating); + }); + } + + return inputData; +} diff --git a/front_minimal/src/sections/tour/tour-details-bookers.jsx b/front_minimal/src/sections/tour/tour-details-bookers.jsx new file mode 100644 index 0000000..71c41c2 --- /dev/null +++ b/front_minimal/src/sections/tour/tour-details-bookers.jsx @@ -0,0 +1,134 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Pagination from '@mui/material/Pagination'; +import IconButton from '@mui/material/IconButton'; +import ListItemText from '@mui/material/ListItemText'; + +import { varAlpha } from 'src/theme/styles'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function TourDetailsBookers({ bookers }) { + const [approved, setApproved] = useState([]); + + const handleClick = useCallback( + (item) => { + const selected = approved.includes(item) + ? approved.filter((value) => value !== item) + : [...approved, item]; + + setApproved(selected); + }, + [approved] + ); + + return ( + <> + + {bookers?.map((booker) => ( + handleClick(booker.id)} + /> + ))} + + + + + ); +} + +function BookerItem({ booker, selected, onSelected }) { + return ( + + + + + + + {booker.guests} guests + + } + secondaryTypographyProps={{ + mt: 0.5, + component: 'span', + typography: 'caption', + color: 'text.disabled', + }} + /> + + + varAlpha(theme.vars.palette.error.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.error.mainChannel, 0.16), + }, + }} + > + + + + varAlpha(theme.vars.palette.info.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.info.mainChannel, 0.16), + }, + }} + > + + + + varAlpha(theme.vars.palette.primary.mainChannel, 0.08), + '&:hover': { + bgcolor: (theme) => varAlpha(theme.vars.palette.primary.mainChannel, 0.16), + }, + }} + > + + + + + + + + ); +} diff --git a/front_minimal/src/sections/tour/tour-details-content.jsx b/front_minimal/src/sections/tour/tour-details-content.jsx new file mode 100644 index 0000000..bbc971d --- /dev/null +++ b/front_minimal/src/sections/tour/tour-details-content.jsx @@ -0,0 +1,222 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Divider from '@mui/material/Divider'; +import Checkbox from '@mui/material/Checkbox'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { fDate } from 'src/utils/format-time'; + +import { TOUR_SERVICE_OPTIONS } from 'src/_mock'; + +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; +import { Markdown } from 'src/components/markdown'; +import { Lightbox, useLightBox } from 'src/components/lightbox'; + +// ---------------------------------------------------------------------- + +export function TourDetailsContent({ tour }) { + const slides = tour?.images.map((slide) => ({ src: slide })) || []; + + const { + selected: selectedImage, + open: openLightbox, + onOpen: handleOpenLightbox, + onClose: handleCloseLightbox, + } = useLightBox(slides); + + const renderGallery = ( + <> + + {slides[0].src} handleOpenLightbox(slides[0].src)} + sx={{ + borderRadius: 2, + cursor: 'pointer', + transition: (theme) => theme.transitions.create('opacity'), + '&:hover': { opacity: 0.8 }, + }} + /> + + + {slides.slice(1, 5).map((slide) => ( + {slide.src} handleOpenLightbox(slide.src)} + sx={{ + borderRadius: 2, + cursor: 'pointer', + transition: (theme) => theme.transitions.create('opacity'), + '&:hover': { opacity: 0.8 }, + }} + /> + ))} + + + + + + ); + + const renderHead = ( + <> + + + {tour?.name} + + + + + + + } + checkedIcon={} + inputProps={{ id: 'favorite-checkbox', 'aria-label': 'Favorite checkbox' }} + /> + + + + + + + {tour?.ratingNumber} + + (234 reviews) + + + + + {tour?.destination} + + + + + + Guide by + + {tour?.tourGuides.map((tourGuide) => tourGuide.name).join(', ')} + + + + ); + + const renderOverview = ( + + {[ + { + label: 'Available', + value: `${fDate(tour?.available.startDate)} - ${fDate(tour?.available.endDate)}`, + icon: , + }, + { + label: 'Contact name', + value: tour?.tourGuides.map((tourGuide) => tourGuide.phoneNumber).join(', '), + icon: , + }, + { + label: 'Durations', + value: tour?.durations, + icon: , + }, + { + label: 'Contact phone', + value: tour?.tourGuides.map((tourGuide) => tourGuide.name).join(', '), + icon: , + }, + ].map((item) => ( + + {item.icon} + + + ))} + + ); + + const renderContent = ( + <> + + + + Services + + + {TOUR_SERVICE_OPTIONS.map((service) => ( + + + {service.label} + + ))} + + + + ); + + return ( + <> + {renderGallery} + + + {renderHead} + + + + {renderOverview} + + + + {renderContent} + + + ); +} diff --git a/front_minimal/src/sections/tour/tour-details-toolbar.jsx b/front_minimal/src/sections/tour/tour-details-toolbar.jsx new file mode 100644 index 0000000..a631dae --- /dev/null +++ b/front_minimal/src/sections/tour/tour-details-toolbar.jsx @@ -0,0 +1,94 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Tooltip from '@mui/material/Tooltip'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import LoadingButton from '@mui/lab/LoadingButton'; + +import { RouterLink } from 'src/routes/components'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function TourDetailsToolbar({ + publish, + backLink, + editLink, + liveLink, + publishOptions, + onChangePublish, + sx, + ...other +}) { + const popover = usePopover(); + + return ( + <> + + + + + + {publish === 'published' && ( + + + + + + )} + + + + + + + + } + onClick={popover.onOpen} + sx={{ textTransform: 'capitalize' }} + > + {publish} + + + + + + {publishOptions.map((option) => ( + { + popover.onClose(); + onChangePublish(option.value); + }} + > + {option.value === 'published' && } + {option.value === 'draft' && } + {option.label} + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/tour/tour-filters-result.jsx b/front_minimal/src/sections/tour/tour-filters-result.jsx new file mode 100644 index 0000000..488adf3 --- /dev/null +++ b/front_minimal/src/sections/tour/tour-filters-result.jsx @@ -0,0 +1,92 @@ +import { useCallback } from 'react'; + +import Chip from '@mui/material/Chip'; +import Avatar from '@mui/material/Avatar'; + +import { fDateRangeShortLabel } from 'src/utils/format-time'; + +import { chipProps, FiltersBlock, FiltersResult } from 'src/components/filters-result'; + +// ---------------------------------------------------------------------- + +export function TourFiltersResult({ filters, totalResults, sx }) { + const handleRemoveServices = useCallback( + (inputValue) => { + const newValue = filters.state.services.filter((item) => item !== inputValue); + + filters.setState({ services: newValue }); + }, + [filters] + ); + + const handleRemoveAvailable = useCallback(() => { + filters.setState({ startDate: null, endDate: null }); + }, [filters]); + + const handleRemoveTourGuide = useCallback( + (inputValue) => { + const newValue = filters.state.tourGuides.filter((item) => item.name !== inputValue.name); + + filters.setState({ tourGuides: newValue }); + }, + [filters] + ); + + const handleRemoveDestination = useCallback( + (inputValue) => { + const newValue = filters.state.destination.filter((item) => item !== inputValue); + + filters.setState({ destination: newValue }); + }, + [filters] + ); + + return ( + + + + + + + {filters.state.services.map((item) => ( + handleRemoveServices(item)} + /> + ))} + + + + {filters.state.tourGuides.map((item) => ( + } + label={item.name} + onDelete={() => handleRemoveTourGuide(item)} + /> + ))} + + + + {filters.state.destination.map((item) => ( + handleRemoveDestination(item)} + /> + ))} + + + ); +} diff --git a/front_minimal/src/sections/tour/tour-filters.jsx b/front_minimal/src/sections/tour/tour-filters.jsx new file mode 100644 index 0000000..589799c --- /dev/null +++ b/front_minimal/src/sections/tour/tour-filters.jsx @@ -0,0 +1,231 @@ +import { useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Chip from '@mui/material/Chip'; +import Stack from '@mui/material/Stack'; +import Badge from '@mui/material/Badge'; +import Drawer from '@mui/material/Drawer'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import Tooltip from '@mui/material/Tooltip'; +import Checkbox from '@mui/material/Checkbox'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import Autocomplete from '@mui/material/Autocomplete'; +import { DatePicker } from '@mui/x-date-pickers/DatePicker'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { CountrySelect } from 'src/components/country-select'; + +// ---------------------------------------------------------------------- + +export function TourFilters({ open, onOpen, onClose, filters, options, canReset, dateError }) { + const handleFilterServices = useCallback( + (newValue) => { + const checked = filters.state.services.includes(newValue) + ? filters.state.services.filter((value) => value !== newValue) + : [...filters.state.services, newValue]; + + filters.setState({ services: checked }); + }, + [filters] + ); + + const handleFilterStartDate = useCallback( + (newValue) => { + filters.setState({ startDate: newValue }); + }, + [filters] + ); + + const handleFilterEndDate = useCallback( + (newValue) => { + filters.setState({ endDate: newValue }); + }, + [filters] + ); + + const handleFilterDestination = useCallback( + (newValue) => { + filters.setState({ destination: newValue }); + }, + [filters] + ); + + const handleFilterTourGuide = useCallback( + (newValue) => { + filters.setState({ tourGuides: newValue }); + }, + [filters] + ); + + const renderHead = ( + <> + + + Filters + + + + + + + + + + + + + + + + + + ); + + const renderDateRange = ( + + + Durations + + + + + + + ); + + const renderDestination = ( + + + Destination + + + handleFilterDestination(newValue)} + /> + + ); + + const renderTourGuide = ( + + + Tour guide + + + handleFilterTourGuide(newValue)} + getOptionLabel={(option) => option.name} + renderInput={(params) => } + renderOption={(props, tourGuide) => ( +
  • + + + {tourGuide.name} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((tourGuide, index) => ( + } + /> + )) + } + /> +
    + ); + + const renderServices = ( + + + Services + + {options.services.map((option) => ( + handleFilterServices(option)} + /> + } + label={option} + /> + ))} + + ); + + return ( + <> + + + + {renderHead} + + + + {renderDateRange} + {renderDestination} + {renderTourGuide} + {renderServices} + + + + + ); +} diff --git a/front_minimal/src/sections/tour/tour-item.jsx b/front_minimal/src/sections/tour/tour-item.jsx new file mode 100644 index 0000000..dfe998f --- /dev/null +++ b/front_minimal/src/sections/tour/tour-item.jsx @@ -0,0 +1,206 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import IconButton from '@mui/material/IconButton'; +import ListItemText from '@mui/material/ListItemText'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { fCurrency } from 'src/utils/format-number'; +import { fDateTime, fDateRangeShortLabel } from 'src/utils/format-time'; + +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function TourItem({ tour, onView, onEdit, onDelete }) { + const popover = usePopover(); + + const renderRating = ( + + {tour.ratingNumber} + + ); + + const renderPrice = ( + + {!!tour.priceSale && ( + + {fCurrency(tour.priceSale)} + + )} + {fCurrency(tour.price)} + + ); + + const renderImages = ( + + + {renderPrice} + {renderRating} + {tour.images[0]} + + + + {tour.images[1]} + {tour.images[2]} + + + ); + + const renderTexts = ( + theme.spacing(2.5, 2.5, 2, 2.5) }} + primary={`Posted date: ${fDateTime(tour.createdAt)}`} + secondary={ + + {tour.name} + + } + primaryTypographyProps={{ typography: 'caption', color: 'text.disabled' }} + secondaryTypographyProps={{ + mt: 1, + noWrap: true, + component: 'span', + color: 'text.primary', + typography: 'subtitle1', + }} + /> + ); + + const renderInfo = ( + theme.spacing(0, 2.5, 2.5, 2.5) }} + > + + + + + {[ + { + icon: , + label: tour.destination, + }, + { + icon: , + label: fDateRangeShortLabel(tour.available.startDate, tour.available.endDate), + }, + { + icon: , + label: `${tour.bookers.length} Booked`, + }, + ].map((item) => ( + + {item.icon} + {item.label} + + ))} + + ); + + return ( + <> + + {renderImages} + + {renderTexts} + + {renderInfo} + + + + + { + popover.onClose(); + onView(); + }} + > + + View + + + { + popover.onClose(); + onEdit(); + }} + > + + Edit + + + { + popover.onClose(); + onDelete(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + + + ); +} diff --git a/front_minimal/src/sections/tour/tour-list.jsx b/front_minimal/src/sections/tour/tour-list.jsx new file mode 100644 index 0000000..aa5609f --- /dev/null +++ b/front_minimal/src/sections/tour/tour-list.jsx @@ -0,0 +1,63 @@ +import { useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Pagination, { paginationClasses } from '@mui/material/Pagination'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { TourItem } from './tour-item'; + +// ---------------------------------------------------------------------- + +export function TourList({ tours }) { + const router = useRouter(); + + const handleView = useCallback( + (id) => { + router.push(paths.dashboard.tour.details(id)); + }, + [router] + ); + + const handleEdit = useCallback( + (id) => { + router.push(paths.dashboard.tour.edit(id)); + }, + [router] + ); + + const handleDelete = useCallback((id) => { + console.info('DELETE', id); + }, []); + + return ( + <> + + {tours.map((tour) => ( + handleView(tour.id)} + onEdit={() => handleEdit(tour.id)} + onDelete={() => handleDelete(tour.id)} + /> + ))} + + + {tours.length > 8 && ( + + )} + + ); +} diff --git a/front_minimal/src/sections/tour/tour-new-edit-form.jsx b/front_minimal/src/sections/tour/tour-new-edit-form.jsx new file mode 100644 index 0000000..374a50a --- /dev/null +++ b/front_minimal/src/sections/tour/tour-new-edit-form.jsx @@ -0,0 +1,310 @@ +import { z as zod } from 'zod'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; +import { useMemo, useEffect, useCallback } from 'react'; + +import Chip from '@mui/material/Chip'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Switch from '@mui/material/Switch'; +import Divider from '@mui/material/Divider'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { fIsAfter } from 'src/utils/format-time'; + +import { _tags, _tourGuides, TOUR_SERVICE_OPTIONS } from 'src/_mock'; + +import { toast } from 'src/components/snackbar'; +import { Form, Field, schemaHelper } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const NewTourSchema = zod + .object({ + name: zod.string().min(1, { message: 'Name is required!' }), + content: schemaHelper.editor({ + message: { required_error: 'Content is required!' }, + }), + images: schemaHelper.files({ + message: { required_error: 'Images is required!' }, + }), + tourGuides: zod + .array( + zod.object({ + id: zod.string(), + name: zod.string(), + avatarUrl: zod.string(), + phoneNumber: zod.string(), + }) + ) + .nonempty({ message: 'Must have at least 1 guide!' }), + available: zod.object({ + startDate: schemaHelper.date({ + message: { required_error: 'Start date is required!' }, + }), + endDate: schemaHelper.date({ + message: { required_error: 'End date is required!' }, + }), + }), + durations: zod.string().min(1, { message: 'Durations is required!' }), + destination: schemaHelper.objectOrNull({ + message: { required_error: 'Destination is required!' }, + }), + services: zod.string().array().min(2, { message: 'Must have at least 2 items!' }), + tags: zod.string().array().min(2, { message: 'Must have at least 2 items!' }), + }) + .refine((data) => !fIsAfter(data.available.startDate, data.available.endDate), { + message: 'End date cannot be earlier than start date!', + path: ['available.endDate'], + }); + +export function TourNewEditForm({ currentTour }) { + const router = useRouter(); + + const defaultValues = useMemo( + () => ({ + name: currentTour?.name || '', + content: currentTour?.content || '', + images: currentTour?.images || [], + tourGuides: currentTour?.tourGuides || [], + available: { + startDate: currentTour?.available.startDate || null, + endDate: currentTour?.available.endDate || null, + }, + durations: currentTour?.durations || '', + destination: currentTour?.destination || '', + services: currentTour?.services || [], + tags: currentTour?.tags || [], + }), + [currentTour] + ); + + const methods = useForm({ + mode: 'all', + resolver: zodResolver(NewTourSchema), + defaultValues, + }); + + const { + watch, + reset, + setValue, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const values = watch(); + + useEffect(() => { + if (currentTour) { + reset(defaultValues); + } + }, [currentTour, defaultValues, reset]); + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + reset(); + toast.success(currentTour ? 'Update success!' : 'Create success!'); + router.push(paths.dashboard.tour.root); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + const handleRemoveFile = useCallback( + (inputFile) => { + const filtered = values.images && values.images?.filter((file) => file !== inputFile); + setValue('images', filtered, { shouldValidate: true }); + }, + [setValue, values.images] + ); + + const handleRemoveAllFiles = useCallback(() => { + setValue('images', [], { shouldValidate: true }); + }, [setValue]); + + const renderDetails = ( + + + + + + + + Name + + + + + Content + + + + + Images + console.info('ON UPLOAD')} + /> + + + + ); + + const renderProperties = ( + + + + + + +
    + + Tour guide + + + option.name} + isOptionEqualToValue={(option, value) => option.id === value.id} + renderOption={(props, tourGuide) => ( +
  • + + + {tourGuide.name} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((tourGuide, index) => ( + } + /> + )) + } + /> +
    + + + Available + + + + + + + + Duration + + + + + Destination + + + + + Services + + + + + Tags + option)} + getOptionLabel={(option) => option} + renderOption={(props, option) => ( +
  • + {option} +
  • + )} + renderTags={(selected, getTagProps) => + selected.map((option, index) => ( + + )) + } + /> +
    +
    +
    + ); + + const renderActions = ( + + } + label="Publish" + sx={{ flexGrow: 1, pl: 3 }} + /> + + + {!currentTour ? 'Create tour' : 'Save changes'} + + + ); + + return ( +
    + + {renderDetails} + + {renderProperties} + + {renderActions} + +
    + ); +} diff --git a/front_minimal/src/sections/tour/tour-search.jsx b/front_minimal/src/sections/tour/tour-search.jsx new file mode 100644 index 0000000..ce1a174 --- /dev/null +++ b/front_minimal/src/sections/tour/tour-search.jsx @@ -0,0 +1,107 @@ +import parse from 'autosuggest-highlight/parse'; +import match from 'autosuggest-highlight/match'; + +import Box from '@mui/material/Box'; +import Avatar from '@mui/material/Avatar'; +import TextField from '@mui/material/TextField'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; +import Autocomplete, { autocompleteClasses } from '@mui/material/Autocomplete'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { Iconify } from 'src/components/iconify'; +import { SearchNotFound } from 'src/components/search-not-found'; + +// ---------------------------------------------------------------------- + +export function TourSearch({ search, onSearch }) { + const router = useRouter(); + + const { state } = search; + + const handleClick = (id) => { + router.push(paths.dashboard.tour.details(id)); + }; + + const handleKeyUp = (event) => { + if (state.query) { + if (event.key === 'Enter') { + const selectProduct = state.results.filter((tour) => tour.name === state.query)[0]; + + handleClick(selectProduct.id); + } + } + }; + + return ( + onSearch(newValue)} + getOptionLabel={(option) => option.name} + noOptionsText={} + isOptionEqualToValue={(option, value) => option.id === value.id} + slotProps={{ + popper: { placement: 'bottom-start', sx: { minWidth: 320 } }, + paper: { sx: { [` .${autocompleteClasses.option}`]: { pl: 0.75 } } }, + }} + renderInput={(params) => ( + + + + ), + }} + /> + )} + renderOption={(props, tour, { inputValue }) => { + const matches = match(tour.name, inputValue); + const parts = parse(tour.name, matches); + + return ( + handleClick(tour.id)} key={tour.id}> + + +
    + {parts.map((part, index) => ( + + {part.text} + + ))} +
    +
    + ); + }} + /> + ); +} diff --git a/front_minimal/src/sections/tour/tour-sort.jsx b/front_minimal/src/sections/tour/tour-sort.jsx new file mode 100644 index 0000000..cee32dc --- /dev/null +++ b/front_minimal/src/sections/tour/tour-sort.jsx @@ -0,0 +1,54 @@ +import Box from '@mui/material/Box'; +import Button from '@mui/material/Button'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function TourSort({ sort, onSort, sortOptions }) { + const popover = usePopover(); + + return ( + <> + + + + + {sortOptions.map((option) => ( + { + popover.onClose(); + onSort(option.value); + }} + > + {option.label} + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/tour/view/index.js b/front_minimal/src/sections/tour/view/index.js new file mode 100644 index 0000000..7416479 --- /dev/null +++ b/front_minimal/src/sections/tour/view/index.js @@ -0,0 +1,7 @@ +export * from './tour-list-view'; + +export * from './tour-edit-view'; + +export * from './tour-create-view'; + +export * from './tour-details-view'; diff --git a/front_minimal/src/sections/tour/view/tour-create-view.jsx b/front_minimal/src/sections/tour/view/tour-create-view.jsx new file mode 100644 index 0000000..714e294 --- /dev/null +++ b/front_minimal/src/sections/tour/view/tour-create-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { TourNewEditForm } from '../tour-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function TourCreateView() { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/tour/view/tour-details-view.jsx b/front_minimal/src/sections/tour/view/tour-details-view.jsx new file mode 100644 index 0000000..9fb6e04 --- /dev/null +++ b/front_minimal/src/sections/tour/view/tour-details-view.jsx @@ -0,0 +1,65 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Tab from '@mui/material/Tab'; +import Tabs from '@mui/material/Tabs'; + +import { paths } from 'src/routes/paths'; + +import { useTabs } from 'src/hooks/use-tabs'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { TOUR_DETAILS_TABS, TOUR_PUBLISH_OPTIONS } from 'src/_mock'; + +import { Label } from 'src/components/label'; + +import { TourDetailsContent } from '../tour-details-content'; +import { TourDetailsBookers } from '../tour-details-bookers'; +import { TourDetailsToolbar } from '../tour-details-toolbar'; + +// ---------------------------------------------------------------------- + +export function TourDetailsView({ tour }) { + const [publish, setPublish] = useState(tour?.publish); + + const tabs = useTabs('content'); + + const handleChangePublish = useCallback((newValue) => { + setPublish(newValue); + }, []); + + const renderTabs = ( + + {TOUR_DETAILS_TABS.map((tab) => ( + {tour?.bookers.length} : '' + } + /> + ))} + + ); + + return ( + + + {renderTabs} + + {tabs.value === 'content' && } + + {tabs.value === 'bookers' && } + + ); +} diff --git a/front_minimal/src/sections/tour/view/tour-edit-view.jsx b/front_minimal/src/sections/tour/view/tour-edit-view.jsx new file mode 100644 index 0000000..d164f5c --- /dev/null +++ b/front_minimal/src/sections/tour/view/tour-edit-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { TourNewEditForm } from '../tour-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function TourEditView({ tour }) { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/tour/view/tour-list-view.jsx b/front_minimal/src/sections/tour/view/tour-list-view.jsx new file mode 100644 index 0000000..572bbd5 --- /dev/null +++ b/front_minimal/src/sections/tour/view/tour-list-view.jsx @@ -0,0 +1,190 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useSetState } from 'src/hooks/use-set-state'; + +import { orderBy } from 'src/utils/helper'; +import { fIsAfter, fIsBetween } from 'src/utils/format-time'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { _tours, _tourGuides, TOUR_SORT_OPTIONS, TOUR_SERVICE_OPTIONS } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; +import { EmptyContent } from 'src/components/empty-content'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { TourList } from '../tour-list'; +import { TourSort } from '../tour-sort'; +import { TourSearch } from '../tour-search'; +import { TourFilters } from '../tour-filters'; +import { TourFiltersResult } from '../tour-filters-result'; + +// ---------------------------------------------------------------------- + +export function TourListView() { + const openFilters = useBoolean(); + + const [sortBy, setSortBy] = useState('latest'); + + const search = useSetState({ query: '', results: [] }); + + const filters = useSetState({ + destination: [], + tourGuides: [], + services: [], + startDate: null, + endDate: null, + }); + + const dateError = fIsAfter(filters.state.startDate, filters.state.endDate); + + const dataFiltered = applyFilter({ + inputData: _tours, + filters: filters.state, + sortBy, + dateError, + }); + + const canReset = + filters.state.destination.length > 0 || + filters.state.tourGuides.length > 0 || + filters.state.services.length > 0 || + (!!filters.state.startDate && !!filters.state.endDate); + + const notFound = !dataFiltered.length && canReset; + + const handleSortBy = useCallback((newValue) => { + setSortBy(newValue); + }, []); + + const handleSearch = useCallback( + (inputValue) => { + search.setState({ query: inputValue }); + + if (inputValue) { + const results = _tours.filter( + (tour) => tour.name.toLowerCase().indexOf(search.state.query.toLowerCase()) !== -1 + ); + + search.setState({ results }); + } + }, + [search] + ); + + const renderFilters = ( + + + + + option.label), + }} + /> + + + + + ); + + const renderResults = ; + + return ( + + } + > + New Tour + + } + sx={{ mb: { xs: 3, md: 5 } }} + /> + + + {renderFilters} + + {canReset && renderResults} + + + {notFound && } + + + + ); +} + +const applyFilter = ({ inputData, filters, sortBy, dateError }) => { + const { services, destination, startDate, endDate, tourGuides } = filters; + + const tourGuideIds = tourGuides.map((tourGuide) => tourGuide.id); + + // Sort by + if (sortBy === 'latest') { + inputData = orderBy(inputData, ['createdAt'], ['desc']); + } + + if (sortBy === 'oldest') { + inputData = orderBy(inputData, ['createdAt'], ['asc']); + } + + if (sortBy === 'popular') { + inputData = orderBy(inputData, ['totalViews'], ['desc']); + } + + // Filters + if (destination.length) { + inputData = inputData.filter((tour) => destination.includes(tour.destination)); + } + + if (tourGuideIds.length) { + inputData = inputData.filter((tour) => + tour.tourGuides.some((filterItem) => tourGuideIds.includes(filterItem.id)) + ); + } + + if (services.length) { + inputData = inputData.filter((tour) => tour.services.some((item) => services.includes(item))); + } + + if (!dateError) { + if (startDate && endDate) { + inputData = inputData.filter((tour) => + fIsBetween(startDate, tour.available.startDate, tour.available.endDate) + ); + } + } + + return inputData; +}; diff --git a/front_minimal/src/sections/user/profile-cover.jsx b/front_minimal/src/sections/user/profile-cover.jsx new file mode 100644 index 0000000..face776 --- /dev/null +++ b/front_minimal/src/sections/user/profile-cover.jsx @@ -0,0 +1,64 @@ +import Box from '@mui/material/Box'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import { useTheme } from '@mui/material/styles'; +import ListItemText from '@mui/material/ListItemText'; + +import { varAlpha, bgGradient } from 'src/theme/styles'; + +// ---------------------------------------------------------------------- + +export function ProfileCover({ name, avatarUrl, role, coverUrl }) { + const theme = useTheme(); + + return ( + + + + {name?.charAt(0).toUpperCase()} + + + + + + ); +} diff --git a/front_minimal/src/sections/user/profile-followers.jsx b/front_minimal/src/sections/user/profile-followers.jsx new file mode 100644 index 0000000..0dc1a59 --- /dev/null +++ b/front_minimal/src/sections/user/profile-followers.jsx @@ -0,0 +1,97 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { Iconify } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function ProfileFollowers({ followers }) { + const _mockFollowed = followers.slice(4, 8).map((i) => i.id); + + const [followed, setFollowed] = useState(_mockFollowed); + + const handleClick = useCallback( + (item) => { + const selected = followed.includes(item) + ? followed.filter((value) => value !== item) + : [...followed, item]; + + setFollowed(selected); + }, + [followed] + ); + + return ( + <> + + Followers + + + + {followers.map((follower) => ( + handleClick(follower.id)} + /> + ))} + + + ); +} + +function FollowerItem({ follower, selected, onSelected }) { + const { name, country, avatarUrl } = follower; + + return ( + theme.spacing(3, 2, 3, 3) }}> + + + + + {country} + + } + primaryTypographyProps={{ noWrap: true, typography: 'subtitle2' }} + secondaryTypographyProps={{ + mt: 0.5, + noWrap: true, + display: 'flex', + component: 'span', + alignItems: 'center', + typography: 'caption', + color: 'text.disabled', + }} + /> + + + + ); +} diff --git a/front_minimal/src/sections/user/profile-friends.jsx b/front_minimal/src/sections/user/profile-friends.jsx new file mode 100644 index 0000000..e856da9 --- /dev/null +++ b/front_minimal/src/sections/user/profile-friends.jsx @@ -0,0 +1,157 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import TextField from '@mui/material/TextField'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { _socials } from 'src/_mock'; + +import { Iconify, SocialIcon } from 'src/components/iconify'; +import { SearchNotFound } from 'src/components/search-not-found'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function ProfileFriends({ friends, searchFriends, onSearchFriends }) { + const dataFiltered = applyFilter({ inputData: friends, query: searchFriends }); + + const notFound = !dataFiltered.length && !!searchFriends; + + return ( + <> + + Friends + + + + + ), + }} + sx={{ width: { xs: 1, sm: 260 } }} + /> + + + {notFound ? ( + + ) : ( + + {dataFiltered.map((item) => ( + + ))} + + )} + + ); +} + +// ---------------------------------------------------------------------- + +function FriendCard({ item }) { + const popover = usePopover(); + + const handleDelete = () => { + popover.onClose(); + console.info('DELETE', item.name); + }; + + const handleEdit = () => { + popover.onClose(); + console.info('EDIT', item.name); + }; + + return ( + <> + + + + + {item.name} + + + + {item.role} + + + + {_socials.map((social) => ( + + + + ))} + + + + + + + + + + + + Delete + + + + + Edit + + + + + ); +} + +// ---------------------------------------------------------------------- + +function applyFilter({ inputData, query }) { + if (query) { + return inputData.filter( + (friend) => friend.name.toLowerCase().indexOf(query.toLowerCase()) !== -1 + ); + } + + return inputData; +} diff --git a/front_minimal/src/sections/user/profile-gallery.jsx b/front_minimal/src/sections/user/profile-gallery.jsx new file mode 100644 index 0000000..ee87cfe --- /dev/null +++ b/front_minimal/src/sections/user/profile-gallery.jsx @@ -0,0 +1,94 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import { useTheme } from '@mui/material/styles'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { fDate } from 'src/utils/format-time'; + +import { varAlpha } from 'src/theme/styles'; + +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; +import { Lightbox, useLightBox } from 'src/components/lightbox'; + +// ---------------------------------------------------------------------- + +export function ProfileGallery({ gallery }) { + const theme = useTheme(); + + const slides = gallery.map((slide) => ({ src: slide.imageUrl })); + + const lightbox = useLightBox(slides); + + return ( + <> + + Gallery + + + + {gallery.map((image) => ( + + + + + + + + gallery lightbox.onOpen(image.imageUrl)} + slotProps={{ + overlay: { + background: `linear-gradient(to bottom, ${varAlpha(theme.vars.palette.grey['900Channel'], 0)} 0%, ${theme.vars.palette.grey[900]} 75%)`, + }, + }} + /> + + ))} + + + + + ); +} diff --git a/front_minimal/src/sections/user/profile-home.jsx b/front_minimal/src/sections/user/profile-home.jsx new file mode 100644 index 0000000..9c65f4b --- /dev/null +++ b/front_minimal/src/sections/user/profile-home.jsx @@ -0,0 +1,190 @@ +'use client'; + +import { useRef } from 'react'; + +import Fab from '@mui/material/Fab'; +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Divider from '@mui/material/Divider'; +import InputBase from '@mui/material/InputBase'; +import Grid from '@mui/material/Unstable_Grid2'; +import CardHeader from '@mui/material/CardHeader'; + +import { fNumber } from 'src/utils/format-number'; + +import { _socials } from 'src/_mock'; +import { varAlpha } from 'src/theme/styles'; + +import { Iconify, SocialIcon } from 'src/components/iconify'; + +import { ProfilePostItem } from './profile-post-item'; + +// ---------------------------------------------------------------------- + +export function ProfileHome({ info, posts }) { + const fileRef = useRef(null); + + const handleAttach = () => { + if (fileRef.current) { + fileRef.current.click(); + } + }; + + const renderFollows = ( + + } + > + + {fNumber(info.totalFollowers)} + + Follower + + + + + {fNumber(info.totalFollowing)} + + Following + + + + + ); + + const renderAbout = ( + + + + + {info.quote} + + + + + + {`Live at `} + + {info.country} + + + + + + + {info.email} + + + + + + + {info.role} {`at `} + + {info.company} + + + + + + + + + {`Studied at `} + + {info.school} + + + + + + ); + + const renderPostInput = ( + + `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.2)}`, + }} + /> + + + + + + Image/Video + + + + + Streaming + + + + + + + + + ); + + const renderSocials = ( + + + + + {_socials.map((link) => ( + + + + {link.value === 'facebook' && info.socialLinks.facebook} + {link.value === 'instagram' && info.socialLinks.instagram} + {link.value === 'linkedin' && info.socialLinks.linkedin} + {link.value === 'twitter' && info.socialLinks.twitter} + + + ))} + + + ); + + return ( + + + + {renderFollows} + + {renderAbout} + + {renderSocials} + + + + + + {renderPostInput} + + {posts.map((post) => ( + + ))} + + + + ); +} diff --git a/front_minimal/src/sections/user/profile-post-item.jsx b/front_minimal/src/sections/user/profile-post-item.jsx new file mode 100644 index 0000000..27fee9d --- /dev/null +++ b/front_minimal/src/sections/user/profile-post-item.jsx @@ -0,0 +1,203 @@ +import { useRef, useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Card from '@mui/material/Card'; +import Paper from '@mui/material/Paper'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Checkbox from '@mui/material/Checkbox'; +import InputBase from '@mui/material/InputBase'; +import IconButton from '@mui/material/IconButton'; +import CardHeader from '@mui/material/CardHeader'; +import Typography from '@mui/material/Typography'; +import InputAdornment from '@mui/material/InputAdornment'; +import FormControlLabel from '@mui/material/FormControlLabel'; +import AvatarGroup, { avatarGroupClasses } from '@mui/material/AvatarGroup'; + +import { fDate } from 'src/utils/format-time'; +import { fShortenNumber } from 'src/utils/format-number'; + +import { varAlpha } from 'src/theme/styles'; + +import { Image } from 'src/components/image'; +import { Iconify } from 'src/components/iconify'; + +import { useMockedUser } from 'src/auth/hooks'; + +// ---------------------------------------------------------------------- + +export function ProfilePostItem({ post }) { + const { user } = useMockedUser(); + + const commentRef = useRef(null); + + const fileRef = useRef(null); + + const [message, setMessage] = useState(''); + + const handleChangeMessage = useCallback((event) => { + setMessage(event.target.value); + }, []); + + const handleAttach = useCallback(() => { + if (fileRef.current) { + fileRef.current.click(); + } + }, []); + + const handleClickComment = useCallback(() => { + if (commentRef.current) { + commentRef.current.focus(); + } + }, []); + + const renderHead = ( + + {user?.displayName?.charAt(0).toUpperCase()} + + } + title={ + + {user?.displayName} + + } + subheader={ + + {fDate(post.createdAt)} + + } + action={ + + + + } + /> + ); + + const renderCommentList = ( + + {post.comments.map((comment) => ( + + + + + + {comment.author.name} + + + {fDate(comment.createdAt)} + + + + {comment.message} + + + ))} + + ); + + const renderInput = ( + theme.spacing(0, 3, 3, 3) }} + > + + {user?.displayName?.charAt(0).toUpperCase()} + + + + + + + + + + + + } + inputProps={{ id: `comment-input-${post.id}`, 'aria-label': 'Write a comment' }} + sx={{ + pl: 1.5, + height: 40, + borderRadius: 1, + border: (theme) => `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.32)}`, + }} + /> + + + + ); + + const renderActions = ( + theme.spacing(2, 3, 3, 3) }}> + } + checkedIcon={} + /> + } + label={fShortenNumber(post.personLikes.length)} + sx={{ mr: 1 }} + /> + + {!!post.personLikes.length && ( + + {post.personLikes.map((person) => ( + + ))} + + )} + + + + + + + + + + + + ); + + return ( + + {renderHead} + + theme.spacing(3, 3, 2, 3) }}> + {post.message} + + + + {post.media} + + + {renderActions} + + {!!post.comments.length && renderCommentList} + + {renderInput} + + ); +} diff --git a/front_minimal/src/sections/user/user-card-list.jsx b/front_minimal/src/sections/user/user-card-list.jsx new file mode 100644 index 0000000..9e3059a --- /dev/null +++ b/front_minimal/src/sections/user/user-card-list.jsx @@ -0,0 +1,42 @@ +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Pagination from '@mui/material/Pagination'; + +import { UserCard } from './user-card'; + +// ---------------------------------------------------------------------- + +export function UserCardList({ users }) { + const [page, setPage] = useState(1); + + const rowsPerPage = 12; + + const handleChangePage = useCallback((event, newPage) => { + setPage(newPage); + }, []); + + return ( + <> + + {users + .slice((page - 1) * rowsPerPage, (page - 1) * rowsPerPage + rowsPerPage) + .map((user) => ( + + ))} + + + + + ); +} diff --git a/front_minimal/src/sections/user/user-card.jsx b/front_minimal/src/sections/user/user-card.jsx new file mode 100644 index 0000000..002682b --- /dev/null +++ b/front_minimal/src/sections/user/user-card.jsx @@ -0,0 +1,110 @@ +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Avatar from '@mui/material/Avatar'; +import Divider from '@mui/material/Divider'; +import IconButton from '@mui/material/IconButton'; +import Typography from '@mui/material/Typography'; +import ListItemText from '@mui/material/ListItemText'; + +import { fShortenNumber } from 'src/utils/format-number'; + +import { _socials } from 'src/_mock'; +import { varAlpha } from 'src/theme/styles'; +import { AvatarShape } from 'src/assets/illustrations'; + +import { Image } from 'src/components/image'; +import { SocialIcon } from 'src/components/iconify'; + +// ---------------------------------------------------------------------- + +export function UserCard({ user }) { + return ( + + + + + + + {user.coverUrl} varAlpha(theme.vars.palette.grey['900Channel'], 0.48), + }, + }} + /> + + + + + + {_socials.map((social) => ( + + + + ))} + + + + + +
    + + Follower + + {fShortenNumber(user.totalFollowers)} +
    + +
    + + Following + + + {fShortenNumber(user.totalFollowing)} +
    + +
    + + Total post + + {fShortenNumber(user.totalPosts)} +
    +
    +
    + ); +} diff --git a/front_minimal/src/sections/user/user-new-edit-form.jsx b/front_minimal/src/sections/user/user-new-edit-form.jsx new file mode 100644 index 0000000..d703809 --- /dev/null +++ b/front_minimal/src/sections/user/user-new-edit-form.jsx @@ -0,0 +1,247 @@ +import { z as zod } from 'zod'; +import { useMemo } from 'react'; +import { zodResolver } from '@hookform/resolvers/zod'; +import { useForm, Controller } from 'react-hook-form'; +import { isValidPhoneNumber } from 'react-phone-number-input/input'; + +import Box from '@mui/material/Box'; +import Card from '@mui/material/Card'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Switch from '@mui/material/Switch'; +import Grid from '@mui/material/Unstable_Grid2'; +import Typography from '@mui/material/Typography'; +import LoadingButton from '@mui/lab/LoadingButton'; +import FormControlLabel from '@mui/material/FormControlLabel'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; + +import { fData } from 'src/utils/format-number'; + +import { Label } from 'src/components/label'; +import { toast } from 'src/components/snackbar'; +import { Form, Field, schemaHelper } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const NewUserSchema = zod.object({ + avatarUrl: schemaHelper.file({ + message: { required_error: 'Avatar is required!' }, + }), + name: zod.string().min(1, { message: 'Name is required!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + phoneNumber: schemaHelper.phoneNumber({ isValidPhoneNumber }), + country: schemaHelper.objectOrNull({ + message: { required_error: 'Country is required!' }, + }), + address: zod.string().min(1, { message: 'Address is required!' }), + company: zod.string().min(1, { message: 'Company is required!' }), + state: zod.string().min(1, { message: 'State is required!' }), + city: zod.string().min(1, { message: 'City is required!' }), + role: zod.string().min(1, { message: 'Role is required!' }), + zipCode: zod.string().min(1, { message: 'Zip code is required!' }), + // Not required + status: zod.string(), + isVerified: zod.boolean(), +}); + +// ---------------------------------------------------------------------- + +export function UserNewEditForm({ currentUser }) { + const router = useRouter(); + + const defaultValues = useMemo( + () => ({ + status: currentUser?.status || '', + avatarUrl: currentUser?.avatarUrl || null, + isVerified: currentUser?.isVerified || true, + name: currentUser?.name || '', + email: currentUser?.email || '', + phoneNumber: currentUser?.phoneNumber || '', + country: currentUser?.country || '', + state: currentUser?.state || '', + city: currentUser?.city || '', + address: currentUser?.address || '', + zipCode: currentUser?.zipCode || '', + company: currentUser?.company || '', + role: currentUser?.role || '', + }), + [currentUser] + ); + + const methods = useForm({ + mode: 'onSubmit', + resolver: zodResolver(NewUserSchema), + defaultValues, + }); + + const { + reset, + watch, + control, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const values = watch(); + + const onSubmit = handleSubmit(async (data) => { + try { + await new Promise((resolve) => setTimeout(resolve, 500)); + reset(); + toast.success(currentUser ? 'Update success!' : 'Create success!'); + router.push(paths.dashboard.user.list); + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + return ( +
    + + + + {currentUser && ( + + )} + + + + Allowed *.jpeg, *.jpg, *.png, *.gif +
    max size of {fData(3145728)} + + } + /> +
    + + {currentUser && ( + ( + + field.onChange(event.target.checked ? 'banned' : 'active') + } + /> + )} + /> + } + label={ + <> + + Banned + + + Apply disable account + + + } + sx={{ + mx: 0, + mb: 3, + width: 1, + justifyContent: 'space-between', + }} + /> + )} + + + + Email verified + + + Disabling this will automatically send the user a verification email + + + } + sx={{ mx: 0, width: 1, justifyContent: 'space-between' }} + /> + + {currentUser && ( + + + + )} +
    +
    + + + + + + + + + + + + + + + + + + + + + {!currentUser ? 'Create user' : 'Save changes'} + + + + +
    +
    + ); +} diff --git a/front_minimal/src/sections/user/user-quick-edit-form.jsx b/front_minimal/src/sections/user/user-quick-edit-form.jsx new file mode 100644 index 0000000..1c9c760 --- /dev/null +++ b/front_minimal/src/sections/user/user-quick-edit-form.jsx @@ -0,0 +1,161 @@ +import { z as zod } from 'zod'; +import { useMemo } from 'react'; +import { useForm } from 'react-hook-form'; +import { zodResolver } from '@hookform/resolvers/zod'; +import { isValidPhoneNumber } from 'react-phone-number-input/input'; + +import Box from '@mui/material/Box'; +import Alert from '@mui/material/Alert'; +import Button from '@mui/material/Button'; +import Dialog from '@mui/material/Dialog'; +import MenuItem from '@mui/material/MenuItem'; +import LoadingButton from '@mui/lab/LoadingButton'; +import DialogTitle from '@mui/material/DialogTitle'; +import DialogActions from '@mui/material/DialogActions'; +import DialogContent from '@mui/material/DialogContent'; + +import { USER_STATUS_OPTIONS } from 'src/_mock'; + +import { toast } from 'src/components/snackbar'; +import { Form, Field, schemaHelper } from 'src/components/hook-form'; + +// ---------------------------------------------------------------------- + +export const UserQuickEditSchema = zod.object({ + name: zod.string().min(1, { message: 'Name is required!' }), + email: zod + .string() + .min(1, { message: 'Email is required!' }) + .email({ message: 'Email must be a valid email address!' }), + phoneNumber: schemaHelper.phoneNumber({ isValidPhoneNumber }), + country: schemaHelper.objectOrNull({ + message: { required_error: 'Country is required!' }, + }), + state: zod.string().min(1, { message: 'State is required!' }), + city: zod.string().min(1, { message: 'City is required!' }), + address: zod.string().min(1, { message: 'Address is required!' }), + zipCode: zod.string().min(1, { message: 'Zip code is required!' }), + company: zod.string().min(1, { message: 'Company is required!' }), + role: zod.string().min(1, { message: 'Role is required!' }), + // Not required + status: zod.string(), +}); + +// ---------------------------------------------------------------------- + +export function UserQuickEditForm({ currentUser, open, onClose }) { + const defaultValues = useMemo( + () => ({ + name: currentUser?.name || '', + email: currentUser?.email || '', + phoneNumber: currentUser?.phoneNumber || '', + address: currentUser?.address || '', + country: currentUser?.country || '', + state: currentUser?.state || '', + city: currentUser?.city || '', + zipCode: currentUser?.zipCode || '', + status: currentUser?.status, + company: currentUser?.company || '', + role: currentUser?.role || '', + }), + [currentUser] + ); + + const methods = useForm({ + mode: 'all', + resolver: zodResolver(UserQuickEditSchema), + defaultValues, + }); + + const { + reset, + handleSubmit, + formState: { isSubmitting }, + } = methods; + + const onSubmit = handleSubmit(async (data) => { + const promise = new Promise((resolve) => setTimeout(resolve, 1000)); + + try { + reset(); + onClose(); + + toast.promise(promise, { + loading: 'Loading...', + success: 'Update success!', + error: 'Update error!', + }); + + await promise; + + console.info('DATA', data); + } catch (error) { + console.error(error); + } + }); + + return ( + +
    + Quick Update + + + + Account is waiting for confirmation + + + + + {USER_STATUS_OPTIONS.map((status) => ( + + {status.label} + + ))} + + + + + + + + + + + + + + + + + + + + + + + + Update + + +
    +
    + ); +} diff --git a/front_minimal/src/sections/user/user-table-filters-result.jsx b/front_minimal/src/sections/user/user-table-filters-result.jsx new file mode 100644 index 0000000..fc42063 --- /dev/null +++ b/front_minimal/src/sections/user/user-table-filters-result.jsx @@ -0,0 +1,57 @@ +import { useCallback } from 'react'; + +import Chip from '@mui/material/Chip'; + +import { chipProps, FiltersBlock, FiltersResult } from 'src/components/filters-result'; + +// ---------------------------------------------------------------------- + +export function UserTableFiltersResult({ filters, onResetPage, totalResults, sx }) { + const handleRemoveKeyword = useCallback(() => { + onResetPage(); + filters.setState({ name: '' }); + }, [filters, onResetPage]); + + const handleRemoveStatus = useCallback(() => { + onResetPage(); + filters.setState({ status: 'all' }); + }, [filters, onResetPage]); + + const handleRemoveRole = useCallback( + (inputValue) => { + const newValue = filters.state.role.filter((item) => item !== inputValue); + + onResetPage(); + filters.setState({ role: newValue }); + }, + [filters, onResetPage] + ); + + const handleReset = useCallback(() => { + onResetPage(); + filters.onResetState(); + }, [filters, onResetPage]); + + return ( + + + + + + + {filters.state.role.map((item) => ( + handleRemoveRole(item)} /> + ))} + + + + + + + ); +} diff --git a/front_minimal/src/sections/user/user-table-row.jsx b/front_minimal/src/sections/user/user-table-row.jsx new file mode 100644 index 0000000..f7d7b0a --- /dev/null +++ b/front_minimal/src/sections/user/user-table-row.jsx @@ -0,0 +1,137 @@ +import Box from '@mui/material/Box'; +import Link from '@mui/material/Link'; +import Stack from '@mui/material/Stack'; +import Button from '@mui/material/Button'; +import Avatar from '@mui/material/Avatar'; +import Tooltip from '@mui/material/Tooltip'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import TableRow from '@mui/material/TableRow'; +import Checkbox from '@mui/material/Checkbox'; +import TableCell from '@mui/material/TableCell'; +import IconButton from '@mui/material/IconButton'; + +import { useBoolean } from 'src/hooks/use-boolean'; + +import { Label } from 'src/components/label'; +import { Iconify } from 'src/components/iconify'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +import { UserQuickEditForm } from './user-quick-edit-form'; + +// ---------------------------------------------------------------------- + +export function UserTableRow({ row, selected, onEditRow, onSelectRow, onDeleteRow }) { + const confirm = useBoolean(); + + const popover = usePopover(); + + const quickEdit = useBoolean(); + + return ( + <> + + + + + + + + + + + + {row.name} + + + {row.email} + + + + + + {row.phoneNumber} + + {row.company} + + {row.role} + + + + + + + + + + + + + + + + + + + + + + + + + { + confirm.onTrue(); + popover.onClose(); + }} + sx={{ color: 'error.main' }} + > + + Delete + + + { + onEditRow(); + popover.onClose(); + }} + > + + Edit + + + + + + Delete + + } + /> + + ); +} diff --git a/front_minimal/src/sections/user/user-table-toolbar.jsx b/front_minimal/src/sections/user/user-table-toolbar.jsx new file mode 100644 index 0000000..0e057cd --- /dev/null +++ b/front_minimal/src/sections/user/user-table-toolbar.jsx @@ -0,0 +1,132 @@ +import { useCallback } from 'react'; + +import Stack from '@mui/material/Stack'; +import Select from '@mui/material/Select'; +import MenuList from '@mui/material/MenuList'; +import MenuItem from '@mui/material/MenuItem'; +import Checkbox from '@mui/material/Checkbox'; +import TextField from '@mui/material/TextField'; +import InputLabel from '@mui/material/InputLabel'; +import IconButton from '@mui/material/IconButton'; +import FormControl from '@mui/material/FormControl'; +import OutlinedInput from '@mui/material/OutlinedInput'; +import InputAdornment from '@mui/material/InputAdornment'; + +import { Iconify } from 'src/components/iconify'; +import { usePopover, CustomPopover } from 'src/components/custom-popover'; + +// ---------------------------------------------------------------------- + +export function UserTableToolbar({ filters, options, onResetPage }) { + const popover = usePopover(); + + const handleFilterName = useCallback( + (event) => { + onResetPage(); + filters.setState({ name: event.target.value }); + }, + [filters, onResetPage] + ); + + const handleFilterRole = useCallback( + (event) => { + const newValue = + typeof event.target.value === 'string' ? event.target.value.split(',') : event.target.value; + + onResetPage(); + filters.setState({ role: newValue }); + }, + [filters, onResetPage] + ); + + return ( + <> + + + Role + + + + + + + + ), + }} + /> + + + + + + + + + + { + popover.onClose(); + }} + > + + Print + + + { + popover.onClose(); + }} + > + + Import + + + { + popover.onClose(); + }} + > + + Export + + + + + ); +} diff --git a/front_minimal/src/sections/user/view/index.js b/front_minimal/src/sections/user/view/index.js new file mode 100644 index 0000000..31f93bd --- /dev/null +++ b/front_minimal/src/sections/user/view/index.js @@ -0,0 +1,9 @@ +export * from './user-edit-view'; + +export * from './user-list-view'; + +export * from './user-cards-view'; + +export * from './user-create-view'; + +export * from './user-profile-view'; diff --git a/front_minimal/src/sections/user/view/user-cards-view.jsx b/front_minimal/src/sections/user/view/user-cards-view.jsx new file mode 100644 index 0000000..b53b64a --- /dev/null +++ b/front_minimal/src/sections/user/view/user-cards-view.jsx @@ -0,0 +1,44 @@ +'use client'; + +import Button from '@mui/material/Button'; + +import { paths } from 'src/routes/paths'; +import { RouterLink } from 'src/routes/components'; + +import { _userCards } from 'src/_mock'; +import { DashboardContent } from 'src/layouts/dashboard'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { UserCardList } from '../user-card-list'; + +// ---------------------------------------------------------------------- + +export function UserCardsView() { + return ( + + } + > + New user + + } + sx={{ mb: { xs: 3, md: 5 } }} + /> + + + + ); +} diff --git a/front_minimal/src/sections/user/view/user-create-view.jsx b/front_minimal/src/sections/user/view/user-create-view.jsx new file mode 100644 index 0000000..5ad5df5 --- /dev/null +++ b/front_minimal/src/sections/user/view/user-create-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { UserNewEditForm } from '../user-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function UserCreateView() { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/user/view/user-edit-view.jsx b/front_minimal/src/sections/user/view/user-edit-view.jsx new file mode 100644 index 0000000..adb7e54 --- /dev/null +++ b/front_minimal/src/sections/user/view/user-edit-view.jsx @@ -0,0 +1,29 @@ +'use client'; + +import { paths } from 'src/routes/paths'; + +import { DashboardContent } from 'src/layouts/dashboard'; + +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { UserNewEditForm } from '../user-new-edit-form'; + +// ---------------------------------------------------------------------- + +export function UserEditView({ user: currentUser }) { + return ( + + + + + + ); +} diff --git a/front_minimal/src/sections/user/view/user-list-view.jsx b/front_minimal/src/sections/user/view/user-list-view.jsx new file mode 100644 index 0000000..d4baa8d --- /dev/null +++ b/front_minimal/src/sections/user/view/user-list-view.jsx @@ -0,0 +1,335 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Tab from '@mui/material/Tab'; +import Tabs from '@mui/material/Tabs'; +import Card from '@mui/material/Card'; +import Table from '@mui/material/Table'; +import Button from '@mui/material/Button'; +import Tooltip from '@mui/material/Tooltip'; +import TableBody from '@mui/material/TableBody'; +import IconButton from '@mui/material/IconButton'; + +import { paths } from 'src/routes/paths'; +import { useRouter } from 'src/routes/hooks'; +import { RouterLink } from 'src/routes/components'; + +import { useBoolean } from 'src/hooks/use-boolean'; +import { useSetState } from 'src/hooks/use-set-state'; + +import { varAlpha } from 'src/theme/styles'; +import { DashboardContent } from 'src/layouts/dashboard'; +import { _roles, _userList, USER_STATUS_OPTIONS } from 'src/_mock'; + +import { Label } from 'src/components/label'; +import { toast } from 'src/components/snackbar'; +import { Iconify } from 'src/components/iconify'; +import { Scrollbar } from 'src/components/scrollbar'; +import { ConfirmDialog } from 'src/components/custom-dialog'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; +import { + useTable, + emptyRows, + rowInPage, + TableNoData, + getComparator, + TableEmptyRows, + TableHeadCustom, + TableSelectedAction, + TablePaginationCustom, +} from 'src/components/table'; + +import { UserTableRow } from '../user-table-row'; +import { UserTableToolbar } from '../user-table-toolbar'; +import { UserTableFiltersResult } from '../user-table-filters-result'; + +// ---------------------------------------------------------------------- + +const STATUS_OPTIONS = [{ value: 'all', label: 'All' }, ...USER_STATUS_OPTIONS]; + +const TABLE_HEAD = [ + { id: 'name', label: 'Name' }, + { id: 'phoneNumber', label: 'Phone number', width: 180 }, + { id: 'company', label: 'Company', width: 220 }, + { id: 'role', label: 'Role', width: 180 }, + { id: 'status', label: 'Status', width: 100 }, + { id: '', width: 88 }, +]; + +// ---------------------------------------------------------------------- + +export function UserListView() { + const table = useTable(); + + const router = useRouter(); + + const confirm = useBoolean(); + + const [tableData, setTableData] = useState(_userList); + + const filters = useSetState({ name: '', role: [], status: 'all' }); + + const dataFiltered = applyFilter({ + inputData: tableData, + comparator: getComparator(table.order, table.orderBy), + filters: filters.state, + }); + + const dataInPage = rowInPage(dataFiltered, table.page, table.rowsPerPage); + + const canReset = + !!filters.state.name || filters.state.role.length > 0 || filters.state.status !== 'all'; + + const notFound = (!dataFiltered.length && canReset) || !dataFiltered.length; + + const handleDeleteRow = useCallback( + (id) => { + const deleteRow = tableData.filter((row) => row.id !== id); + + toast.success('Delete success!'); + + setTableData(deleteRow); + + table.onUpdatePageDeleteRow(dataInPage.length); + }, + [dataInPage.length, table, tableData] + ); + + const handleDeleteRows = useCallback(() => { + const deleteRows = tableData.filter((row) => !table.selected.includes(row.id)); + + toast.success('Delete success!'); + + setTableData(deleteRows); + + table.onUpdatePageDeleteRows({ + totalRowsInPage: dataInPage.length, + totalRowsFiltered: dataFiltered.length, + }); + }, [dataFiltered.length, dataInPage.length, table, tableData]); + + const handleEditRow = useCallback( + (id) => { + router.push(paths.dashboard.user.edit(id)); + }, + [router] + ); + + const handleFilterStatus = useCallback( + (event, newValue) => { + table.onResetPage(); + filters.setState({ status: newValue }); + }, + [filters, table] + ); + + return ( + <> + + } + > + New user + + } + sx={{ mb: { xs: 3, md: 5 } }} + /> + + + + `inset 0 -2px 0 0 ${varAlpha(theme.vars.palette.grey['500Channel'], 0.08)}`, + }} + > + {STATUS_OPTIONS.map((tab) => ( + + {['active', 'pending', 'banned', 'rejected'].includes(tab.value) + ? tableData.filter((user) => user.status === tab.value).length + : tableData.length} + + } + /> + ))} + + + + + {canReset && ( + + )} + + + + table.onSelectAllRows( + checked, + dataFiltered.map((row) => row.id) + ) + } + action={ + + + + + + } + /> + + + + + table.onSelectAllRows( + checked, + dataFiltered.map((row) => row.id) + ) + } + /> + + + {dataFiltered + .slice( + table.page * table.rowsPerPage, + table.page * table.rowsPerPage + table.rowsPerPage + ) + .map((row) => ( + table.onSelectRow(row.id)} + onDeleteRow={() => handleDeleteRow(row.id)} + onEditRow={() => handleEditRow(row.id)} + /> + ))} + + + + + +
    +
    +
    + + +
    +
    + + + Are you sure want to delete {table.selected.length} items? + + } + action={ + + } + /> + + ); +} + +function applyFilter({ inputData, comparator, filters }) { + const { name, status, role } = filters; + + const stabilizedThis = inputData.map((el, index) => [el, index]); + + stabilizedThis.sort((a, b) => { + const order = comparator(a[0], b[0]); + if (order !== 0) return order; + return a[1] - b[1]; + }); + + inputData = stabilizedThis.map((el) => el[0]); + + if (name) { + inputData = inputData.filter( + (user) => user.name.toLowerCase().indexOf(name.toLowerCase()) !== -1 + ); + } + + if (status !== 'all') { + inputData = inputData.filter((user) => user.status === status); + } + + if (role.length) { + inputData = inputData.filter((user) => role.includes(user.role)); + } + + return inputData; +} diff --git a/front_minimal/src/sections/user/view/user-profile-view.jsx b/front_minimal/src/sections/user/view/user-profile-view.jsx new file mode 100644 index 0000000..1c3213b --- /dev/null +++ b/front_minimal/src/sections/user/view/user-profile-view.jsx @@ -0,0 +1,113 @@ +'use client'; + +import { useState, useCallback } from 'react'; + +import Box from '@mui/material/Box'; +import Tab from '@mui/material/Tab'; +import Card from '@mui/material/Card'; +import Tabs from '@mui/material/Tabs'; + +import { paths } from 'src/routes/paths'; + +import { useTabs } from 'src/hooks/use-tabs'; + +import { DashboardContent } from 'src/layouts/dashboard'; +import { _userAbout, _userFeeds, _userFriends, _userGallery, _userFollowers } from 'src/_mock'; + +import { Iconify } from 'src/components/iconify'; +import { CustomBreadcrumbs } from 'src/components/custom-breadcrumbs'; + +import { useMockedUser } from 'src/auth/hooks'; + +import { ProfileHome } from '../profile-home'; +import { ProfileCover } from '../profile-cover'; +import { ProfileFriends } from '../profile-friends'; +import { ProfileGallery } from '../profile-gallery'; +import { ProfileFollowers } from '../profile-followers'; + +// ---------------------------------------------------------------------- + +const TABS = [ + { value: 'profile', label: 'Profile', icon: }, + { value: 'followers', label: 'Followers', icon: }, + { + value: 'friends', + label: 'Friends', + icon: , + }, + { + value: 'gallery', + label: 'Gallery', + icon: , + }, +]; + +// ---------------------------------------------------------------------- + +export function UserProfileView() { + const { user } = useMockedUser(); + + const [searchFriends, setSearchFriends] = useState(''); + + const tabs = useTabs('profile'); + + const handleSearchFriends = useCallback((event) => { + setSearchFriends(event.target.value); + }, []); + + return ( + + + + + + + + + {TABS.map((tab) => ( + + ))} + + + + + {tabs.value === 'profile' && } + + {tabs.value === 'followers' && } + + {tabs.value === 'friends' && ( + + )} + + {tabs.value === 'gallery' && } + + ); +} diff --git a/front_minimal/src/theme/color-scheme-script.js b/front_minimal/src/theme/color-scheme-script.js new file mode 100644 index 0000000..e780bd1 --- /dev/null +++ b/front_minimal/src/theme/color-scheme-script.js @@ -0,0 +1,14 @@ +'use client'; + +import { getInitColorSchemeScript as _getInitColorSchemeScript } from '@mui/material/styles'; + +import { defaultSettings } from 'src/components/settings'; + +// ---------------------------------------------------------------------- + +export const schemeConfig = { + modeStorageKey: 'theme-mode', + defaultMode: defaultSettings.colorScheme, +}; + +export const getInitColorSchemeScript = _getInitColorSchemeScript(schemeConfig); diff --git a/front_minimal/src/theme/core/colors.json b/front_minimal/src/theme/core/colors.json new file mode 100644 index 0000000..b258fd8 --- /dev/null +++ b/front_minimal/src/theme/core/colors.json @@ -0,0 +1,66 @@ +{ + "primary": { + "lighter": "#C8FAD6", + "light": "#5BE49B", + "main": "#00A76F", + "dark": "#007867", + "darker": "#004B50", + "contrastText": "#FFFFFF" + }, + "secondary": { + "lighter": "#EFD6FF", + "light": "#C684FF", + "main": "#8E33FF", + "dark": "#5119B7", + "darker": "#27097A", + "contrastText": "#FFFFFF" + }, + "info": { + "lighter": "#CAFDF5", + "light": "#61F3F3", + "main": "#00B8D9", + "dark": "#006C9C", + "darker": "#003768", + "contrastText": "#FFFFFF" + }, + "success": { + "lighter": "#D3FCD2", + "light": "#77ED8B", + "main": "#22C55E", + "dark": "#118D57", + "darker": "#065E49", + "contrastText": "#ffffff" + }, + "warning": { + "lighter": "#FFF5CC", + "light": "#FFD666", + "main": "#FFAB00", + "dark": "#B76E00", + "darker": "#7A4100", + "contrastText": "#1C252E" + }, + "error": { + "lighter": "#FFE9D5", + "light": "#FFAC82", + "main": "#FF5630", + "dark": "#B71D18", + "darker": "#7A0916", + "contrastText": "#FFFFFF" + }, + "grey": { + "50": "#FCFDFD", + "100": "#F9FAFB", + "200": "#F4F6F8", + "300": "#DFE3E8", + "400": "#C4CDD5", + "500": "#919EAB", + "600": "#637381", + "700": "#454F5B", + "800": "#1C252E", + "900": "#141A21" + }, + "common": { + "black": "#000000", + "white": "#FFFFFF" + } +} diff --git a/front_minimal/src/theme/core/components/accordion.jsx b/front_minimal/src/theme/core/components/accordion.jsx new file mode 100644 index 0000000..eb9b05c --- /dev/null +++ b/front_minimal/src/theme/core/components/accordion.jsx @@ -0,0 +1,46 @@ +import { accordionClasses } from '@mui/material/Accordion'; +import { typographyClasses } from '@mui/material/Typography'; +import { accordionSummaryClasses } from '@mui/material/AccordionSummary'; + +// ---------------------------------------------------------------------- + +const MuiAccordion = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + backgroundColor: 'transparent', + [`&.${accordionClasses.expanded}`]: { + boxShadow: theme.customShadows.z8, + borderRadius: theme.shape.borderRadius, + backgroundColor: theme.vars.palette.background.paper, + }, + [`&.${accordionClasses.disabled}`]: { backgroundColor: 'transparent' }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiAccordionSummary = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + paddingLeft: theme.spacing(2), + paddingRight: theme.spacing(1), + [`&.${accordionSummaryClasses.disabled}`]: { + opacity: 1, + color: theme.vars.palette.action.disabled, + [`& .${typographyClasses.root}`]: { color: 'inherit' }, + }, + }), + expandIconWrapper: { color: 'inherit' }, + }, +}; + +// ---------------------------------------------------------------------- + +export const accordion = { MuiAccordion, MuiAccordionSummary }; diff --git a/front_minimal/src/theme/core/components/alert.jsx b/front_minimal/src/theme/core/components/alert.jsx new file mode 100644 index 0000000..09c92cc --- /dev/null +++ b/front_minimal/src/theme/core/components/alert.jsx @@ -0,0 +1,162 @@ +import SvgIcon from '@mui/material/SvgIcon'; +import { alertClasses } from '@mui/material/Alert'; + +import { varAlpha, stylesMode } from '../../styles'; + +// ---------------------------------------------------------------------- + +/** + * Icons + */ +/* https://icon-sets.iconify.design/solar/info-circle-bold/ */ +const AlertInfoIcon = (props) => ( + + + +); + +/* https://icon-sets.iconify.design/solar/check-circle-bold/ */ +const AlertSuccessIcon = (props) => ( + + + +); + +/* https:// icon-sets.iconify.design/solar/danger-triangle-bold/ */ +const AlertWarningIcon = (props) => ( + + + +); + +/* https://icon-sets.iconify.design/solar/danger-bold/ */ +const AlertErrorIcon = (props) => ( + + + +); + +// ---------------------------------------------------------------------- + +const COLORS = ['info', 'success', 'warning', 'error']; + +function styleColors(ownerState, styles) { + const outputStyle = COLORS.reduce((acc, color) => { + if (ownerState.severity === color) { + acc = styles(color); + } + return acc; + }, {}); + + return outputStyle; +} + +// ---------------------------------------------------------------------- + +const MuiAlert = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { + iconMapping: { + error: , + info: , + success: , + warning: , + }, + }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + icon: { opacity: 1 }, + /** + * @variant standard + */ + standard: ({ ownerState, theme }) => { + const styled = { + colors: styleColors(ownerState, (color) => ({ + color: theme.vars.palette[color].darker, + backgroundColor: theme.vars.palette[color].lighter, + [stylesMode.dark]: { + color: theme.vars.palette[color].lighter, + backgroundColor: theme.vars.palette[color].darker, + }, + [`& .${alertClasses.icon}`]: { + color: theme.vars.palette[color].main, + [stylesMode.dark]: { color: theme.vars.palette[color].light }, + }, + })), + }; + + return { ...styled.colors }; + }, + /** + * @variant filled + */ + filled: ({ ownerState, theme }) => { + const styled = { + colors: styleColors(ownerState, (color) => ({ + color: theme.vars.palette[color].contrastText, + })), + }; + + return { ...styled.colors }; + }, + /** + * @variant outlined + */ + outlined: ({ ownerState, theme }) => { + const styled = { + colors: styleColors(ownerState, (color) => ({ + backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.08), + color: theme.vars.palette[color].dark, + border: `solid 1px ${varAlpha(theme.vars.palette[color].mainChannel, 0.16)}`, + [stylesMode.dark]: { color: theme.vars.palette[color].light }, + [`& .${alertClasses.icon}`]: { color: theme.vars.palette[color].main }, + })), + }; + + return { ...styled.colors }; + }, + }, +}; + +// ---------------------------------------------------------------------- + +const MuiAlertTitle = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + marginBottom: theme.spacing(0.5), + fontWeight: theme.typography.fontWeightSemiBold, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const alert = { MuiAlert, MuiAlertTitle }; diff --git a/front_minimal/src/theme/core/components/appbar.jsx b/front_minimal/src/theme/core/components/appbar.jsx new file mode 100644 index 0000000..c7c4bd9 --- /dev/null +++ b/front_minimal/src/theme/core/components/appbar.jsx @@ -0,0 +1,17 @@ +// ---------------------------------------------------------------------- + +const MuiAppBar = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { color: 'transparent' }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { root: { boxShadow: 'none' } }, +}; + +// ---------------------------------------------------------------------- + +export const appBar = { MuiAppBar }; diff --git a/front_minimal/src/theme/core/components/autocomplete.jsx b/front_minimal/src/theme/core/components/autocomplete.jsx new file mode 100644 index 0000000..6532929 --- /dev/null +++ b/front_minimal/src/theme/core/components/autocomplete.jsx @@ -0,0 +1,57 @@ +import SvgIcon, { svgIconClasses } from '@mui/material/SvgIcon'; +import { autocompleteClasses } from '@mui/material/Autocomplete'; + +import { paper, varAlpha, menuItem } from '../../styles'; + +// ---------------------------------------------------------------------- + +/** + * Icons + * https://icon-sets.iconify.design/eva/arrow-ios-downward-fill/ + */ +const ArrowDownIcon = (props) => ( + + + +); + +// ---------------------------------------------------------------------- + +const MuiAutocomplete = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { popupIcon: }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + [`& span.${autocompleteClasses.tag}`]: { + ...theme.typography.subtitle2, + height: 24, + minWidth: 24, + lineHeight: '24px', + textAlign: 'center', + padding: theme.spacing(0, 0.75), + color: theme.vars.palette.text.secondary, + borderRadius: theme.shape.borderRadius, + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + }, + }), + paper: ({ theme }) => ({ ...paper({ theme, dropdown: true }) }), + listbox: ({ theme }) => ({ + padding: 0, + [`& .${autocompleteClasses.option}`]: { ...menuItem(theme) }, + }), + endAdornment: { [`& .${svgIconClasses.root}`]: { width: 18, height: 18 } }, + }, +}; + +// ---------------------------------------------------------------------- + +export const autocomplete = { MuiAutocomplete }; diff --git a/front_minimal/src/theme/core/components/avatar.jsx b/front_minimal/src/theme/core/components/avatar.jsx new file mode 100644 index 0000000..4b27265 --- /dev/null +++ b/front_minimal/src/theme/core/components/avatar.jsx @@ -0,0 +1,113 @@ +import { avatarGroupClasses } from '@mui/material/AvatarGroup'; + +import { varAlpha } from '../../styles'; + +const COLORS = ['primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const colorByName = (name) => { + const charAt = name.charAt(0).toLowerCase(); + + if (['a', 'c', 'f'].includes(charAt)) return 'primary'; + if (['e', 'd', 'h'].includes(charAt)) return 'secondary'; + if (['i', 'k', 'l'].includes(charAt)) return 'info'; + if (['m', 'n', 'p'].includes(charAt)) return 'success'; + if (['q', 's', 't'].includes(charAt)) return 'warning'; + if (['v', 'x', 'y'].includes(charAt)) return 'error'; + return 'default'; +}; + +// ---------------------------------------------------------------------- + +const avatarColors = { + colors: COLORS.map((color) => ({ + props: ({ ownerState }) => ownerState.color === color, + style: ({ theme }) => ({ + color: theme.vars.palette[color].contrastText, + backgroundColor: theme.vars.palette[color].main, + }), + })), + defaultColor: [ + { + props: ({ ownerState }) => ownerState.color === 'default', + style: ({ theme }) => ({ + color: theme.vars.palette.text.secondary, + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.24), + }), + }, + ], +}; + +const MuiAvatar = { + /** ************************************** + * VARIANTS + *************************************** */ + variants: [...[...avatarColors.defaultColor, ...avatarColors.colors]], + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + rounded: ({ theme }) => ({ borderRadius: theme.shape.borderRadius * 1.5 }), + colorDefault: ({ ownerState, theme }) => { + const color = colorByName(`${ownerState.alt}`); + + return { + ...(!!ownerState.alt && { + ...(color !== 'default' + ? { + color: theme.vars.palette[color].contrastText, + backgroundColor: theme.vars.palette[color].main, + } + : { + color: theme.vars.palette.text.secondary, + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.24), + }), + }), + }; + }, + }, +}; + +// ---------------------------------------------------------------------- + +const MuiAvatarGroup = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { max: 4 }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ ownerState }) => ({ + justifyContent: 'flex-end', + ...(ownerState.variant === 'compact' && { + width: 40, + height: 40, + position: 'relative', + [`& .${avatarGroupClasses.avatar}`]: { + margin: 0, + width: 28, + height: 28, + position: 'absolute', + '&:first-of-type': { left: 0, bottom: 0, zIndex: 9 }, + '&:last-of-type': { top: 0, right: 0 }, + }, + }), + }), + avatar: ({ theme }) => ({ + fontSize: 16, + fontWeight: theme.typography.fontWeightSemiBold, + '&:first-of-type': { + fontSize: 12, + color: theme.vars.palette.primary.dark, + backgroundColor: theme.vars.palette.primary.lighter, + }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const avatar = { MuiAvatar, MuiAvatarGroup }; diff --git a/front_minimal/src/theme/core/components/backdrop.jsx b/front_minimal/src/theme/core/components/backdrop.jsx new file mode 100644 index 0000000..03a6f61 --- /dev/null +++ b/front_minimal/src/theme/core/components/backdrop.jsx @@ -0,0 +1,19 @@ +import { varAlpha } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiBackdrop = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + backgroundColor: varAlpha(theme.vars.palette.grey['800Channel'], 0.48), + }), + invisible: { background: 'transparent' }, + }, +}; + +// ---------------------------------------------------------------------- + +export const backdrop = { MuiBackdrop }; diff --git a/front_minimal/src/theme/core/components/badge.jsx b/front_minimal/src/theme/core/components/badge.jsx new file mode 100644 index 0000000..96b09e3 --- /dev/null +++ b/front_minimal/src/theme/core/components/badge.jsx @@ -0,0 +1,93 @@ +import { badgeClasses } from '@mui/material/Badge'; + +// ---------------------------------------------------------------------- + +const baseStyles = (theme) => ({ + width: 10, + zIndex: 9, + padding: 0, + height: 10, + minWidth: 'auto', + '&::before, &::after': { + content: "''", + borderRadius: 1, + backgroundColor: theme.vars.palette.common.white, + }, + [`&.${badgeClasses.invisible}`]: { transform: 'unset' }, +}); + +const MuiBadge = { + /** ************************************** + * VARIANTS + *************************************** */ + variants: [ + /** + * @variant online + */ + { + props: ({ ownerState }) => ownerState.variant === 'online', + style: ({ theme }) => ({ + [`& .${badgeClasses.badge}`]: { + ...baseStyles(theme), + backgroundColor: theme.vars.palette.success.main, + }, + }), + }, + /** + * @variant alway + */ + { + props: ({ ownerState }) => ownerState.variant === 'alway', + style: ({ theme }) => ({ + [`& .${badgeClasses.badge}`]: { + ...baseStyles(theme), + backgroundColor: theme.vars.palette.warning.main, + '&::before': { width: 2, height: 4, transform: 'translateX(1px) translateY(-1px)' }, + '&::after': { width: 2, height: 4, transform: 'translateY(1px) rotate(125deg)' }, + }, + }), + }, + /** + * @variant busy + */ + { + props: ({ ownerState }) => ownerState.variant === 'busy', + style: ({ theme }) => ({ + [`& .${badgeClasses.badge}`]: { + ...baseStyles(theme), + backgroundColor: theme.vars.palette.error.main, + '&::before': { width: 6, height: 2 }, + }, + }), + }, + /** + * @variant offline + */ + { + props: ({ ownerState }) => ownerState.variant === 'offline', + style: ({ theme }) => ({ + [`& .${badgeClasses.badge}`]: { + ...baseStyles(theme), + backgroundColor: theme.vars.palette.text.disabled, + '&::before': { width: 6, height: 6, borderRadius: '50%' }, + }, + }), + }, + /** + * @variant invisible + */ + { + props: ({ ownerState }) => ownerState.variant === 'invisible', + style: { [`& .${badgeClasses.badge}`]: { display: 'none' } }, + }, + ], + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { dot: { borderRadius: '50%' } }, +}; + +// ---------------------------------------------------------------------- + +export const badge = { MuiBadge }; diff --git a/front_minimal/src/theme/core/components/breadcrumbs.jsx b/front_minimal/src/theme/core/components/breadcrumbs.jsx new file mode 100644 index 0000000..b0e2c30 --- /dev/null +++ b/front_minimal/src/theme/core/components/breadcrumbs.jsx @@ -0,0 +1,17 @@ +// ---------------------------------------------------------------------- + +const MuiBreadcrumbs = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + ol: ({ theme }) => ({ rowGap: theme.spacing(0.5), columnGap: theme.spacing(2) }), + + li: ({ theme }) => ({ display: 'inline-flex', '& > *': { ...theme.typography.body2 } }), + separator: { margin: 0 }, + }, +}; + +// ---------------------------------------------------------------------- + +export const breadcrumbs = { MuiBreadcrumbs }; diff --git a/front_minimal/src/theme/core/components/button-fab.jsx b/front_minimal/src/theme/core/components/button-fab.jsx new file mode 100644 index 0000000..e2e34c7 --- /dev/null +++ b/front_minimal/src/theme/core/components/button-fab.jsx @@ -0,0 +1,190 @@ +import { fabClasses } from '@mui/material/Fab'; + +import { varAlpha, stylesMode } from '../../styles'; + +const COLORS = ['primary', 'secondary', 'info', 'success', 'warning', 'error']; + +const DEFAULT_COLORS = ['default', 'inherit']; +const EXTENDED_VARIANT = ['extended', 'outlinedExtended', 'softExtended']; +const FILLED_VARIANT = ['circular', 'extended']; +const OUTLINED_VARIANT = ['outlined', 'outlinedExtended']; +const SOFT_VARIANT = ['soft', 'softExtended']; + +// ---------------------------------------------------------------------- + +const filledVariant = { + colors: COLORS.map((color) => ({ + props: ({ ownerState }) => + !ownerState.disabled && + FILLED_VARIANT.includes(ownerState.variant) && + ownerState.color === color, + style: ({ theme }) => ({ + boxShadow: theme.customShadows[color], + '&:hover': { boxShadow: 'none' }, + }), + })), + base: [ + { + props: ({ ownerState }) => + FILLED_VARIANT.includes(ownerState.variant) && DEFAULT_COLORS.includes(ownerState.color), + style: ({ theme }) => ({ + boxShadow: theme.customShadows.z8, + /** + * @color default + */ + color: theme.vars.palette.grey[800], + backgroundColor: theme.vars.palette.grey[300], + '&:hover': { boxShadow: 'none', backgroundColor: theme.vars.palette.grey[400] }, + /** + * @color inherit + */ + [`&.${fabClasses.colorInherit}`]: { + color: theme.vars.palette.common.white, + backgroundColor: theme.vars.palette.text.primary, + '&:hover': { backgroundColor: theme.vars.palette.grey[700] }, + [stylesMode.dark]: { + color: theme.vars.palette.grey[800], + '&:hover': { backgroundColor: theme.vars.palette.grey[400] }, + }, + }, + }), + }, + ], +}; + +const outlinedVariant = { + colors: COLORS.map((color) => ({ + props: ({ ownerState }) => + !ownerState.disabled && + OUTLINED_VARIANT.includes(ownerState.variant) && + ownerState.color === color, + style: ({ theme }) => ({ + color: theme.vars.palette[color].main, + border: `solid 1px ${varAlpha(theme.vars.palette[color].mainChannel, 0.48)}`, + '&:hover': { backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.08) }, + }), + })), + base: [ + { + props: ({ ownerState }) => OUTLINED_VARIANT.includes(ownerState.variant), + style: ({ theme }) => ({ + boxShadow: 'none', + backgroundColor: 'transparent', + color: theme.vars.palette.text.secondary, + border: `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.32)}`, + '&:hover': { + borderColor: 'currentColor', + boxShadow: '0 0 0 0.75px currentColor', + backgroundColor: theme.vars.palette.action.hover, + }, + [`&.${fabClasses.colorInherit}`]: { color: theme.vars.palette.text.primary }, + [`&.${fabClasses.disabled}`]: { + backgroundColor: 'transparent', + border: `1px solid ${theme.vars.palette.action.disabledBackground}`, + }, + }), + }, + ], +}; + +const softVariant = { + colors: COLORS.map((color) => ({ + props: ({ ownerState }) => + !ownerState.disabled && + SOFT_VARIANT.includes(ownerState.variant) && + ownerState.color === color, + style: ({ theme }) => ({ + boxShadow: 'none', + color: theme.vars.palette[color].dark, + backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.16), + '&:hover': { + boxShadow: 'none', + backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.32), + }, + [stylesMode.dark]: { color: theme.vars.palette[color].light }, + }), + })), + base: [ + { + props: ({ ownerState }) => + SOFT_VARIANT.includes(ownerState.variant) && DEFAULT_COLORS.includes(ownerState.color), + style: ({ theme }) => ({ + /** + * @color default + */ + boxShadow: 'none', + color: theme.vars.palette.grey[800], + backgroundColor: theme.vars.palette.grey[300], + '&:hover': { boxShadow: 'none', backgroundColor: theme.vars.palette.grey[400] }, + /** + * @color inherit + */ + [`&.${fabClasses.colorInherit}`]: { + color: theme.vars.palette.text.primary, + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + '&:hover': { backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.24) }, + }, + }), + }, + ], +}; + +const sizes = [ + { + props: ({ ownerState }) => EXTENDED_VARIANT.includes(ownerState.variant), + style: ({ theme }) => ({ + height: 48, + width: 'auto', + minHeight: 48, + borderRadius: 48 / 2, + gap: theme.spacing(1), + padding: theme.spacing(0, 2), + [`&.${fabClasses.sizeSmall}`]: { + height: 34, + minHeight: 34, + borderRadius: 34 / 2, + gap: theme.spacing(0.5), + padding: theme.spacing(0, 1), + }, + [`&.${fabClasses.sizeMedium}`]: { height: 40, minHeight: 40, borderRadius: 40 / 2 }, + }), + }, +]; + +const MuiFab = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { color: 'primary' }, + + /** ************************************** + * VARIANTS + *************************************** */ + variants: [ + /** + * @variant filled + */ + ...[...filledVariant.base, ...filledVariant.colors], + /** + * @variant outlined + */ + ...[...outlinedVariant.base, ...outlinedVariant.colors], + /** + * @variant soft + */ + ...[...softVariant.base, ...softVariant.colors], + /** + * @sizes + */ + ...sizes, + ], + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: {}, +}; + +// ---------------------------------------------------------------------- + +export const fab = { MuiFab }; diff --git a/front_minimal/src/theme/core/components/button-group.jsx b/front_minimal/src/theme/core/components/button-group.jsx new file mode 100644 index 0000000..825fe93 --- /dev/null +++ b/front_minimal/src/theme/core/components/button-group.jsx @@ -0,0 +1,142 @@ +import { buttonGroupClasses } from '@mui/material/ButtonGroup'; + +import { varAlpha, stylesMode } from '../../styles'; + +const COLORS = ['primary', 'secondary', 'info', 'success', 'warning', 'error']; + +function styleColors(ownerState, styles) { + const outputStyle = COLORS.reduce((acc, color) => { + if (!ownerState.disabled && ownerState.color === color) { + acc = styles(color); + } + return acc; + }, {}); + + return outputStyle; +} + +const buttonClasses = `& .${buttonGroupClasses.firstButton}, & .${buttonGroupClasses.middleButton}`; + +const softVariant = { + colors: COLORS.map((color) => ({ + props: ({ ownerState }) => + !ownerState.disabled && ownerState.variant === 'soft' && ownerState.color === color, + style: ({ theme }) => ({ + [buttonClasses]: { + borderColor: varAlpha(theme.vars.palette[color].darkChannel, 0.24), + [stylesMode.dark]: { borderColor: varAlpha(theme.vars.palette[color].lightChannel, 0.24) }, + }, + [`&.${buttonGroupClasses.vertical}`]: { + [buttonClasses]: { + borderColor: varAlpha(theme.vars.palette[color].darkChannel, 0.24), + [stylesMode.dark]: { + borderColor: varAlpha(theme.vars.palette[color].lightChannel, 0.24), + }, + }, + }, + }), + })), + base: [ + { + props: ({ ownerState }) => ownerState.variant === 'soft', + style: ({ theme }) => ({ + [buttonClasses]: { + borderRight: `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.32)}`, + [`&.${buttonGroupClasses.disabled}`]: { + borderColor: theme.vars.palette.action.disabledBackground, + }, + }, + [`&.${buttonGroupClasses.vertical}`]: { + [buttonClasses]: { + borderRight: 'none', + borderBottom: `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.32)}`, + [`&.${buttonGroupClasses.disabled}`]: { + borderColor: theme.vars.palette.action.disabledBackground, + }, + }, + }, + }), + }, + ], +}; + +// ---------------------------------------------------------------------- + +const MuiButtonGroup = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { disableElevation: true }, + + /** ************************************** + * VARIANTS + *************************************** */ + variants: [ + /** + * @variant soft + */ + ...[...softVariant.base, ...softVariant.colors], + ], + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + /** + * @variant contained + */ + contained: ({ theme, ownerState }) => { + const styled = { + colors: styleColors(ownerState, (color) => ({ + [buttonClasses]: { borderColor: varAlpha(theme.vars.palette[color].darkChannel, 0.48) }, + })), + inheritColor: { + ...(ownerState.color === 'inherit' && { + [buttonClasses]: { borderColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.32) }, + }), + }, + disabled: { + ...(ownerState.disabled && { + [buttonClasses]: { + [`&.${buttonGroupClasses.disabled}`]: { + borderColor: theme.vars.palette.action.disabledBackground, + }, + }, + }), + }, + }; + + return { ...styled.inheritColor, ...styled.colors, ...styled.disabled }; + }, + /** + * @variant text + */ + text: ({ theme, ownerState }) => { + const styled = { + colors: styleColors(ownerState, (color) => ({ + [buttonClasses]: { borderColor: varAlpha(theme.vars.palette[color].mainChannel, 0.48) }, + })), + inheritColor: { + ...(ownerState.color === 'inherit' && { + [buttonClasses]: { borderColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.32) }, + }), + }, + disabled: { + ...(ownerState.disabled && { + [buttonClasses]: { + [`&.${buttonGroupClasses.disabled}`]: { + borderColor: theme.vars.palette.action.disabledBackground, + }, + }, + }), + }, + }; + + return { ...styled.inheritColor, ...styled.colors, ...styled.disabled }; + }, + }, +}; + +// ---------------------------------------------------------------------- + +export const buttonGroup = { MuiButtonGroup }; diff --git a/front_minimal/src/theme/core/components/button-toggle.jsx b/front_minimal/src/theme/core/components/button-toggle.jsx new file mode 100644 index 0000000..0fe0a64 --- /dev/null +++ b/front_minimal/src/theme/core/components/button-toggle.jsx @@ -0,0 +1,81 @@ +import { toggleButtonClasses } from '@mui/material/ToggleButton'; + +import { varAlpha } from '../../styles'; + +// ---------------------------------------------------------------------- + +const COLORS = ['primary', 'secondary', 'info', 'success', 'warning', 'error']; + +function styleColors(ownerState, styles) { + const outputStyle = COLORS.reduce((acc, color) => { + if (!ownerState.disabled && ownerState.color === color) { + acc = styles(color); + } + return acc; + }, {}); + + return outputStyle; +} + +// ---------------------------------------------------------------------- + +const MuiToggleButton = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme, ownerState }) => { + const styled = { + colors: styleColors(ownerState, (color) => ({ + '&:hover': { + borderColor: varAlpha(theme.vars.palette[color].mainChannel, 0.48), + backgroundColor: varAlpha( + theme.vars.palette[color].mainChannel, + theme.vars.palette.action.hoverOpacity + ), + }, + })), + selected: { + [`&.${toggleButtonClasses.selected}`]: { + borderColor: 'currentColor', + boxShadow: '0 0 0 0.75px currentColor', + }, + }, + disabled: { + ...(ownerState.disabled && { + [`&.${toggleButtonClasses.selected}`]: { + color: theme.vars.palette.action.disabled, + backgroundColor: theme.vars.palette.action.selected, + borderColor: theme.vars.palette.action.disabledBackground, + }, + }), + }, + }; + + return { ...styled.colors, ...styled.selected, ...styled.disabled }; + }, + }, +}; + +// ---------------------------------------------------------------------- + +const MuiToggleButtonGroup = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + gap: 4, + padding: 4, + border: `solid 1px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.08)}`, + }), + grouped: { + [`&.${toggleButtonClasses.root}`]: { border: 'none', borderRadius: 'inherit' }, + [`&.${toggleButtonClasses.selected}`]: { boxShadow: 'none' }, + }, + }, +}; + +// ---------------------------------------------------------------------- + +export const toggleButton = { MuiToggleButton, MuiToggleButtonGroup }; diff --git a/front_minimal/src/theme/core/components/button.jsx b/front_minimal/src/theme/core/components/button.jsx new file mode 100644 index 0000000..e34c282 --- /dev/null +++ b/front_minimal/src/theme/core/components/button.jsx @@ -0,0 +1,168 @@ +import { buttonClasses } from '@mui/material/Button'; +import { loadingButtonClasses } from '@mui/lab/LoadingButton'; + +import { varAlpha, stylesMode } from '../../styles'; + +const COLORS = ['primary', 'secondary', 'info', 'success', 'warning', 'error']; + +function styleColors(ownerState, styles) { + const outputStyle = COLORS.reduce((acc, color) => { + if (!ownerState.disabled && ownerState.color === color) { + acc = styles(color); + } + return acc; + }, {}); + + return outputStyle; +} + +// ---------------------------------------------------------------------- + +const MuiButtonBase = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { root: ({ theme }) => ({ fontFamily: theme.typography.fontFamily }) }, +}; + +// ---------------------------------------------------------------------- + +const softVariant = { + colors: COLORS.map((color) => ({ + props: ({ ownerState }) => + !ownerState.disabled && ownerState.variant === 'soft' && ownerState.color === color, + style: ({ theme }) => ({ + color: theme.vars.palette[color].dark, + backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.16), + '&:hover': { backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.32) }, + [stylesMode.dark]: { color: theme.vars.palette[color].light }, + }), + })), + base: [ + { + props: ({ ownerState }) => ownerState.variant === 'soft', + style: ({ theme }) => ({ + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + '&:hover': { backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.24) }, + [`&.${buttonClasses.disabled}`]: { + backgroundColor: theme.vars.palette.action.disabledBackground, + }, + [`& .${loadingButtonClasses.loadingIndicatorStart}`]: { left: 14 }, + [`& .${loadingButtonClasses.loadingIndicatorEnd}`]: { right: 14 }, + [`&.${buttonClasses.sizeSmall}`]: { + [`& .${loadingButtonClasses.loadingIndicatorStart}`]: { left: 10 }, + [`& .${loadingButtonClasses.loadingIndicatorEnd}`]: { right: 10 }, + }, + }), + }, + ], +}; + +const MuiButton = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { color: 'inherit', disableElevation: true }, + + /** ************************************** + * VARIANTS + *************************************** */ + variants: [ + /** + * @variant soft + */ + ...[...softVariant.base, ...softVariant.colors], + ], + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + /** + * @variant contained + */ + contained: ({ theme, ownerState }) => { + const styled = { + colors: styleColors(ownerState, (color) => ({ + '&:hover': { boxShadow: theme.customShadows[color] }, + })), + inheritColor: { + ...(ownerState.color === 'inherit' && + !ownerState.disabled && { + color: theme.vars.palette.common.white, + backgroundColor: theme.vars.palette.grey[800], + '&:hover': { + boxShadow: theme.customShadows.z8, + backgroundColor: theme.vars.palette.grey[700], + }, + [stylesMode.dark]: { + color: theme.vars.palette.grey[800], + backgroundColor: theme.vars.palette.common.white, + '&:hover': { backgroundColor: theme.vars.palette.grey[400] }, + }, + }), + }, + }; + return { ...styled.inheritColor, ...styled.colors }; + }, + /** + * @variant outlined + */ + outlined: ({ theme, ownerState }) => { + const styled = { + colors: styleColors(ownerState, (color) => ({ + borderColor: varAlpha(theme.vars.palette[color].mainChannel, 0.48), + })), + inheritColor: { + ...(ownerState.color === 'inherit' && + !ownerState.disabled && { + borderColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.32), + '&:hover': { backgroundColor: theme.vars.palette.action.hover }, + }), + }, + base: { + '&:hover': { borderColor: 'currentColor', boxShadow: '0 0 0 0.75px currentColor' }, + }, + }; + return { ...styled.base, ...styled.inheritColor, ...styled.colors }; + }, + /** + * @variant text + */ + text: ({ ownerState, theme }) => { + const styled = { + inheritColor: { + ...(ownerState.color === 'inherit' && + !ownerState.disabled && { + '&:hover': { backgroundColor: theme.vars.palette.action.hover }, + }), + }, + }; + return { ...styled.inheritColor }; + }, + /** + * @size + */ + sizeSmall: ({ ownerState }) => ({ + height: 30, + ...(ownerState.variant === 'text' + ? { paddingLeft: '4px', paddingRight: '4px' } + : { paddingLeft: '8px', paddingRight: '8px' }), + }), + sizeMedium: ({ ownerState }) => ({ + ...(ownerState.variant === 'text' + ? { paddingLeft: '8px', paddingRight: '8px' } + : { paddingLeft: '12px', paddingRight: '12px' }), + }), + sizeLarge: ({ ownerState }) => ({ + height: 48, + ...(ownerState.variant === 'text' + ? { paddingLeft: '10px', paddingRight: '10px' } + : { paddingLeft: '16px', paddingRight: '16px' }), + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const button = { MuiButtonBase, MuiButton }; diff --git a/front_minimal/src/theme/core/components/card.jsx b/front_minimal/src/theme/core/components/card.jsx new file mode 100644 index 0000000..3bdd7b7 --- /dev/null +++ b/front_minimal/src/theme/core/components/card.jsx @@ -0,0 +1,49 @@ +// ---------------------------------------------------------------------- + +const MuiCard = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + position: 'relative', + boxShadow: theme.customShadows.card, + borderRadius: theme.shape.borderRadius * 2, + zIndex: 0, // Fix Safari overflow: hidden with border radius + }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiCardHeader = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { + titleTypographyProps: { variant: 'h6' }, + subheaderTypographyProps: { variant: 'body2', marginTop: '4px' }, + }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + padding: theme.spacing(3, 3, 0), + }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiCardContent = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { root: ({ theme }) => ({ padding: theme.spacing(3) }) }, +}; + +// ---------------------------------------------------------------------- + +export const card = { MuiCard, MuiCardHeader, MuiCardContent }; diff --git a/front_minimal/src/theme/core/components/checkbox.jsx b/front_minimal/src/theme/core/components/checkbox.jsx new file mode 100644 index 0000000..e089e99 --- /dev/null +++ b/front_minimal/src/theme/core/components/checkbox.jsx @@ -0,0 +1,56 @@ +import SvgIcon from '@mui/material/SvgIcon'; +import { checkboxClasses } from '@mui/material/Checkbox'; + +// ---------------------------------------------------------------------- + +/** + * Icons + */ +export const CheckboxIcon = (props) => ( + + + +); + +export const CheckboxCheckedIcon = (props) => ( + + + +); + +export const CheckboxIndeterminateIcon = (props) => ( + + + +); + +// ---------------------------------------------------------------------- + +const MuiCheckbox = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { + size: 'small', + icon: , + checkedIcon: , + indeterminateIcon: , + }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ ownerState, theme }) => ({ + padding: theme.spacing(1), + ...(ownerState.color === 'default' && { + [`&.${checkboxClasses.checked}`]: { color: theme.vars.palette.text.primary }, + }), + [`&.${checkboxClasses.disabled}`]: { color: theme.vars.palette.action.disabled }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const checkbox = { MuiCheckbox }; diff --git a/front_minimal/src/theme/core/components/chip.jsx b/front_minimal/src/theme/core/components/chip.jsx new file mode 100644 index 0000000..00885af --- /dev/null +++ b/front_minimal/src/theme/core/components/chip.jsx @@ -0,0 +1,160 @@ +import SvgIcon from '@mui/material/SvgIcon'; +import { chipClasses } from '@mui/material/Chip'; + +import { varAlpha, stylesMode } from '../../styles'; + +// ---------------------------------------------------------------------- + +/** + * Icons + * https://icon-sets.iconify.design/solar/close-circle-bold + */ +export const ChipDeleteIcon = (props) => ( + + + +); + +const COLORS = ['primary', 'secondary', 'info', 'success', 'warning', 'error']; + +// ---------------------------------------------------------------------- + +function styleColors(ownerState, styles) { + const outputStyle = COLORS.reduce((acc, color) => { + if (!ownerState.disabled && ownerState.color === color) { + acc = styles(color); + } + return acc; + }, {}); + + return outputStyle; +} + +const softVariant = { + colors: COLORS.map((color) => ({ + props: ({ ownerState }) => + !ownerState.disabled && ownerState.variant === 'soft' && ownerState.color === color, + style: ({ theme }) => ({ + color: theme.vars.palette[color].dark, + backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.16), + '&:hover': { backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.32) }, + [stylesMode.dark]: { color: theme.vars.palette[color].light }, + }), + })), + inheritColor: [ + { + props: ({ ownerState }) => ownerState.variant === 'soft' && ownerState.color === 'default', + style: ({ theme }) => ({ + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + '&:hover': { backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.32) }, + }), + }, + ], +}; + +// ---------------------------------------------------------------------- + +const MuiChip = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { deleteIcon: }, + + /** ************************************** + * VARIANTS + *************************************** */ + variants: [ + /** + * @variant soft + */ + ...[...softVariant.inheritColor, ...softVariant.colors], + ], + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ ownerState, theme }) => { + const styled = { + colors: styleColors(ownerState, (color) => ({ + [`& .${chipClasses.avatar}`]: { + color: theme.vars.palette[color].lighter, + backgroundColor: theme.vars.palette[color].dark, + }, + })), + disabled: { + [`&.${chipClasses.disabled}`]: { + opacity: 1, + [`& .${chipClasses.avatar}`]: { + color: theme.vars.palette.action.disabled, + backgroundColor: theme.vars.palette.action.disabledBackground, + }, + ...(ownerState.variant === 'outlined' && { + color: theme.vars.palette.action.disabled, + borderColor: theme.vars.palette.action.disabledBackground, + }), + ...(['filled', 'soft'].includes(ownerState.variant) && { + color: theme.vars.palette.action.disabled, + backgroundColor: theme.vars.palette.action.disabledBackground, + }), + }, + }, + }; + + return { ...styled.colors, ...styled.disabled }; + }, + label: ({ theme }) => ({ fontWeight: theme.typography.fontWeightMedium }), + icon: { color: 'currentColor' }, + deleteIcon: { + opacity: 0.48, + color: 'currentColor', + '&:hover': { opacity: 1, color: 'currentColor' }, + }, + sizeMedium: ({ theme }) => ({ borderRadius: theme.shape.borderRadius * 1.25 }), + sizeSmall: ({ theme }) => ({ borderRadius: theme.shape.borderRadius }), + /** + * @variant filled + */ + filled: ({ ownerState, theme }) => { + const styled = { + defaultColor: { + ...(!ownerState.disabled && + ownerState.color === 'default' && { + color: theme.vars.palette.common.white, + backgroundColor: theme.vars.palette.text.primary, + [`& .${chipClasses.avatar}`]: { color: theme.vars.palette.text.primary }, + '&:hover': { backgroundColor: theme.vars.palette.grey[700] }, + [stylesMode.dark]: { + color: theme.vars.palette.grey[800], + '&:hover': { backgroundColor: theme.vars.palette.grey[100] }, + }, + }), + }, + }; + return { ...styled.defaultColor }; + }, + /** + * @variant outlined + */ + outlined: ({ ownerState, theme }) => { + const styled = { + defaultColor: { + ...(!ownerState.disabled && + ownerState.color === 'default' && { + borderColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.32), + }), + }, + }; + return { ...styled.defaultColor }; + }, + }, +}; + +// ---------------------------------------------------------------------- + +export const chip = { MuiChip }; diff --git a/front_minimal/src/theme/core/components/dialog.jsx b/front_minimal/src/theme/core/components/dialog.jsx new file mode 100644 index 0000000..d474596 --- /dev/null +++ b/front_minimal/src/theme/core/components/dialog.jsx @@ -0,0 +1,62 @@ +// ---------------------------------------------------------------------- + +const MuiDialog = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + paper: ({ ownerState, theme }) => ({ + boxShadow: theme.customShadows.dialog, + borderRadius: theme.shape.borderRadius * 2, + ...(!ownerState.fullScreen && { margin: theme.spacing(2) }), + }), + paperFullScreen: { borderRadius: 0 }, + }, +}; + +const MuiDialogTitle = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { root: ({ theme }) => ({ padding: theme.spacing(3) }) }, +}; + +const MuiDialogContent = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ padding: theme.spacing(0, 3) }), + dividers: ({ theme }) => ({ + borderTop: 0, + borderBottomStyle: 'dashed', + paddingBottom: theme.spacing(3), + }), + }, +}; + +const MuiDialogActions = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { disableSpacing: true }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + padding: theme.spacing(3), + '& > :not(:first-of-type)': { marginLeft: theme.spacing(1.5) }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const dialog = { + MuiDialog, + MuiDialogTitle, + MuiDialogContent, + MuiDialogActions, +}; diff --git a/front_minimal/src/theme/core/components/drawer.jsx b/front_minimal/src/theme/core/components/drawer.jsx new file mode 100644 index 0000000..0d3f667 --- /dev/null +++ b/front_minimal/src/theme/core/components/drawer.jsx @@ -0,0 +1,33 @@ +import { paper, varAlpha, stylesMode } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiDrawer = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + paperAnchorRight: ({ ownerState, theme }) => ({ + ...(ownerState.variant === 'temporary' && { + ...paper({ theme }), + boxShadow: `-40px 40px 80px -8px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.24)}`, + [stylesMode.dark]: { + boxShadow: `-40px 40px 80px -8px ${varAlpha(theme.vars.palette.common.blackChannel, 0.24)}`, + }, + }), + }), + paperAnchorLeft: ({ ownerState, theme }) => ({ + ...(ownerState.variant === 'temporary' && { + ...paper({ theme }), + boxShadow: `40px 40px 80px -8px ${varAlpha(theme.vars.palette.grey['500Channel'], 0.24)}`, + [stylesMode.dark]: { + boxShadow: `40px 40px 80px -8px ${varAlpha(theme.vars.palette.common.blackChannel, 0.24)}`, + }, + }), + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const drawer = { MuiDrawer }; diff --git a/front_minimal/src/theme/core/components/form.jsx b/front_minimal/src/theme/core/components/form.jsx new file mode 100644 index 0000000..de1deb9 --- /dev/null +++ b/front_minimal/src/theme/core/components/form.jsx @@ -0,0 +1,51 @@ +import { inputLabelClasses } from '@mui/material/InputLabel'; + +// ---------------------------------------------------------------------- + +const MuiFormLabel = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + ...theme.typography.body2, + color: theme.vars.palette.text.disabled, + [`&.${inputLabelClasses.shrink}`]: { + ...theme.typography.body1, + fontWeight: 600, + color: theme.vars.palette.text.secondary, + [`&.${inputLabelClasses.focused}`]: { color: theme.vars.palette.text.primary }, + [`&.${inputLabelClasses.error}`]: { color: theme.vars.palette.error.main }, + [`&.${inputLabelClasses.disabled}`]: { color: theme.vars.palette.text.disabled }, + [`&.${inputLabelClasses.filled}`]: { transform: 'translate(12px, 6px) scale(0.75)' }, + }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiFormHelperText = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { component: 'div' }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { root: ({ theme }) => ({ marginTop: theme.spacing(1) }) }, +}; + +// ---------------------------------------------------------------------- + +const MuiFormControlLabel = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { label: ({ theme }) => ({ ...theme.typography.body2 }) }, +}; + +// ---------------------------------------------------------------------- + +export const form = { MuiFormLabel, MuiFormHelperText, MuiFormControlLabel }; diff --git a/front_minimal/src/theme/core/components/index.js b/front_minimal/src/theme/core/components/index.js new file mode 100644 index 0000000..4d572f0 --- /dev/null +++ b/front_minimal/src/theme/core/components/index.js @@ -0,0 +1,91 @@ +import { list } from './list'; +import { card } from './card'; +import { menu } from './menu'; +import { chip } from './chip'; +import { link } from './link'; +import { tabs } from './tabs'; +import { form } from './form'; +import { table } from './table'; +import { alert } from './alert'; +import { stack } from './stack'; +import { paper } from './paper'; +import { badge } from './badge'; +import { radio } from './radio'; +import { appBar } from './appbar'; +import { dialog } from './dialog'; +import { avatar } from './avatar'; +import { drawer } from './drawer'; +import { select } from './select'; +import { rating } from './rating'; +import { slider } from './slider'; +import { button } from './button'; +import { fab } from './button-fab'; +import { tooltip } from './tooltip'; +import { popover } from './popover'; +import { stepper } from './stepper'; +import { switches } from './switch'; +import { svgIcon } from './svg-icon'; +import { skeleton } from './skeleton'; +import { backdrop } from './backdrop'; +import { progress } from './progress'; +import { timeline } from './timeline'; +import { checkbox } from './checkbox'; +import { accordion } from './accordion'; +import { textfield } from './textfield'; +import { typography } from './typography'; +import { pagination } from './pagination'; +import { breadcrumbs } from './breadcrumbs'; +import { dataGrid } from './mui-x-data-grid'; +import { treeView } from './mui-x-tree-view'; +import { buttonGroup } from './button-group'; +import { autocomplete } from './autocomplete'; +import { toggleButton } from './button-toggle'; +import { datePicker } from './mui-x-date-picker'; + +// ---------------------------------------------------------------------- + +export const components = { + ...fab, + ...card, + ...link, + ...form, + ...tabs, + ...chip, + ...menu, + ...list, + ...stack, + ...paper, + ...table, + ...alert, + ...badge, + ...radio, + ...dialog, + ...appBar, + ...avatar, + ...drawer, + ...slider, + ...rating, + ...select, + ...button, + ...stepper, + ...tooltip, + ...popover, + ...svgIcon, + ...skeleton, + ...timeline, + ...backdrop, + ...progress, + ...switches, + ...checkbox, + ...treeView, + ...dataGrid, + ...accordion, + ...textfield, + ...typography, + ...pagination, + ...datePicker, + ...breadcrumbs, + ...buttonGroup, + ...autocomplete, + ...toggleButton, +}; diff --git a/front_minimal/src/theme/core/components/link.jsx b/front_minimal/src/theme/core/components/link.jsx new file mode 100644 index 0000000..5d40589 --- /dev/null +++ b/front_minimal/src/theme/core/components/link.jsx @@ -0,0 +1,17 @@ +// ---------------------------------------------------------------------- + +const MuiLink = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { underline: 'hover' }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: {}, +}; + +// ---------------------------------------------------------------------- + +export const link = { MuiLink }; diff --git a/front_minimal/src/theme/core/components/list.jsx b/front_minimal/src/theme/core/components/list.jsx new file mode 100644 index 0000000..ffe6208 --- /dev/null +++ b/front_minimal/src/theme/core/components/list.jsx @@ -0,0 +1,41 @@ +// ---------------------------------------------------------------------- + +const MuiListItemIcon = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ color: 'inherit', minWidth: 'auto', marginRight: theme.spacing(2) }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiListItemAvatar = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { root: ({ theme }) => ({ minWidth: 'auto', marginRight: theme.spacing(2) }) }, +}; + +// ---------------------------------------------------------------------- + +const MuiListItemText = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { primaryTypographyProps: { typography: 'subtitle2' } }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { root: { margin: 0 }, multiline: { margin: 0 } }, +}; + +// ---------------------------------------------------------------------- + +export const list = { + MuiListItemIcon, + MuiListItemAvatar, + MuiListItemText, +}; diff --git a/front_minimal/src/theme/core/components/menu.jsx b/front_minimal/src/theme/core/components/menu.jsx new file mode 100644 index 0000000..13572ca --- /dev/null +++ b/front_minimal/src/theme/core/components/menu.jsx @@ -0,0 +1,14 @@ +import { menuItem } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiMenuItem = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { root: ({ theme }) => ({ ...menuItem(theme) }) }, +}; + +// ---------------------------------------------------------------------- + +export const menu = { MuiMenuItem }; diff --git a/front_minimal/src/theme/core/components/mui-x-data-grid.jsx b/front_minimal/src/theme/core/components/mui-x-data-grid.jsx new file mode 100644 index 0000000..95c4474 --- /dev/null +++ b/front_minimal/src/theme/core/components/mui-x-data-grid.jsx @@ -0,0 +1,363 @@ +import { listClasses } from '@mui/material/List'; +import { paperClasses } from '@mui/material/Paper'; +import { textFieldClasses } from '@mui/material/TextField'; +import { inputBaseClasses } from '@mui/material/InputBase'; +import { inputLabelClasses } from '@mui/material/InputLabel'; +import { iconButtonClasses } from '@mui/material/IconButton'; +import SvgIcon, { svgIconClasses } from '@mui/material/SvgIcon'; +import { listItemIconClasses } from '@mui/material/ListItemIcon'; +import { circularProgressClasses } from '@mui/material/CircularProgress'; +import { formControlLabelClasses } from '@mui/material/FormControlLabel'; + +import { paper, varAlpha } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiDataGrid = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { + slots: { + /* Column */ + columnSortedAscendingIcon: (props) => ( + + ), + columnSortedDescendingIcon: (props) => ( + + ), + columnUnsortedIcon: (props) => ( + + ), + columnMenuIcon: (props) => , + columnMenuSortAscendingIcon: (props) => , + columnMenuSortDescendingIcon: (props) => , + columnMenuFilterIcon: (props) => , + columnMenuHideIcon: (props) => , + columnMenuManageColumnsIcon: (props) => , + columnSelectorIcon: (props) => , + /* Filter */ + filterPanelDeleteIcon: (props) => , + openFilterButtonIcon: (props) => , + columnFilteredIcon: (props) => ( + + ), + /* Density */ + densityCompactIcon: (props) => , + densityStandardIcon: (props) => , + densityComfortableIcon: (props) => , + /* Export */ + exportIcon: (props) => , + /* Quick Filter */ + quickFilterIcon: (props) => ( + + ), + quickFilterClearIcon: (props) => , + }, + slotProps: { + basePopper: { placement: 'bottom-end' }, + baseChip: { size: 'small' }, + baseSwitch: { size: 'small' }, + baseCheckbox: { size: 'small', disableRipple: true }, + baseInputLabel: { shrink: true }, + baseTextField: { variant: 'outlined' }, + baseSelect: { native: true, variant: 'outlined' }, + }, + }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + '--unstable_DataGrid-radius': 0, + '--DataGrid-rowBorderColor': theme.vars.palette.divider, + '--DataGrid-containerBackground': theme.vars.palette.background.neutral, + '--unstable_DataGrid-headWeight': theme.typography.fontWeightSemiBold, + borderWidth: 0, + scrollbarWidth: 'thin', + scrollbarColor: `${varAlpha(theme.vars.palette.text.disabledChannel, 0.4)} ${varAlpha(theme.vars.palette.text.disabledChannel, 0.08)}`, + '& .MuiDataGrid-filler > div': { borderTopStyle: 'dashed' }, + '& .MuiDataGrid-topContainer::after': { height: 0 }, + }), + withBorderColor: { borderColor: 'var(--DataGrid-rowBorderColor)' }, + /** + * Column + */ + columnHeader: ({ theme }) => ({ + fontSize: 14, + color: theme.vars.palette.text.secondary, + '&--sorted': { color: theme.vars.palette.text.primary }, + }), + columnSeparator: { color: 'var(--DataGrid-rowBorderColor)' }, + /** + * Row, Cell + */ + cell: ({ theme }) => ({ + borderTopStyle: 'dashed', + '&--editing': { + boxShadow: 'none', + backgroundColor: varAlpha(theme.vars.palette.primary.mainChannel, 0.08), + }, + }), + /** + * Toolbar + */ + toolbarContainer: ({ theme }) => ({ + gap: theme.spacing(2), + padding: theme.spacing(2), + [`& .${textFieldClasses.root}`]: { + padding: 0, + width: '100%', + [`& .${inputBaseClasses.input}`]: { + paddingTop: theme.spacing(2), + paddingBottom: theme.spacing(2), + }, + [theme.breakpoints.up('md')]: { width: 'unset' }, + }, + }), + /** + * Paper + */ + paper: ({ theme }) => ({ + ...paper({ theme, dropdown: true }), + padding: 0, + }), + menu: ({ theme }) => ({ + [`& .${paperClasses.root}`]: { + ...paper({ theme, dropdown: true }), + minWidth: 140, + }, + [`& .${listClasses.root}`]: { + padding: 0, + [`& .${listItemIconClasses.root}`]: { + minWidth: 0, + marginRight: theme.spacing(2), + }, + }, + }), + /** + * Icons + */ + menuIcon: ({ theme }) => ({ + [`& .${iconButtonClasses.root}`]: { + margin: theme.spacing(0, 1), + padding: theme.spacing(0.25), + }, + }), + iconButtonContainer: ({ theme }) => ({ + [`& .${iconButtonClasses.root}`]: { + padding: theme.spacing(0.25), + marginLeft: theme.spacing(1), + }, + }), + /** + * Footer + */ + footerContainer: { minHeight: 'auto', borderTopStyle: 'dashed' }, + selectedRowCount: { display: 'none', whiteSpace: 'nowrap' }, + overlay: ({ theme }) => ({ + [`& .${circularProgressClasses.root}`]: { color: theme.vars.palette.text.primary }, + }), + /** + * Column panel + */ + columnsManagementHeader: ({ theme }) => ({ + padding: theme.spacing(2.5, 2, 0, 2), + [`& .${inputBaseClasses.input}`]: { + paddingTop: theme.spacing(2), + paddingBottom: theme.spacing(2), + }, + }), + columnsManagement: ({ theme }) => ({ + gap: theme.spacing(0.5), + padding: theme.spacing(2, 1.5), + [`& .${formControlLabelClasses.root}`]: { gap: 4, marginLeft: 0 }, + }), + columnsManagementFooter: ({ theme }) => ({ + borderTopStyle: 'dashed', + padding: theme.spacing(1.5), + [`& .${formControlLabelClasses.root}`]: { gap: 4, marginLeft: 0 }, + }), + /** + * Filter panel + */ + filterForm: ({ theme }) => ({ + alignItems: 'center', + gap: theme.spacing(1.5), + padding: theme.spacing(2), + /* Fix label with input variant === 'outlined' */ + [`& .${inputLabelClasses.shrink}`]: { transform: 'translate(14px, -9px) scale(0.75)' }, + }), + filterFormDeleteIcon: ({ theme }) => ({ + [`& .${iconButtonClasses.root}`]: { + padding: theme.spacing(0.25), + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + [`& .${svgIconClasses.root}`]: { width: 16, height: 16 }, + }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const dataGrid = { MuiDataGrid }; + +// ---------------------------------------------------------------------- + +/** + * Icons + */ +/* https://icon-sets.iconify.design/solar/alt-arrow-up-bold-duotone */ +export const DataGridArrowUpIcon = ({ ...props }) => ( + + + + +); + +/* https://icon-sets.iconify.design/solar/alt-arrow-down-bold-duotone */ +export const DataGridArrowDownIcon = ({ ...props }) => ( + + + + +); + +/* https://icon-sets.iconify.design/solar/filter-bold */ +export const DataGridFilterIcon = ({ ...props }) => ( + + + +); + +/* https://icon-sets.iconify.design/solar/export-bold */ +export const DataGridExportIcon = ({ ...props }) => ( + + + + +); + +/* https://icon-sets.iconify.design/solar/eye-bold */ +export const DataGridEyeIcon = ({ ...props }) => ( + + + + +); + +/* https://icon-sets.iconify.design/ph/eye-closed-bold */ +export const DataGridEyeCloseIcon = ({ ...props }) => ( + + + +); + +/* https://icon-sets.iconify.design/eva/search-fill */ +export const DataGridSearchIcon = ({ ...props }) => ( + + + +); + +/* https://icon-sets.iconify.design/eva/close-fill */ +export const DataGridCloseIcon = ({ ...props }) => ( + + + +); + +/* https://icon-sets.iconify.design/mingcute/more-1-fill */ +export const DataGridMoreIcon = ({ ...props }) => ( + + + + + + +); + +/* https://icon-sets.iconify.design/material-symbols/table-rows-narrow-rounded */ +export const DataGridDensityCompactIcon = ({ ...props }) => ( + + + +); + +/* https://icon-sets.iconify.design/mingcute/rows-2-fill */ +export const DataGridDensityComfortableIcon = ({ ...props }) => ( + + + + + + +); + +/* https://icon-sets.iconify.design/mingcute/rows-4-fill */ +export const DataGridDensityStandardIcon = ({ ...props }) => ( + + + + + + +); diff --git a/front_minimal/src/theme/core/components/mui-x-date-picker.jsx b/front_minimal/src/theme/core/components/mui-x-date-picker.jsx new file mode 100644 index 0000000..98e4948 --- /dev/null +++ b/front_minimal/src/theme/core/components/mui-x-date-picker.jsx @@ -0,0 +1,210 @@ +import SvgIcon from '@mui/material/SvgIcon'; +import { buttonClasses } from '@mui/material/Button'; +import { dialogActionsClasses } from '@mui/material/DialogActions'; + +import { stylesMode } from '../../styles'; + +// ---------------------------------------------------------------------- + +/** + * Icons + */ +/* https://icon-sets.iconify.design/eva/chevron-down-fill */ +export const PickerSwitchIcon = (props) => ( + + + +); + +/* https://icon-sets.iconify.design/eva/arrow-ios-back-fill */ +export const PickerLeftIcon = (props) => ( + + + +); + +/* https://icon-sets.iconify.design/eva/arrow-ios-forward-fill */ +export const PickerRightIcon = (props) => ( + + + +); + +/* https://icon-sets.iconify.design/solar/calendar-mark-bold-duotone */ +export const PickerCalendarIcon = (props) => ( + + + + + +); + +/* https://icon-sets.iconify.design/solar/clock-circle-outline */ +export const PickerClockIcon = (props) => ( + + + +); + +const defaultProps = { + date: { + openPickerIcon: PickerCalendarIcon, + leftArrowIcon: PickerLeftIcon, + rightArrowIcon: PickerRightIcon, + switchViewIcon: PickerSwitchIcon, + }, + time: { + openPickerIcon: PickerClockIcon, + rightArrowIcon: PickerRightIcon, + switchViewIcon: PickerSwitchIcon, + }, +}; + +const MuiDatePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.date }, +}; + +const MuiDateTimePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.date }, +}; + +const MuiStaticDatePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.date }, +}; + +const MuiDesktopDatePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.date }, +}; + +const MuiDesktopDateTimePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.date }, +}; + +const MuiMobileDatePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.date }, +}; + +const MuiMobileDateTimePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.date }, +}; + +const MuiTimePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.time }, +}; + +const MuiMobileTimePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.time }, +}; + +const MuiStaticTimePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.time }, +}; + +const MuiDesktopTimePicker = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { slots: defaultProps.time }, +}; + +const MuiPickersLayout = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + [`& .${dialogActionsClasses.root}`]: { + [`& .${buttonClasses.root}`]: { + [`&:last-of-type`]: { + color: theme.vars.palette.common.white, + backgroundColor: theme.vars.palette.text.primary, + [stylesMode.dark]: { color: theme.vars.palette.grey[800] }, + }, + }, + }, + }), + }, +}; + +const MuiPickersPopper = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + styleOverrides: { + paper: ({ theme }) => ({ + boxShadow: theme.customShadows.dropdown, + borderRadius: theme.shape.borderRadius * 1.5, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const datePicker = { + MuiPickersPopper, + MuiPickersLayout, + // Date + MuiDatePicker, + MuiDateTimePicker, + MuiStaticDatePicker, + MuiDesktopDatePicker, + MuiDesktopDateTimePicker, + MuiMobileDatePicker, + MuiMobileDateTimePicker, + // Time + MuiTimePicker, + MuiMobileTimePicker, + MuiStaticTimePicker, + MuiDesktopTimePicker, +}; diff --git a/front_minimal/src/theme/core/components/mui-x-tree-view.jsx b/front_minimal/src/theme/core/components/mui-x-tree-view.jsx new file mode 100644 index 0000000..213fa38 --- /dev/null +++ b/front_minimal/src/theme/core/components/mui-x-tree-view.jsx @@ -0,0 +1,15 @@ +// ---------------------------------------------------------------------- + +const MuiTreeItem = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + label: ({ theme }) => ({ ...theme.typography.body2 }), + iconContainer: { width: 'auto' }, + }, +}; + +// ---------------------------------------------------------------------- + +export const treeView = { MuiTreeItem }; diff --git a/front_minimal/src/theme/core/components/pagination.jsx b/front_minimal/src/theme/core/components/pagination.jsx new file mode 100644 index 0000000..002e87a --- /dev/null +++ b/front_minimal/src/theme/core/components/pagination.jsx @@ -0,0 +1,97 @@ +import { paginationItemClasses } from '@mui/material/PaginationItem'; + +import { varAlpha, stylesMode } from '../../styles'; + +const COLORS = ['primary', 'secondary', 'info', 'success', 'warning', 'error']; + +// ---------------------------------------------------------------------- + +const softVariant = { + colors: COLORS.map((color) => ({ + props: ({ ownerState }) => + !ownerState.disabled && ownerState.variant === 'soft' && ownerState.color === color, + style: ({ theme }) => ({ + [`& .${paginationItemClasses.root}`]: { + [`&.${paginationItemClasses.selected}`]: { + fontWeight: theme.typography.fontWeightSemiBold, + color: theme.vars.palette[color].dark, + backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.08), + '&:hover': { backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.16) }, + [stylesMode.dark]: { color: theme.vars.palette[color].light }, + }, + }, + }), + })), + standardColor: [ + { + props: ({ ownerState }) => ownerState.variant === 'soft' && ownerState.color === 'standard', + style: ({ theme }) => ({ + [`& .${paginationItemClasses.root}`]: { + [`&.${paginationItemClasses.selected}`]: { + fontWeight: theme.typography.fontWeightSemiBold, + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + '&:hover': { backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.16) }, + }, + }, + }), + }, + ], +}; + +// ---------------------------------------------------------------------- + +const MuiPagination = { + /** ************************************** + * VARIANTS + *************************************** */ + variants: [ + /** + * @variant soft + */ + ...[...softVariant.standardColor, ...softVariant.colors], + ], + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + /** + * @variant text + */ + text: ({ ownerState, theme }) => ({ + [`& .${paginationItemClasses.root}`]: { + [`&.${paginationItemClasses.selected}`]: { + fontWeight: theme.typography.fontWeightSemiBold, + ...(ownerState.color === 'standard' && { + color: theme.vars.palette.common.white, + backgroundColor: theme.vars.palette.text.primary, + '&:hover': { backgroundColor: theme.vars.palette.grey[700] }, + [stylesMode.dark]: { + color: theme.vars.palette.grey[800], + '&:hover': { backgroundColor: theme.vars.palette.grey[100] }, + }, + }), + }, + }, + }), + /** + * @variant outlined + */ + outlined: ({ ownerState, theme }) => ({ + [`& .${paginationItemClasses.root}`]: { + borderColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.24), + [`&.${paginationItemClasses.selected}`]: { + borderColor: 'currentColor', + fontWeight: theme.typography.fontWeightSemiBold, + ...(ownerState.color === 'standard' && { + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + }), + }, + }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const pagination = { MuiPagination }; diff --git a/front_minimal/src/theme/core/components/paper.jsx b/front_minimal/src/theme/core/components/paper.jsx new file mode 100644 index 0000000..1c81234 --- /dev/null +++ b/front_minimal/src/theme/core/components/paper.jsx @@ -0,0 +1,24 @@ +import { varAlpha } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiPaper = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { elevation: 0 }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: { backgroundImage: 'none' }, + outlined: ({ theme }) => ({ + borderColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const paper = { MuiPaper }; diff --git a/front_minimal/src/theme/core/components/popover.jsx b/front_minimal/src/theme/core/components/popover.jsx new file mode 100644 index 0000000..ba1c7e7 --- /dev/null +++ b/front_minimal/src/theme/core/components/popover.jsx @@ -0,0 +1,21 @@ +import { listClasses } from '@mui/material/List'; + +import { paper } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiPopover = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + paper: ({ theme }) => ({ + ...paper({ theme, dropdown: true }), + [`& .${listClasses.root}`]: { paddingTop: 0, paddingBottom: 0 }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const popover = { MuiPopover }; diff --git a/front_minimal/src/theme/core/components/progress.jsx b/front_minimal/src/theme/core/components/progress.jsx new file mode 100644 index 0000000..ec53fdc --- /dev/null +++ b/front_minimal/src/theme/core/components/progress.jsx @@ -0,0 +1,48 @@ +import { varAlpha } from '../../styles'; + +// ---------------------------------------------------------------------- + +const COLORS = ['primary', 'secondary', 'info', 'success', 'warning', 'error']; + +// ---------------------------------------------------------------------- + +function styleColors(ownerState, styles) { + const outputStyle = COLORS.reduce((acc, color) => { + if (ownerState.color === color) { + acc = styles(color); + } + return acc; + }, {}); + + return outputStyle; +} + +const MuiLinearProgress = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme, ownerState }) => { + const styled = { + colors: styleColors(ownerState, (color) => ({ + backgroundColor: varAlpha(theme.vars.palette[color].mainChannel, 0.24), + })), + inheritColor: { + ...(ownerState.color === 'inherit' && { + '&::before': { display: 'none' }, + backgroundColor: varAlpha(theme.vars.palette.text.primaryChannel, 0.24), + }), + }, + }; + return { + borderRadius: 4, + ...(ownerState.variant !== 'buffer' && { ...styled.inheritColor, ...styled.colors }), + }; + }, + bar: { borderRadius: 'inherit' }, + }, +}; + +// ---------------------------------------------------------------------- + +export const progress = { MuiLinearProgress }; diff --git a/front_minimal/src/theme/core/components/radio.jsx b/front_minimal/src/theme/core/components/radio.jsx new file mode 100644 index 0000000..6df4214 --- /dev/null +++ b/front_minimal/src/theme/core/components/radio.jsx @@ -0,0 +1,57 @@ +import SvgIcon from '@mui/material/SvgIcon'; +import { radioClasses } from '@mui/material/Radio'; + +// ---------------------------------------------------------------------- + +/** + * Icons + */ +export const RadioIcon = (props) => ( + + + +); + +export const RadioCheckedIcon = (props) => ( + + + +); + +// ---------------------------------------------------------------------- + +const MuiRadio = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { + size: 'small', + icon: , + checkedIcon: , + }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ ownerState, theme }) => ({ + padding: theme.spacing(1), + ...(ownerState.color === 'default' && { + [`&.${radioClasses.checked}`]: { color: theme.vars.palette.text.primary }, + }), + [`&.${radioClasses.disabled}`]: { color: theme.vars.palette.action.disabled }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const radio = { MuiRadio }; diff --git a/front_minimal/src/theme/core/components/rating.jsx b/front_minimal/src/theme/core/components/rating.jsx new file mode 100644 index 0000000..5da14f6 --- /dev/null +++ b/front_minimal/src/theme/core/components/rating.jsx @@ -0,0 +1,39 @@ +import { ratingClasses } from '@mui/material/Rating'; +import SvgIcon, { svgIconClasses } from '@mui/material/SvgIcon'; + +import { varAlpha } from '../../styles'; + +// ---------------------------------------------------------------------- + +/** + * Icons + */ +export const RatingIcon = (props) => ( + + + +); + +// ---------------------------------------------------------------------- + +const MuiRating = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { emptyIcon: , icon: }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: { [`&.${ratingClasses.disabled}`]: { opacity: 0.48 } }, + iconEmpty: ({ theme }) => ({ color: varAlpha(theme.vars.palette.grey['500Channel'], 0.48) }), + sizeSmall: { [`& .${svgIconClasses.root}`]: { width: 20, height: 20 } }, + sizeMedium: { [`& .${svgIconClasses.root}`]: { width: 24, height: 24 } }, + sizeLarge: { [`& .${svgIconClasses.root}`]: { width: 28, height: 28 } }, + }, +}; + +// ---------------------------------------------------------------------- + +export const rating = { MuiRating }; diff --git a/front_minimal/src/theme/core/components/select.jsx b/front_minimal/src/theme/core/components/select.jsx new file mode 100644 index 0000000..2c1dfc5 --- /dev/null +++ b/front_minimal/src/theme/core/components/select.jsx @@ -0,0 +1,62 @@ +import SvgIcon from '@mui/material/SvgIcon'; + +// ---------------------------------------------------------------------- + +/** + * Icons + * https://icon-sets.iconify.design/eva/arrow-ios-downward-fill/ + */ +const ArrowDownIcon = (props) => ( + + + +); + +// ---------------------------------------------------------------------- + +const MuiSelect = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { IconComponent: ArrowDownIcon }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + icon: { + right: 10, + width: 18, + height: 18, + top: 'calc(50% - 9px)', + }, + }, +}; + +// ---------------------------------------------------------------------- + +const MuiNativeSelect = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { IconComponent: ArrowDownIcon }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + icon: { + right: 10, + width: 18, + height: 18, + top: 'calc(50% - 9px)', + }, + }, +}; + +// ---------------------------------------------------------------------- + +export const select = { MuiSelect, MuiNativeSelect }; diff --git a/front_minimal/src/theme/core/components/skeleton.jsx b/front_minimal/src/theme/core/components/skeleton.jsx new file mode 100644 index 0000000..98db047 --- /dev/null +++ b/front_minimal/src/theme/core/components/skeleton.jsx @@ -0,0 +1,24 @@ +import { varAlpha } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiSkeleton = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { animation: 'wave', variant: 'rounded' }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + backgroundColor: varAlpha(theme.vars.palette.grey['400Channel'], 0.12), + }), + rounded: ({ theme }) => ({ borderRadius: theme.shape.borderRadius * 2 }), + }, +}; + +// ---------------------------------------------------------------------- + +export const skeleton = { MuiSkeleton }; diff --git a/front_minimal/src/theme/core/components/slider.jsx b/front_minimal/src/theme/core/components/slider.jsx new file mode 100644 index 0000000..f26673c --- /dev/null +++ b/front_minimal/src/theme/core/components/slider.jsx @@ -0,0 +1,112 @@ +import { sliderClasses } from '@mui/material/Slider'; + +import { varAlpha, stylesMode } from '../../styles'; + +// ---------------------------------------------------------------------- + +const SIZE = { + rail: { small: 6, medium: 10 }, + thumb: { small: 16, medium: 20 }, + mark: { small: 4, medium: 6 }, +}; + +const MuiSlider = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { size: 'small' }, + + /** ************************************** + * VARIANTS + *************************************** */ + variants: [ + /** + * @color inherit + */ + { + props: ({ ownerState }) => ownerState.color === 'inherit', + style: ({ theme }) => ({ + [`& .${sliderClasses.markActive}`]: { + [stylesMode.dark]: { + backgroundColor: varAlpha(theme.vars.palette.grey['800Channel'], 0.48), + }, + }, + }), + }, + /** + * @state disabled + */ + { + props: ({ ownerState }) => !!ownerState.disabled, + style: ({ theme }) => ({ + [`&.${sliderClasses.disabled}`]: { + color: varAlpha( + theme.vars.palette.grey['500Channel'], + theme.vars.palette.action.disabledOpacity + ), + }, + }), + }, + ], + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + [`& .${sliderClasses.thumb}`]: { + borderWidth: 1, + borderStyle: 'solid', + width: SIZE.thumb.medium, + height: SIZE.thumb.medium, + boxShadow: theme.customShadows.z1, + color: theme.vars.palette.common.white, + borderColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + '&::before': { + opacity: 0.4, + boxShadow: 'none', + width: 'calc(100% - 4px)', + height: 'calc(100% - 4px)', + backgroundImage: `linear-gradient(180deg, ${theme.vars.palette.grey[500]} 0%, ${varAlpha(theme.vars.palette.grey['500Channel'], 0)} 100%)`, + [stylesMode.dark]: { opacity: 0.8 }, + }, + }, + }), + rail: ({ theme }) => ({ + opacity: 0.12, + height: SIZE.rail.medium, + backgroundColor: theme.vars.palette.grey[500], + }), + track: { height: SIZE.rail.medium }, + mark: ({ theme }) => ({ + width: 1, + height: SIZE.mark.medium, + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.48), + '&[data-index="0"]': { display: 'none' }, + }), + markActive: ({ theme }) => ({ + backgroundColor: varAlpha(theme.vars.palette.common.whiteChannel, 0.64), + }), + markLabel: ({ theme }) => ({ + fontSize: theme.typography.pxToRem(13), + color: theme.vars.palette.text.disabled, + }), + valueLabel: ({ theme }) => ({ + borderRadius: 8, + backgroundColor: theme.vars.palette.grey[800], + [stylesMode.dark]: { backgroundColor: theme.vars.palette.grey[700] }, + }), + sizeSmall: { + [`& .${sliderClasses.thumb}`]: { width: SIZE.thumb.small, height: SIZE.thumb.small }, + [`& .${sliderClasses.rail}`]: { height: SIZE.rail.small }, + [`& .${sliderClasses.track}`]: { height: SIZE.rail.small }, + [`& .${sliderClasses.mark}`]: { height: SIZE.mark.small }, + }, + }, +}; + +// ---------------------------------------------------------------------- + +export const slider = { + MuiSlider, +}; diff --git a/front_minimal/src/theme/core/components/stack.jsx b/front_minimal/src/theme/core/components/stack.jsx new file mode 100644 index 0000000..63b0c7e --- /dev/null +++ b/front_minimal/src/theme/core/components/stack.jsx @@ -0,0 +1,16 @@ +// ---------------------------------------------------------------------- + +const MuiStack = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { useFlexGap: true }, + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: {}, +}; + +// ---------------------------------------------------------------------- + +export const stack = { MuiStack }; diff --git a/front_minimal/src/theme/core/components/stepper.jsx b/front_minimal/src/theme/core/components/stepper.jsx new file mode 100644 index 0000000..f81a6ff --- /dev/null +++ b/front_minimal/src/theme/core/components/stepper.jsx @@ -0,0 +1,12 @@ +// ---------------------------------------------------------------------- + +const MuiStepConnector = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { line: ({ theme }) => ({ borderColor: theme.vars.palette.divider }) }, +}; + +// ---------------------------------------------------------------------- + +export const stepper = { MuiStepConnector }; diff --git a/front_minimal/src/theme/core/components/svg-icon.jsx b/front_minimal/src/theme/core/components/svg-icon.jsx new file mode 100644 index 0000000..7a2a703 --- /dev/null +++ b/front_minimal/src/theme/core/components/svg-icon.jsx @@ -0,0 +1,12 @@ +// ---------------------------------------------------------------------- + +const MuiSvgIcon = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { fontSizeLarge: { width: 32, height: 32, fontSize: 'inherit' } }, +}; + +// ---------------------------------------------------------------------- + +export const svgIcon = { MuiSvgIcon }; diff --git a/front_minimal/src/theme/core/components/switch.jsx b/front_minimal/src/theme/core/components/switch.jsx new file mode 100644 index 0000000..69e1348 --- /dev/null +++ b/front_minimal/src/theme/core/components/switch.jsx @@ -0,0 +1,53 @@ +import { switchClasses } from '@mui/material/Switch'; + +import { varAlpha, stylesMode } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiSwitch = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: { alignItems: 'center' }, + switchBase: ({ ownerState, theme }) => ({ + top: 'unset', + transform: 'translateX(6px)', + [`&.${switchClasses.checked}`]: { + [`& .${switchClasses.thumb}`]: { + ...(ownerState.color === 'default' && { + [stylesMode.dark]: { color: theme.vars.palette.grey[800] }, + }), + }, + [`&+.${switchClasses.track}`]: { + opacity: 1, + ...(ownerState.color === 'default' && { + backgroundColor: theme.vars.palette.text.primary, + }), + }, + }, + [`&.${switchClasses.disabled}`]: { + [`& .${switchClasses.thumb}`]: { opacity: 1, [stylesMode.dark]: { opacity: 0.48 } }, + [`&+.${switchClasses.track}`]: { opacity: 0.48 }, + }, + }), + track: ({ theme }) => ({ + opacity: 1, + borderRadius: 10, + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.48), + }), + thumb: ({ theme }) => ({ color: theme.vars.palette.common.white }), + sizeMedium: { + [`& .${switchClasses.track}`]: { height: 20 }, + [`& .${switchClasses.thumb}`]: { width: 14, height: 14 }, + }, + sizeSmall: { + [`& .${switchClasses.track}`]: { height: 16 }, + [`& .${switchClasses.thumb}`]: { width: 10, height: 10 }, + }, + }, +}; + +// ---------------------------------------------------------------------- + +export const switches = { MuiSwitch }; diff --git a/front_minimal/src/theme/core/components/table.jsx b/front_minimal/src/theme/core/components/table.jsx new file mode 100644 index 0000000..13b7c70 --- /dev/null +++ b/front_minimal/src/theme/core/components/table.jsx @@ -0,0 +1,111 @@ +import { tableRowClasses } from '@mui/material/TableRow'; +import { tableCellClasses } from '@mui/material/TableCell'; + +import { varAlpha } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiTableContainer = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + position: 'relative', + scrollbarWidth: 'thin', + scrollbarColor: `${varAlpha(theme.vars.palette.text.disabledChannel, 0.4)} ${varAlpha(theme.vars.palette.text.disabledChannel, 0.08)}`, + }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiTable = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ '--palette-TableCell-border': theme.vars.palette.divider }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiTableRow = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + [`&.${tableRowClasses.selected}`]: { + backgroundColor: varAlpha(theme.vars.palette.primary.darkChannel, 0.04), + '&:hover': { backgroundColor: varAlpha(theme.vars.palette.primary.darkChannel, 0.08) }, + }, + '&:last-of-type': { [`& .${tableCellClasses.root}`]: { borderColor: 'transparent' } }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiTableCell = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: { borderBottomStyle: 'dashed' }, + head: ({ theme }) => ({ + fontSize: 14, + color: theme.vars.palette.text.secondary, + fontWeight: theme.typography.fontWeightSemiBold, + backgroundColor: theme.vars.palette.background.neutral, + }), + stickyHeader: ({ theme }) => ({ + backgroundColor: theme.vars.palette.background.paper, + backgroundImage: `linear-gradient(to bottom, ${theme.vars.palette.background.neutral} 0%, ${theme.vars.palette.background.neutral} 100%)`, + }), + paddingCheckbox: ({ theme }) => ({ paddingLeft: theme.spacing(1) }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiTablePagination = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { + backIconButtonProps: { size: 'small' }, + nextIconButtonProps: { size: 'small' }, + slotProps: { select: { name: 'table-pagination-select' } }, + }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: { width: '100%' }, + toolbar: { height: 64 }, + actions: { marginRight: 8 }, + select: ({ theme }) => ({ + paddingLeft: 8, + '&:focus': { borderRadius: theme.shape.borderRadius }, + }), + selectIcon: { + right: 4, + width: 16, + height: 16, + top: 'calc(50% - 8px)', + }, + }, +}; + +// ---------------------------------------------------------------------- + +export const table = { + MuiTable, + MuiTableRow, + MuiTableCell, + MuiTableContainer, + MuiTablePagination, +}; diff --git a/front_minimal/src/theme/core/components/tabs.jsx b/front_minimal/src/theme/core/components/tabs.jsx new file mode 100644 index 0000000..aa52cbb --- /dev/null +++ b/front_minimal/src/theme/core/components/tabs.jsx @@ -0,0 +1,61 @@ +import { tabClasses } from '@mui/material/Tab'; + +// ---------------------------------------------------------------------- + +const MuiTabs = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { + textColor: 'inherit', + variant: 'scrollable', + allowScrollButtonsMobile: true, + }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + flexContainer: ({ ownerState, theme }) => ({ + ...(ownerState.variant !== 'fullWidth' && { + gap: '24px', + [theme.breakpoints.up('sm')]: { + gap: '40px', + }, + }), + }), + indicator: { backgroundColor: 'currentColor' }, + }, +}; + +// ---------------------------------------------------------------------- + +const MuiTab = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { disableRipple: true, iconPosition: 'start' }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + opacity: 1, + minWidth: 48, + minHeight: 48, + padding: theme.spacing(1, 0), + color: theme.vars.palette.text.secondary, + fontWeight: theme.typography.fontWeightMedium, + lineHeight: theme.typography.body2.lineHeight, + [`&.${tabClasses.selected}`]: { + color: theme.vars.palette.text.primary, + fontWeight: theme.typography.fontWeightSemiBold, + }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const tabs = { MuiTabs, MuiTab }; diff --git a/front_minimal/src/theme/core/components/textfield.jsx b/front_minimal/src/theme/core/components/textfield.jsx new file mode 100644 index 0000000..7d074fd --- /dev/null +++ b/front_minimal/src/theme/core/components/textfield.jsx @@ -0,0 +1,119 @@ +import { inputBaseClasses } from '@mui/material/InputBase'; +import { filledInputClasses } from '@mui/material/FilledInput'; +import { outlinedInputClasses } from '@mui/material/OutlinedInput'; + +import { varAlpha } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiInputBase = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + [`&.${inputBaseClasses.disabled}`]: { + '& svg': { color: theme.vars.palette.text.disabled }, + }, + }), + input: ({ theme }) => ({ + fontSize: theme.typography.pxToRem(15), + [theme.breakpoints.down('sm')]: { + // This will prevent zoom in Safari min font size ~ 16px + fontSize: theme.typography.pxToRem(16), + }, + '&::placeholder': { + opacity: 1, + color: theme.vars.palette.text.disabled, + }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiInput = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + underline: ({ theme }) => ({ + '&::before': { borderBottomColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.32) }, + '&::after': { borderBottomColor: theme.vars.palette.text.primary }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiOutlinedInput = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + [`&.${outlinedInputClasses.focused}`]: { + [`& .${outlinedInputClasses.notchedOutline}`]: { + borderColor: theme.vars.palette.text.primary, + }, + }, + [`&.${outlinedInputClasses.error}`]: { + [`& .${outlinedInputClasses.notchedOutline}`]: { + borderColor: theme.vars.palette.error.main, + }, + }, + [`&.${outlinedInputClasses.disabled}`]: { + [`& .${outlinedInputClasses.notchedOutline}`]: { + borderColor: theme.vars.palette.action.disabledBackground, + }, + }, + }), + notchedOutline: ({ theme }) => ({ + borderColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.2), + transition: theme.transitions.create(['border-color'], { + duration: theme.transitions.duration.shortest, + }), + }), + }, +}; + +// ---------------------------------------------------------------------- + +const MuiFilledInput = { + /** ************************************** + * DEFAULT PROPS + *************************************** */ + defaultProps: { disableUnderline: true }, + + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + root: ({ theme }) => ({ + borderRadius: theme.shape.borderRadius, + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.08), + '&:hover': { backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.16) }, + [`&.${filledInputClasses.focused}`]: { + backgroundColor: varAlpha(theme.vars.palette.grey['500Channel'], 0.16), + }, + [`&.${filledInputClasses.error}`]: { + backgroundColor: varAlpha(theme.vars.palette.error.mainChannel, 0.08), + [`&.${filledInputClasses.focused}`]: { + backgroundColor: varAlpha(theme.vars.palette.error.mainChannel, 0.16), + }, + }, + [`&.${filledInputClasses.disabled}`]: { + backgroundColor: theme.vars.palette.action.disabledBackground, + }, + }), + }, +}; + +// ---------------------------------------------------------------------- + +export const textfield = { + MuiInput, + MuiInputBase, + MuiFilledInput, + MuiOutlinedInput, +}; diff --git a/front_minimal/src/theme/core/components/timeline.jsx b/front_minimal/src/theme/core/components/timeline.jsx new file mode 100644 index 0000000..48cef4f --- /dev/null +++ b/front_minimal/src/theme/core/components/timeline.jsx @@ -0,0 +1,19 @@ +// ---------------------------------------------------------------------- + +const MuiTimelineDot = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { root: { boxShadow: 'none' } }, +}; + +const MuiTimelineConnector = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { root: ({ theme }) => ({ backgroundColor: theme.vars.palette.divider }) }, +}; + +// ---------------------------------------------------------------------- + +export const timeline = { MuiTimelineDot, MuiTimelineConnector }; diff --git a/front_minimal/src/theme/core/components/tooltip.jsx b/front_minimal/src/theme/core/components/tooltip.jsx new file mode 100644 index 0000000..7660cc7 --- /dev/null +++ b/front_minimal/src/theme/core/components/tooltip.jsx @@ -0,0 +1,43 @@ +import { tooltipClasses } from '@mui/material/Tooltip'; + +import { stylesMode } from '../../styles'; + +// ---------------------------------------------------------------------- + +const MuiTooltip = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + tooltip: ({ theme }) => ({ + backgroundColor: theme.vars.palette.grey[800], + [stylesMode.dark]: { + backgroundColor: theme.vars.palette.grey[700], + }, + }), + arrow: ({ theme }) => ({ + color: theme.vars.palette.grey[800], + [stylesMode.dark]: { + color: theme.vars.palette.grey[700], + }, + }), + popper: { + [`&.${tooltipClasses.popper}[data-popper-placement*="bottom"] .${tooltipClasses.tooltip}`]: { + marginTop: 12, + }, + [`&.${tooltipClasses.popper}[data-popper-placement*="top"] .${tooltipClasses.tooltip}`]: { + marginBottom: 12, + }, + [`&.${tooltipClasses.popper}[data-popper-placement*="right"] .${tooltipClasses.tooltip}`]: { + marginLeft: 12, + }, + [`&.${tooltipClasses.popper}[data-popper-placement*="left"] .${tooltipClasses.tooltip}`]: { + marginRight: 12, + }, + }, + }, +}; + +// ---------------------------------------------------------------------- + +export const tooltip = { MuiTooltip }; diff --git a/front_minimal/src/theme/core/components/typography.jsx b/front_minimal/src/theme/core/components/typography.jsx new file mode 100644 index 0000000..37a8afb --- /dev/null +++ b/front_minimal/src/theme/core/components/typography.jsx @@ -0,0 +1,15 @@ +// ---------------------------------------------------------------------- + +const MuiTypography = { + /** ************************************** + * STYLE + *************************************** */ + styleOverrides: { + paragraph: ({ theme }) => ({ marginBottom: theme.spacing(2) }), + gutterBottom: ({ theme }) => ({ marginBottom: theme.spacing(1) }), + }, +}; + +// ---------------------------------------------------------------------- + +export const typography = { MuiTypography }; diff --git a/front_minimal/src/theme/core/custom-shadows.js b/front_minimal/src/theme/core/custom-shadows.js new file mode 100644 index 0000000..67f6bfc --- /dev/null +++ b/front_minimal/src/theme/core/custom-shadows.js @@ -0,0 +1,39 @@ +import { varAlpha } from '../styles'; +import { grey, info, error, common, primary, success, warning, secondary } from './palette'; + +// ---------------------------------------------------------------------- + +export function createShadowColor(colorChannel) { + return `0 8px 16px 0 ${varAlpha(colorChannel, 0.24)}`; +} + +export function customShadows(colorScheme) { + const colorChannel = colorScheme === 'light' ? grey['500Channel'] : common.blackChannel; + + return { + z1: `0 1px 2px 0 ${varAlpha(colorChannel, 0.16)}`, + z4: `0 4px 8px 0 ${varAlpha(colorChannel, 0.16)}`, + z8: `0 8px 16px 0 ${varAlpha(colorChannel, 0.16)}`, + z12: `0 12px 24px -4px ${varAlpha(colorChannel, 0.16)}`, + z16: `0 16px 32px -4px ${varAlpha(colorChannel, 0.16)}`, + z20: `0 20px 40px -4px ${varAlpha(colorChannel, 0.16)}`, + z24: `0 24px 48px 0 ${varAlpha(colorChannel, 0.16)}`, + // + dialog: `-40px 40px 80px -8px ${varAlpha(common.blackChannel, 0.24)}`, + card: `0 0 2px 0 ${varAlpha( + colorChannel, + 0.2 + )}, 0 12px 24px -4px ${varAlpha(colorChannel, 0.12)}`, + dropdown: `0 0 2px 0 ${varAlpha( + colorChannel, + 0.24 + )}, -20px 20px 40px -4px ${varAlpha(colorChannel, 0.24)}`, + // + primary: createShadowColor(primary.mainChannel), + secondary: createShadowColor(secondary.mainChannel), + info: createShadowColor(info.mainChannel), + success: createShadowColor(success.mainChannel), + warning: createShadowColor(warning.mainChannel), + error: createShadowColor(error.mainChannel), + }; +} diff --git a/front_minimal/src/theme/core/index.js b/front_minimal/src/theme/core/index.js new file mode 100644 index 0000000..1f6edd4 --- /dev/null +++ b/front_minimal/src/theme/core/index.js @@ -0,0 +1,9 @@ +export * from './shadows'; + +export * from './palette'; + +export * from './typography'; + +export * from './components'; + +export * from './custom-shadows'; diff --git a/front_minimal/src/theme/core/palette.js b/front_minimal/src/theme/core/palette.js new file mode 100644 index 0000000..56d5868 --- /dev/null +++ b/front_minimal/src/theme/core/palette.js @@ -0,0 +1,109 @@ +import COLORS from './colors.json'; +import { varAlpha, createPaletteChannel } from '../styles'; + +// ---------------------------------------------------------------------- + +// Grey +export const grey = createPaletteChannel(COLORS.grey); + +// Primary +export const primary = createPaletteChannel(COLORS.primary); + +// Secondary +export const secondary = createPaletteChannel(COLORS.secondary); + +// Info +export const info = createPaletteChannel(COLORS.info); + +// Success +export const success = createPaletteChannel(COLORS.success); + +// Warning +export const warning = createPaletteChannel(COLORS.warning); + +// Error +export const error = createPaletteChannel(COLORS.error); + +// Common +export const common = createPaletteChannel(COLORS.common); + +// Text +export const text = { + light: createPaletteChannel({ + primary: grey[800], + secondary: grey[600], + disabled: grey[500], + }), + dark: createPaletteChannel({ + primary: '#FFFFFF', + secondary: grey[500], + disabled: grey[600], + }), +}; + +// Background +export const background = { + light: createPaletteChannel({ + paper: '#FFFFFF', + default: '#FFFFFF', + neutral: grey[200], + }), + dark: createPaletteChannel({ + paper: grey[800], + default: grey[900], + neutral: '#28323D', + }), +}; + +// Action +export const baseAction = { + hover: varAlpha(grey['500Channel'], 0.08), + selected: varAlpha(grey['500Channel'], 0.16), + focus: varAlpha(grey['500Channel'], 0.24), + disabled: varAlpha(grey['500Channel'], 0.8), + disabledBackground: varAlpha(grey['500Channel'], 0.24), + hoverOpacity: 0.08, + disabledOpacity: 0.48, +}; + +export const action = { + light: { ...baseAction, active: grey[600] }, + dark: { ...baseAction, active: grey[500] }, +}; + +/* + * Base palette + */ +export const basePalette = { + primary, + secondary, + info, + success, + warning, + error, + grey, + common, + divider: varAlpha(grey['500Channel'], 0.2), + action, +}; + +export const lightPalette = { + ...basePalette, + text: text.light, + background: background.light, + action: action.light, +}; + +export const darkPalette = { + ...basePalette, + text: text.dark, + background: background.dark, + action: action.dark, +}; + +// ---------------------------------------------------------------------- + +export const colorSchemes = { + light: { palette: lightPalette }, + dark: { palette: darkPalette }, +}; diff --git a/front_minimal/src/theme/core/shadows.js b/front_minimal/src/theme/core/shadows.js new file mode 100644 index 0000000..60c4eb6 --- /dev/null +++ b/front_minimal/src/theme/core/shadows.js @@ -0,0 +1,40 @@ +import { varAlpha } from '../styles'; +import { grey, common } from './palette'; + +// ---------------------------------------------------------------------- + +export function shadows(colorScheme) { + const colorChannel = colorScheme === 'light' ? grey['500Channel'] : common.blackChannel; + + const color1 = varAlpha(colorChannel, 0.2); + const color2 = varAlpha(colorChannel, 0.14); + const color3 = varAlpha(colorChannel, 0.12); + + return [ + 'none', + `0px 2px 1px -1px ${color1},0px 1px 1px 0px ${color2},0px 1px 3px 0px ${color3}`, + `0px 3px 1px -2px ${color1},0px 2px 2px 0px ${color2},0px 1px 5px 0px ${color3}`, + `0px 3px 3px -2px ${color1},0px 3px 4px 0px ${color2},0px 1px 8px 0px ${color3}`, + `0px 2px 4px -1px ${color1},0px 4px 5px 0px ${color2},0px 1px 10px 0px ${color3}`, + `0px 3px 5px -1px ${color1},0px 5px 8px 0px ${color2},0px 1px 14px 0px ${color3}`, + `0px 3px 5px -1px ${color1},0px 6px 10px 0px ${color2},0px 1px 18px 0px ${color3}`, + `0px 4px 5px -2px ${color1},0px 7px 10px 1px ${color2},0px 2px 16px 1px ${color3}`, + `0px 5px 5px -3px ${color1},0px 8px 10px 1px ${color2},0px 3px 14px 2px ${color3}`, + `0px 5px 6px -3px ${color1},0px 9px 12px 1px ${color2},0px 3px 16px 2px ${color3}`, + `0px 6px 6px -3px ${color1},0px 10px 14px 1px ${color2},0px 4px 18px 3px ${color3}`, + `0px 6px 7px -4px ${color1},0px 11px 15px 1px ${color2},0px 4px 20px 3px ${color3}`, + `0px 7px 8px -4px ${color1},0px 12px 17px 2px ${color2},0px 5px 22px 4px ${color3}`, + `0px 7px 8px -4px ${color1},0px 13px 19px 2px ${color2},0px 5px 24px 4px ${color3}`, + `0px 7px 9px -4px ${color1},0px 14px 21px 2px ${color2},0px 5px 26px 4px ${color3}`, + `0px 8px 9px -5px ${color1},0px 15px 22px 2px ${color2},0px 6px 28px 5px ${color3}`, + `0px 8px 10px -5px ${color1},0px 16px 24px 2px ${color2},0px 6px 30px 5px ${color3}`, + `0px 8px 11px -5px ${color1},0px 17px 26px 2px ${color2},0px 6px 32px 5px ${color3}`, + `0px 9px 11px -5px ${color1},0px 18px 28px 2px ${color2},0px 7px 34px 6px ${color3}`, + `0px 9px 12px -6px ${color1},0px 19px 29px 2px ${color2},0px 7px 36px 6px ${color3}`, + `0px 10px 13px -6px ${color1},0px 20px 31px 3px ${color2},0px 8px 38px 7px ${color3}`, + `0px 10px 13px -6px ${color1},0px 21px 33px 3px ${color2},0px 8px 40px 7px ${color3}`, + `0px 10px 14px -6px ${color1},0px 22px 35px 3px ${color2},0px 8px 42px 7px ${color3}`, + `0px 11px 14px -7px ${color1},0px 23px 36px 3px ${color2},0px 9px 44px 8px ${color3}`, + `0px 11px 15px -7px ${color1},0px 24px 38px 3px ${color2},0px 9px 46px 8px ${color3}`, + ]; +} diff --git a/front_minimal/src/theme/core/typography.js b/front_minimal/src/theme/core/typography.js new file mode 100644 index 0000000..62ad7a0 --- /dev/null +++ b/front_minimal/src/theme/core/typography.js @@ -0,0 +1,94 @@ +import { setFont, pxToRem, responsiveFontSizes } from '../styles/utils'; + +// ---------------------------------------------------------------------- + +export const defaultFont = 'Public Sans'; + +export const primaryFont = setFont(defaultFont); + +export const secondaryFont = setFont('Barlow'); + +// ---------------------------------------------------------------------- + +export const typography = { + fontFamily: primaryFont, + fontSecondaryFamily: secondaryFont, + fontWeightLight: '300', + fontWeightRegular: '400', + fontWeightMedium: '500', + fontWeightSemiBold: '600', + fontWeightBold: '700', + h1: { + fontWeight: 800, + lineHeight: 80 / 64, + fontSize: pxToRem(40), + fontFamily: secondaryFont, + ...responsiveFontSizes({ sm: 52, md: 58, lg: 64 }), + }, + h2: { + fontWeight: 800, + lineHeight: 64 / 48, + fontSize: pxToRem(32), + fontFamily: secondaryFont, + ...responsiveFontSizes({ sm: 40, md: 44, lg: 48 }), + }, + h3: { + fontWeight: 700, + lineHeight: 1.5, + fontSize: pxToRem(24), + fontFamily: secondaryFont, + ...responsiveFontSizes({ sm: 26, md: 30, lg: 32 }), + }, + h4: { + fontWeight: 700, + lineHeight: 1.5, + fontSize: pxToRem(20), + ...responsiveFontSizes({ sm: 20, md: 24, lg: 24 }), + }, + h5: { + fontWeight: 700, + lineHeight: 1.5, + fontSize: pxToRem(18), + ...responsiveFontSizes({ sm: 19, md: 20, lg: 20 }), + }, + h6: { + fontWeight: 600, + lineHeight: 28 / 18, + fontSize: pxToRem(17), + ...responsiveFontSizes({ sm: 18, md: 18, lg: 18 }), + }, + subtitle1: { + fontWeight: 600, + lineHeight: 1.5, + fontSize: pxToRem(16), + }, + subtitle2: { + fontWeight: 600, + lineHeight: 22 / 14, + fontSize: pxToRem(14), + }, + body1: { + lineHeight: 1.5, + fontSize: pxToRem(16), + }, + body2: { + lineHeight: 22 / 14, + fontSize: pxToRem(14), + }, + caption: { + lineHeight: 1.5, + fontSize: pxToRem(12), + }, + overline: { + fontWeight: 700, + lineHeight: 1.5, + fontSize: pxToRem(12), + textTransform: 'uppercase', + }, + button: { + fontWeight: 700, + lineHeight: 24 / 14, + fontSize: pxToRem(14), + textTransform: 'unset', + }, +}; diff --git a/front_minimal/src/theme/create-theme.js b/front_minimal/src/theme/create-theme.js new file mode 100644 index 0000000..196731f --- /dev/null +++ b/front_minimal/src/theme/create-theme.js @@ -0,0 +1,97 @@ +import { experimental_extendTheme as extendTheme } from '@mui/material/styles'; + +import { setFont } from './styles/utils'; +import { overridesTheme } from './overrides-theme'; +import { shadows, typography, components, colorSchemes, customShadows } from './core'; +import { updateCoreWithSettings, updateComponentsWithSettings } from './with-settings/update-theme'; + +// ---------------------------------------------------------------------- + +export function createTheme(localeComponents, settings) { + const initialTheme = { + colorSchemes, + shadows: shadows(settings.colorScheme), + customShadows: customShadows(settings.colorScheme), + direction: settings.direction, + shape: { borderRadius: 8 }, + components, + typography: { + ...typography, + fontFamily: setFont(settings.fontFamily), + }, + cssVarPrefix: '', + shouldSkipGeneratingVar, + }; + + /** + * 1.Update values from settings before creating theme. + */ + const updateTheme = updateCoreWithSettings(initialTheme, settings); + + /** + * 2.Create theme + add locale + update component with settings. + */ + const theme = extendTheme( + updateTheme, + localeComponents, + updateComponentsWithSettings(settings), + overridesTheme + ); + + return theme; +} + +// ---------------------------------------------------------------------- + +function shouldSkipGeneratingVar(keys, value) { + const skipGlobalKeys = [ + 'mixins', + 'overlays', + 'direction', + 'breakpoints', + 'cssVarPrefix', + 'unstable_sxConfig', + 'typography', + // 'transitions', + ]; + + const skipPaletteKeys = { + global: ['tonalOffset', 'dividerChannel', 'contrastThreshold'], + grey: ['A100', 'A200', 'A400', 'A700'], + text: ['icon'], + }; + + const isPaletteKey = keys[0] === 'palette'; + + if (isPaletteKey) { + const paletteType = keys[1]; + const skipKeys = skipPaletteKeys[paletteType] || skipPaletteKeys.global; + + return keys.some((key) => skipKeys?.includes(key)); + } + + return keys.some((key) => skipGlobalKeys?.includes(key)); +} + +/** +* createTheme without @settings and @locale components. +* + ```jsx +export function createTheme(): Theme { + const initialTheme = { + colorSchemes, + shadows: shadows('light'), + customShadows: customShadows('light'), + shape: { borderRadius: 8 }, + components, + typography, + cssVarPrefix: '', + shouldSkipGeneratingVar, + }; + + const theme = extendTheme(initialTheme, overridesTheme); + + return theme; +} + ``` +*/ diff --git a/front_minimal/src/theme/overrides-theme.js b/front_minimal/src/theme/overrides-theme.js new file mode 100644 index 0000000..cad6c5d --- /dev/null +++ b/front_minimal/src/theme/overrides-theme.js @@ -0,0 +1,24 @@ +// ---------------------------------------------------------------------- + +export const overridesTheme = { + /** + * + ```jsx + colorSchemes: { + light: { + palette: { + primary: createPaletteChannel({ + lighter: '#E4DCFD', + light: '#A996F8', + main: '#6950E8', + dark: '#3828A7', + darker: '#180F6F', + contrastText: '#FFFFFF', + }), + }, + }, + }, + shape: { borderRadius: 0 }, + ``` + */ +}; diff --git a/front_minimal/src/theme/styles/index.js b/front_minimal/src/theme/styles/index.js new file mode 100644 index 0000000..e4c2a09 --- /dev/null +++ b/front_minimal/src/theme/styles/index.js @@ -0,0 +1,3 @@ +export * from './utils'; + +export * from './mixins'; diff --git a/front_minimal/src/theme/styles/mixins.js b/front_minimal/src/theme/styles/mixins.js new file mode 100644 index 0000000..33293c7 --- /dev/null +++ b/front_minimal/src/theme/styles/mixins.js @@ -0,0 +1,220 @@ +import { dividerClasses } from '@mui/material/Divider'; +import { checkboxClasses } from '@mui/material/Checkbox'; +import { menuItemClasses } from '@mui/material/MenuItem'; +import { autocompleteClasses } from '@mui/material/Autocomplete'; + +import { CONFIG } from 'src/config-global'; + +import { remToPx, varAlpha, mediaQueries } from './utils'; + +// ---------------------------------------------------------------------- + +/** + * Usage: + * ...hideScrollX, + * ...hideScrollY, + */ +export const hideScrollX = { + msOverflowStyle: 'none', + scrollbarWidth: 'none', + overflowX: 'auto', + '&::-webkit-scrollbar': { display: 'none' }, +}; + +export const hideScrollY = { + msOverflowStyle: 'none', + scrollbarWidth: 'none', + overflowY: 'auto', + '&::-webkit-scrollbar': { display: 'none' }, +}; + +/** + * Usage: + * ...textGradient(`to right, ${theme.vars.palette.text.primary}, ${alpha(theme.vars.palette.text.primary, 0.2)}` + */ +export function textGradient(color) { + return { + background: `linear-gradient(${color})`, + WebkitBackgroundClip: 'text', + WebkitTextFillColor: 'transparent', + backgroundClip: 'text', + textFillColor: 'transparent', + color: 'transparent', + }; +} + +/** + * Usage: + * ...borderGradient({ color: `to right, ${theme.vars.palette.text.primary}, ${alpha(theme.vars.palette.text.primary, 0.2)}`, padding: '4px' }), + */ +export function borderGradient(props) { + return { + inset: 0, + width: '100%', + content: '""', + height: '100%', + margin: 'auto', + position: 'absolute', + borderRadius: 'inherit', + padding: props?.padding ?? '2px', + // + mask: 'linear-gradient(#FFF 0 0) content-box, linear-gradient(#FFF 0 0)', + WebkitMask: 'linear-gradient(#FFF 0 0) content-box, linear-gradient(#FFF 0 0)', + maskComposite: 'exclude', + WebkitMaskComposite: 'xor', + ...(props?.color && { + background: `linear-gradient(${props.color})`, + }), + }; +} + +/** + * Usage: + * ...bgGradient({ color: `to right, ${theme.vars.palette.grey[900]} 25%, ${varAlpha(theme.vars.palette.primary.darkerChannel, 0.88)}`, imgUrl: '/assets/background/overlay.png' }), + */ +export function bgGradient({ color, imgUrl }) { + if (imgUrl) { + return { + background: `linear-gradient(${color}), url(${imgUrl})`, + backgroundSize: 'cover', + backgroundRepeat: 'no-repeat', + backgroundPosition: 'center center', + }; + } + return { background: `linear-gradient(${color})` }; +} + +/** + * Usage: + * ...bgBlur({ color: `varAlpha(theme.vars.palette.background.paperChannel, 0.8)`, imgUrl: '/assets/background/overlay.png', blur: 6 }), + */ +export function bgBlur({ color, blur = 6, imgUrl }) { + if (imgUrl) { + return { + position: 'relative', + backgroundImage: `url(${imgUrl})`, + '&::before': { + position: 'absolute', + top: 0, + left: 0, + zIndex: 9, + content: '""', + width: '100%', + height: '100%', + backdropFilter: `blur(${blur}px)`, + WebkitBackdropFilter: `blur(${blur}px)`, + backgroundColor: color, + }, + }; + } + return { + backdropFilter: `blur(${blur}px)`, + WebkitBackdropFilter: `blur(${blur}px)`, + backgroundColor: color, + }; +} + +/** + * Usage: + * ...maxLine({ line: 2, persistent: theme.typography.caption }), + */ +function getFontSize(fontSize) { + return typeof fontSize === 'string' ? remToPx(fontSize) : fontSize; +} + +function getLineHeight(lineHeight, fontSize) { + if (typeof lineHeight === 'string') { + return fontSize ? remToPx(lineHeight) / fontSize : 1; + } + return lineHeight; +} + +export function maxLine({ line, persistent }) { + const baseStyles = { + overflow: 'hidden', + display: '-webkit-box', + textOverflow: 'ellipsis', + WebkitLineClamp: line, + WebkitBoxOrient: 'vertical', + }; + + if (persistent) { + const fontSizeBase = getFontSize(persistent.fontSize); + const fontSizeSm = getFontSize(persistent[mediaQueries.upSm]?.fontSize); + const fontSizeMd = getFontSize(persistent[mediaQueries.upMd]?.fontSize); + const fontSizeLg = getFontSize(persistent[mediaQueries.upLg]?.fontSize); + + const lineHeight = getLineHeight(persistent.lineHeight, fontSizeBase); + + return { + ...baseStyles, + ...(lineHeight && { + ...(fontSizeBase && { height: fontSizeBase * lineHeight * line }), + ...(fontSizeSm && { + [mediaQueries.upSm]: { height: fontSizeSm * lineHeight * line }, + }), + ...(fontSizeMd && { + [mediaQueries.upMd]: { height: fontSizeMd * lineHeight * line }, + }), + ...(fontSizeLg && { + [mediaQueries.upLg]: { height: fontSizeLg * lineHeight * line }, + }), + }), + }; + } + + return baseStyles; +} + +/** + * Usage: + * ...paper({ theme, color: varAlpha(theme.vars.palette.background.paperChannel, 0.9), dropdown: true }), + */ +export function paper({ theme, color, dropdown }) { + return { + ...bgBlur({ + color: color ?? varAlpha(theme.vars.palette.background.paperChannel, 0.9), + blur: 20, + }), + backgroundImage: `url(${CONFIG.site.basePath}/assets/cyan-blur.png), url(${CONFIG.site.basePath}/assets/red-blur.png)`, + backgroundRepeat: 'no-repeat, no-repeat', + backgroundPosition: 'top right, left bottom', + backgroundSize: '50%, 50%', + ...(theme.direction === 'rtl' && { + backgroundPosition: 'top left, right bottom', + }), + ...(dropdown && { + padding: theme.spacing(0.5), + boxShadow: theme.customShadows.dropdown, + borderRadius: `${theme.shape.borderRadius * 1.25}px`, + }), + }; +} + +/** + * Usage: + * ...menuItem(theme) + */ +export function menuItem(theme) { + return { + ...theme.typography.body2, + padding: theme.spacing(0.75, 1), + borderRadius: theme.shape.borderRadius * 0.75, + '&:not(:last-of-type)': { marginBottom: 4 }, + [`&.${menuItemClasses.selected}`]: { + fontWeight: theme.typography.fontWeightSemiBold, + backgroundColor: theme.vars.palette.action.selected, + '&:hover': { backgroundColor: theme.vars.palette.action.hover }, + }, + [`& .${checkboxClasses.root}`]: { + padding: theme.spacing(0.5), + marginLeft: theme.spacing(-0.5), + marginRight: theme.spacing(0.5), + }, + [`&.${autocompleteClasses.option}[aria-selected="true"]`]: { + backgroundColor: theme.vars.palette.action.selected, + '&:hover': { backgroundColor: theme.vars.palette.action.hover }, + }, + [`&+.${dividerClasses.root}`]: { margin: theme.spacing(0.5, 0) }, + }; +} diff --git a/front_minimal/src/theme/styles/utils.js b/front_minimal/src/theme/styles/utils.js new file mode 100644 index 0000000..57ed0c4 --- /dev/null +++ b/front_minimal/src/theme/styles/utils.js @@ -0,0 +1,99 @@ +// ---------------------------------------------------------------------- + +export const stylesMode = { + light: '[data-mui-color-scheme="light"] &', + dark: '[data-mui-color-scheme="dark"] &', +}; + +export const mediaQueries = { + upXs: '@media (min-width:0px)', + upSm: '@media (min-width:600px)', + upMd: '@media (min-width:900px)', + upLg: '@media (min-width:1200px)', + upXl: '@media (min-width:1536px)', +}; + +/** + * Set font family + */ +export function setFont(fontName) { + return `"${fontName}",-apple-system,BlinkMacSystemFont,"Segoe UI",Roboto,"Helvetica Neue",Arial,sans-serif,"Apple Color Emoji","Segoe UI Emoji","Segoe UI Symbol"`; +} + +/** + * Converts rem to px + */ +export function remToPx(value) { + return Math.round(parseFloat(value) * 16); +} + +/** + * Converts px to rem + */ +export function pxToRem(value) { + return `${value / 16}rem`; +} + +/** + * Responsive font sizes + */ +export function responsiveFontSizes({ sm, md, lg }) { + return { + [mediaQueries.upSm]: { fontSize: pxToRem(sm) }, + [mediaQueries.upMd]: { fontSize: pxToRem(md) }, + [mediaQueries.upLg]: { fontSize: pxToRem(lg) }, + }; +} + +/** + * Converts a hex color to RGB channels + */ +export function hexToRgbChannel(hex) { + if (!/^#[0-9A-F]{6}$/i.test(hex)) { + throw new Error(`Invalid hex color: ${hex}`); + } + + const r = parseInt(hex.substring(1, 3), 16); + const g = parseInt(hex.substring(3, 5), 16); + const b = parseInt(hex.substring(5, 7), 16); + + return `${r} ${g} ${b}`; +} + +/** + * Converts a hex color to RGB channels + */ +export function createPaletteChannel(hexPalette) { + const channelPalette = {}; + + Object.entries(hexPalette).forEach(([key, value]) => { + channelPalette[`${key}Channel`] = hexToRgbChannel(value); + }); + + return { ...hexPalette, ...channelPalette }; +} + +/** + * Color with alpha channel + */ +export function varAlpha(color, opacity = 1) { + const unsupported = + color.startsWith('#') || + color.startsWith('rgb') || + color.startsWith('rgba') || + (!color.includes('var') && color.includes('Channel')); + + if (unsupported) { + throw new Error(`[Alpha]: Unsupported color format "${color}". + Supported formats are: + - RGB channels: "0 184 217". + - CSS variables with "Channel" prefix: "var(--palette-common-blackChannel, #000000)". + Unsupported formats are: + - Hex: "#00B8D9". + - RGB: "rgb(0, 184, 217)". + - RGBA: "rgba(0, 184, 217, 1)". + `); + } + + return `rgba(${color} / ${opacity})`; +} diff --git a/front_minimal/src/theme/theme-provider.jsx b/front_minimal/src/theme/theme-provider.jsx new file mode 100644 index 0000000..270c869 --- /dev/null +++ b/front_minimal/src/theme/theme-provider.jsx @@ -0,0 +1,36 @@ +'use client'; + +import CssBaseline from '@mui/material/CssBaseline'; +import { AppRouterCacheProvider } from '@mui/material-nextjs/v14-appRouter'; +import { Experimental_CssVarsProvider as CssVarsProvider } from '@mui/material/styles'; + +import { useTranslate } from 'src/locales'; + +import { useSettingsContext } from 'src/components/settings'; + +import { createTheme } from './create-theme'; +import { RTL } from './with-settings/right-to-left'; +import { schemeConfig } from './color-scheme-script'; + +// ---------------------------------------------------------------------- + +export function ThemeProvider({ children }) { + const { currentLang } = useTranslate(); + + const settings = useSettingsContext(); + + const theme = createTheme(currentLang?.systemValue, settings); + + return ( + + + + {children} + + + ); +} diff --git a/front_minimal/src/theme/with-settings/primary-color.json b/front_minimal/src/theme/with-settings/primary-color.json new file mode 100644 index 0000000..9d96e52 --- /dev/null +++ b/front_minimal/src/theme/with-settings/primary-color.json @@ -0,0 +1,42 @@ +{ + "cyan": { + "lighter": "#CCF4FE", + "light": "#68CDF9", + "main": "#078DEE", + "dark": "#0351AB", + "darker": "#012972", + "contrastText": "#FFFFFF" + }, + "purple": { + "lighter": "#EBD6FD", + "light": "#B985F4", + "main": "#7635dc", + "dark": "#431A9E", + "darker": "#200A69", + "contrastText": "#FFFFFF" + }, + "blue": { + "lighter": "#CDE9FD", + "light": "#6BB1F8", + "main": "#0C68E9", + "dark": "#063BA7", + "darker": "#021D6F", + "contrastText": "#FFFFFF" + }, + "orange": { + "lighter": "#FEF4D4", + "light": "#FED680", + "main": "#fda92d", + "dark": "#B66816", + "darker": "#793908", + "contrastText": "#1C252E" + }, + "red": { + "lighter": "#FFE3D5", + "light": "#FFC1AC", + "main": "#FF3030", + "dark": "#B71833", + "darker": "#7A0930", + "contrastText": "#FFFFFF" + } +} diff --git a/front_minimal/src/theme/with-settings/right-to-left.jsx b/front_minimal/src/theme/with-settings/right-to-left.jsx new file mode 100644 index 0000000..88a8932 --- /dev/null +++ b/front_minimal/src/theme/with-settings/right-to-left.jsx @@ -0,0 +1,24 @@ +import { useEffect } from 'react'; +import createCache from '@emotion/cache'; +import rtlPlugin from 'stylis-plugin-rtl'; +import { CacheProvider } from '@emotion/react'; + +// ---------------------------------------------------------------------- + +const cacheRtl = createCache({ + key: 'rtl', + prepend: true, + stylisPlugins: [rtlPlugin], +}); + +export function RTL({ children, direction }) { + useEffect(() => { + document.dir = direction; + }, [direction]); + + if (direction === 'rtl') { + return {children}; + } + + return <>{children}; +} diff --git a/front_minimal/src/theme/with-settings/update-theme.js b/front_minimal/src/theme/with-settings/update-theme.js new file mode 100644 index 0000000..11c2b02 --- /dev/null +++ b/front_minimal/src/theme/with-settings/update-theme.js @@ -0,0 +1,109 @@ +import COLORS from '../core/colors.json'; +import PRIMARY_COLOR from './primary-color.json'; +import { components as coreComponents } from '../core/components'; +import { hexToRgbChannel, createPaletteChannel } from '../styles'; +import { grey as coreGreyPalette, primary as corePrimaryPalette } from '../core/palette'; +import { createShadowColor, customShadows as coreCustomShadows } from '../core/custom-shadows'; + +// ---------------------------------------------------------------------- + +/** + * [1] settings @primaryColor + * [2] settings @contrast + */ + +export function updateCoreWithSettings(theme, settings) { + const { colorSchemes, customShadows } = theme; + + return { + ...theme, + colorSchemes: { + ...colorSchemes, + light: { + palette: { + ...colorSchemes?.light?.palette, + /** [1] */ + primary: getPalettePrimary(settings.primaryColor), + /** [2] */ + background: { + ...colorSchemes?.light?.palette?.background, + default: getBackgroundDefault(settings.contrast), + defaultChannel: hexToRgbChannel(getBackgroundDefault(settings.contrast)), + }, + }, + }, + dark: { + palette: { + ...colorSchemes?.dark?.palette, + /** [1] */ + primary: getPalettePrimary(settings.primaryColor), + }, + }, + }, + customShadows: { + ...customShadows, + /** [1] */ + primary: + settings.primaryColor === 'default' + ? coreCustomShadows('light').primary + : createShadowColor(getPalettePrimary(settings.primaryColor).mainChannel), + }, + }; +} + +// ---------------------------------------------------------------------- + +export function updateComponentsWithSettings(settings) { + const components = {}; + + /** [2] */ + if (settings.contrast === 'hight') { + const MuiCard = { + styleOverrides: { + root: ({ theme, ownerState }) => { + let rootStyles = {}; + if (typeof coreComponents?.MuiCard?.styleOverrides?.root === 'function') { + rootStyles = + coreComponents.MuiCard.styleOverrides.root({ + ownerState, + theme, + }) ?? {}; + } + + return { + ...rootStyles, + boxShadow: theme.customShadows.z1, + }; + }, + }, + }; + + components.MuiCard = MuiCard; + } + + return { components }; +} + +// ---------------------------------------------------------------------- + +const PRIMARY_COLORS = { + default: COLORS.primary, + cyan: PRIMARY_COLOR.cyan, + purple: PRIMARY_COLOR.purple, + blue: PRIMARY_COLOR.blue, + orange: PRIMARY_COLOR.orange, + red: PRIMARY_COLOR.red, +}; + +function getPalettePrimary(primaryColorName) { + /** [1] */ + const selectedPrimaryColor = PRIMARY_COLORS[primaryColorName]; + const updatedPrimaryPalette = createPaletteChannel(selectedPrimaryColor); + + return primaryColorName === 'default' ? corePrimaryPalette : updatedPrimaryPalette; +} + +function getBackgroundDefault(contrast) { + /** [2] */ + return contrast === 'default' ? '#FFFFFF' : coreGreyPalette[200]; +} diff --git a/front_minimal/src/utils/axios.js b/front_minimal/src/utils/axios.js new file mode 100644 index 0000000..bb8b943 --- /dev/null +++ b/front_minimal/src/utils/axios.js @@ -0,0 +1,58 @@ +import axios from 'axios'; + +import { CONFIG } from 'src/config-global'; + +// ---------------------------------------------------------------------- + +const axiosInstance = axios.create({ baseURL: CONFIG.site.serverUrl }); + +axiosInstance.interceptors.response.use( + (response) => response, + (error) => Promise.reject((error.response && error.response.data) || 'Something went wrong!') +); + +export default axiosInstance; + +// ---------------------------------------------------------------------- + +export const fetcher = async (args) => { + try { + const [url, config] = Array.isArray(args) ? args : [args]; + + const res = await axiosInstance.get(url, { ...config }); + + return res.data; + } catch (error) { + console.error('Failed to fetch:', error); + throw error; + } +}; + +// ---------------------------------------------------------------------- + +export const endpoints = { + chat: '/api/chat', + kanban: '/api/kanban', + calendar: '/api/calendar', + auth: { + me: '/profile/me/', + signIn: '/auth/login/', + signUp: '/auth/register/', + }, + mail: { + list: '/api/mail/list', + details: '/api/mail/details', + labels: '/api/mail/labels', + }, + post: { + list: '/api/post/list', + details: '/api/post/details', + latest: '/api/post/latest', + search: '/api/post/search', + }, + product: { + list: '/api/product/list', + details: '/api/product/details', + search: '/api/product/search', + }, +}; diff --git a/front_minimal/src/utils/change-case.js b/front_minimal/src/utils/change-case.js new file mode 100644 index 0000000..3b7e7ff --- /dev/null +++ b/front_minimal/src/utils/change-case.js @@ -0,0 +1,23 @@ +// ---------------------------------------------------------------------- + +export function paramCase(str) { + return str + .toLowerCase() + .replace(/\s+/g, '-') + .replace(/[^a-z0-9-]/g, ''); +} + +// ---------------------------------------------------------------------- + +export function snakeCase(str) { + return str + .toLowerCase() + .replace(/\s+/g, '_') + .replace(/[^a-z0-9_]/g, ''); +} + +// ---------------------------------------------------------------------- + +export function sentenceCase(string) { + return string.charAt(0).toUpperCase() + string.slice(1); +} diff --git a/front_minimal/src/utils/dashboard-api.ts b/front_minimal/src/utils/dashboard-api.ts new file mode 100644 index 0000000..0b8ba09 --- /dev/null +++ b/front_minimal/src/utils/dashboard-api.ts @@ -0,0 +1,309 @@ +/** + * API модуль для dashboard + */ + +import apiClient from 'src/utils/axios'; + +// Типы данных dashboard +export interface DashboardStats { + total_clients?: number; + active_clients?: number; + lessons_this_month?: number; + lessons_today?: number; + lessons_this_week?: number; + earnings_this_month?: number; + total_revenue?: number; + upcoming_lessons?: LessonPreview[]; + recent_homework?: HomeworkPreview[]; + total_lessons?: number; + completed_lessons?: number; + homework_pending?: number; + homework_completed?: number; + average_grade?: number; + next_lesson?: LessonPreview | null; + children_count?: number; + children_stats?: ChildStats[]; + total_homeworks?: number; + pending_submissions?: number; + total_materials?: number; + unread_notifications?: number; +} + +export interface LessonPreview { + id: string; + title: string; + subject: string; + start_time: string; + end_time: string; + mentor?: UserPreview; + client?: UserPreview; + status: 'scheduled' | 'in_progress' | 'completed' | 'cancelled'; + room_url?: string; +} + +export interface HomeworkPreview { + id: string; + title: string; + subject: string; + due_date: string; + status: 'pending' | 'submitted' | 'reviewed' | 'completed'; + grade?: number; + lesson?: LessonPreview; +} + +export interface ChildStats { + id: string; + name: string; + avatar?: string | null; + avatar_url?: string | null; + total_lessons: number; + completed_lessons: number; + average_grade: number; + next_lesson?: LessonPreview | null; + homework_pending: number; +} + +export interface UserPreview { + id: string; + email?: string; + name?: string; + first_name: string; + last_name: string; + avatar?: string; +} + +export interface MentorDashboardResponse { + summary: { + total_clients: number; + total_lessons: number; + lessons_this_week: number; + lessons_this_month: number; + completed_lessons: number; + total_homeworks: number; + pending_submissions: number; + total_materials: number; + unread_notifications: number; + total_revenue: number; + revenue_this_month: number; + }; + upcoming_lessons: Array<{ + id: string; + title: string; + subject?: string | null; + client: { + id: string; + name: string; + avatar?: string | null; + first_name?: string; + last_name?: string; + }; + start_time: string; + end_time: string; + }>; + recent_submissions?: Array<{ + id: string; + homework: { + id: string; + title: string; + }; + subject?: string | null; + student: { + id: string; + name: string; + avatar?: string | null; + first_name?: string; + last_name?: string; + }; + status: string; + score?: number | null; + max_score: number; + submitted_at: string; + }>; +} + +export interface IncomeChartData { + date: string; + income: number; + lessons: number; +} + +export interface MentorIncomeResponse { + period: string; + start_date: string; + end_date: string; + summary: { + total_income: number; + total_lessons: number; + average_lesson_price: number; + }; + chart_data: IncomeChartData[]; +} + +/** + * Получить статистику для дашборда ментора + */ +export async function getMentorDashboard(options?: { signal?: AbortSignal }): Promise { + const config = options?.signal ? { signal: options.signal } : undefined; + const response = await apiClient.get('/mentor/dashboard/', config); + return response.data; +} + +/** + * Ответ API прогресса клиента (оценки по предметам, посещаемость и т.д.) + */ +export interface ClientProgressResponse { + total_lessons: number; + completed_lessons: number; + cancelled_lessons: number; + attendance_rate: number; + average_mentor_grade: number; + average_school_grade: number; + total_homework: number; + completed_homework: number; + homework_completion_rate: number; + grades_by_subject: Array<{ subject: string; average_grade: number; lessons_count: number }>; + recent_grades?: Array<{ + lesson_title: string; + date: string | null; + mentor_grade: number; + school_grade: number; + }>; +} + +/** + * Получить прогресс клиента (для списка предметов и сводок). + * GET /api/client/progress/?period=90 + */ +export async function getClientProgress(params?: { period?: number }): Promise { + const url = params?.period != null ? `/client/progress/?period=${params.period}` : '/client/progress/'; + const response = await apiClient.get(url); + return response.data; +} + +/** Ответ API /client/dashboard/ и /parent/{id}/child_dashboard/ — данные в summary */ +interface ClientDashboardApiResponse { + summary?: { + total_lessons?: number; + completed_lessons?: number; + lessons_this_week?: number; + total_homeworks?: number; + completed_homeworks?: number; + pending_homeworks?: number; + average_score?: number; + shared_materials?: number; + unread_notifications?: number; + }; + upcoming_lessons?: Array<{ + id: string | number; + title?: string; + mentor?: { id: number; name: string }; + start_time?: string | null; + end_time?: string | null; + }>; +} + +function normalizeClientDashboardResponse(raw: ClientDashboardApiResponse): DashboardStats { + const s = raw.summary ?? {}; + const upcoming = raw.upcoming_lessons ?? []; + return { + total_lessons: s.total_lessons ?? 0, + completed_lessons: s.completed_lessons ?? 0, + homework_pending: s.pending_homeworks ?? 0, + homework_completed: s.completed_homeworks ?? 0, + average_grade: s.average_score ?? 0, + next_lesson: upcoming[0] ? { + id: String(upcoming[0].id), + title: upcoming[0].title ?? '', + subject: '', + start_time: upcoming[0].start_time ?? '', + end_time: upcoming[0].end_time ?? '', + status: 'scheduled', + mentor: upcoming[0].mentor ? { id: String(upcoming[0].mentor.id), first_name: upcoming[0].mentor.name, last_name: '', email: '' } : undefined, + } : null, + upcoming_lessons: upcoming.map((l) => ({ + id: String(l.id), + title: l.title ?? '', + subject: '', + start_time: l.start_time ?? '', + end_time: l.end_time ?? '', + status: 'scheduled' as const, + mentor: l.mentor ? { id: String(l.mentor.id), first_name: l.mentor.name, last_name: '', email: '' } : undefined, + })), + recent_homework: [], + }; +} + +/** + * Получить статистику для дашборда клиента + */ +export async function getClientDashboard(): Promise { + const response = await apiClient.get('/client/dashboard/'); + return normalizeClientDashboardResponse(response.data); +} + +/** + * Получить статистику для дашборда родителя + */ +export async function getParentDashboard(): Promise { + const response = await apiClient.get('/parent/dashboard/'); + return response.data; +} + +/** + * Получить дашборд выбранного ребенка для родителя + */ +export async function getChildDashboard(childId: string): Promise { + const response = await apiClient.get(`/parent/${childId}/child_dashboard/`); + return normalizeClientDashboardResponse(response.data); +} + +/** + * Получить список учеников ментора + */ +export async function getMentorStudents(): Promise { + const response = await apiClient.get('/manage/clients/?page=1&page_size=200'); + return response.data; +} + +/** + * Получить список предметов ментора + */ +export async function getMentorSubjects(): Promise { + const response = await apiClient.get('/schedule/subjects/'); + return response.data; +} + +/** + * Создать новое занятие + */ +export async function createCalendarLesson(data: any): Promise { + const response = await apiClient.post('/schedule/lessons/', data); + return response.data; +} + +/** + * Получить список уроков для календаря + */ +export async function getCalendarLessons(startDate?: string, endDate?: string): Promise { + const url = `/schedule/lessons/calendar/${startDate ? `?start_date=${startDate}&end_date=${endDate}` : ''}`; + const response = await apiClient.get(url); + return response.data; +} + +/** + * Получить статистику доходов ментора + */ +export async function getMentorIncome( + period: 'day' | 'week' | 'month' | 'range' = 'week', + startDate?: string, + endDate?: string, + options?: { signal?: AbortSignal } +): Promise { + let url = `/mentor/income/?period=${period}`; + if (period === 'range' && startDate && endDate) { + url += `&start_date=${startDate}&end_date=${endDate}`; + } + const config = options?.signal ? { signal: options.signal } : undefined; + const response = await apiClient.get(url, config); + return response.data; +} diff --git a/front_minimal/src/utils/format-number.js b/front_minimal/src/utils/format-number.js new file mode 100644 index 0000000..54da4af --- /dev/null +++ b/front_minimal/src/utils/format-number.js @@ -0,0 +1,97 @@ +import { formatNumberLocale } from 'src/locales'; + +// ---------------------------------------------------------------------- + +const DEFAULT_LOCALE = { code: 'en-US', currency: 'USD' }; + +function processInput(inputValue) { + if (inputValue == null || Number.isNaN(inputValue)) return null; + return Number(inputValue); +} + +// ---------------------------------------------------------------------- + +export function fNumber(inputValue, options) { + const locale = formatNumberLocale() || DEFAULT_LOCALE; + + const number = processInput(inputValue); + if (number === null) return ''; + + const fm = new Intl.NumberFormat(locale.code, { + minimumFractionDigits: 0, + maximumFractionDigits: 2, + ...options, + }).format(number); + + return fm; +} + +// ---------------------------------------------------------------------- + +export function fCurrency(inputValue, options) { + const locale = formatNumberLocale() || DEFAULT_LOCALE; + + const number = processInput(inputValue); + if (number === null) return ''; + + const fm = new Intl.NumberFormat(locale.code, { + style: 'currency', + currency: locale.currency, + minimumFractionDigits: 0, + maximumFractionDigits: 2, + ...options, + }).format(number); + + return fm; +} + +// ---------------------------------------------------------------------- + +export function fPercent(inputValue, options) { + const locale = formatNumberLocale() || DEFAULT_LOCALE; + + const number = processInput(inputValue); + if (number === null) return ''; + + const fm = new Intl.NumberFormat(locale.code, { + style: 'percent', + minimumFractionDigits: 0, + maximumFractionDigits: 1, + ...options, + }).format(number / 100); + + return fm; +} + +// ---------------------------------------------------------------------- + +export function fShortenNumber(inputValue, options) { + const locale = formatNumberLocale() || DEFAULT_LOCALE; + + const number = processInput(inputValue); + if (number === null) return ''; + + const fm = new Intl.NumberFormat(locale.code, { + notation: 'compact', + maximumFractionDigits: 2, + ...options, + }).format(number); + + return fm.replace(/[A-Z]/g, (match) => match.toLowerCase()); +} + +// ---------------------------------------------------------------------- + +export function fData(inputValue) { + const number = processInput(inputValue); + if (number === null || number === 0) return '0 bytes'; + + const units = ['bytes', 'Kb', 'Mb', 'Gb', 'Tb', 'Pb', 'Eb', 'Zb', 'Yb']; + const decimal = 2; + const baseValue = 1024; + + const index = Math.floor(Math.log(number) / Math.log(baseValue)); + const fm = `${parseFloat((number / baseValue ** index).toFixed(decimal))} ${units[index]}`; + + return fm; +} diff --git a/front_minimal/src/utils/format-time.js b/front_minimal/src/utils/format-time.js new file mode 100644 index 0000000..04061dd --- /dev/null +++ b/front_minimal/src/utils/format-time.js @@ -0,0 +1,241 @@ +import dayjs from 'dayjs'; +import 'dayjs/locale/ru'; // Импорт русской локали для dayjs +import duration from 'dayjs/plugin/duration'; +import relativeTime from 'dayjs/plugin/relativeTime'; + +// ---------------------------------------------------------------------- + +dayjs.locale('ru'); // Глобальная установка локали +dayjs.extend(duration); +dayjs.extend(relativeTime); + +/** + * Docs: https://day.js.org/docs/en/display/format + */ +export const formatStr = { + dateTime: 'DD MMM YYYY h:mm a', // 17 Apr 2022 12:00 am + date: 'DD MMM YYYY', // 17 Apr 2022 + time: 'h:mm a', // 12:00 am + split: { + dateTime: 'DD/MM/YYYY h:mm a', // 17/04/2022 12:00 am + date: 'DD/MM/YYYY', // 17/04/2022 + }, + paramCase: { + dateTime: 'DD-MM-YYYY h:mm a', // 17-04-2022 12:00 am + date: 'DD-MM-YYYY', // 17-04-2022 + }, +}; + +export function today(format) { + return dayjs(new Date()).startOf('day').format(format); +} + +// ---------------------------------------------------------------------- + +/** output: 17 Apr 2022 12:00 am + */ +export function fDateTime(date, format) { + if (!date) { + return null; + } + + const isValid = dayjs(date).isValid(); + + return isValid ? dayjs(date).format(format ?? formatStr.dateTime) : 'Invalid time value'; +} + +// ---------------------------------------------------------------------- + +/** output: 17 Apr 2022 + */ +export function fDate(date, format) { + if (!date) { + return null; + } + + const isValid = dayjs(date).isValid(); + + return isValid ? dayjs(date).format(format ?? formatStr.date) : 'Invalid time value'; +} + +// ---------------------------------------------------------------------- + +/** output: 12:00 am + */ +export function fTime(date, format) { + if (!date) { + return null; + } + + const isValid = dayjs(date).isValid(); + + return isValid ? dayjs(date).format(format ?? formatStr.time) : 'Invalid time value'; +} + +// ---------------------------------------------------------------------- + +/** output: 1713250100 + */ +export function fTimestamp(date) { + if (!date) { + return null; + } + + const isValid = dayjs(date).isValid(); + + return isValid ? dayjs(date).valueOf() : 'Invalid time value'; +} + +// ---------------------------------------------------------------------- + +/** output: a few seconds, 2 years + */ +export function fToNow(date) { + if (!date) { + return null; + } + + const isValid = dayjs(date).isValid(); + + return isValid ? dayjs(date).toNow(true) : 'Invalid time value'; +} + +// ---------------------------------------------------------------------- + +/** output: boolean + */ +export function fIsBetween(inputDate, startDate, endDate) { + if (!inputDate || !startDate || !endDate) { + return false; + } + + const formattedInputDate = fTimestamp(inputDate); + const formattedStartDate = fTimestamp(startDate); + const formattedEndDate = fTimestamp(endDate); + + if (formattedInputDate && formattedStartDate && formattedEndDate) { + return formattedInputDate >= formattedStartDate && formattedInputDate <= formattedEndDate; + } + + return false; +} + +// ---------------------------------------------------------------------- + +/** output: boolean + */ +export function fIsAfter(startDate, endDate) { + return dayjs(startDate).isAfter(endDate); +} + +// ---------------------------------------------------------------------- + +/** output: boolean + */ +export function fIsSame(startDate, endDate, units) { + if (!startDate || !endDate) { + return false; + } + + const isValid = dayjs(startDate).isValid() && dayjs(endDate).isValid(); + + if (!isValid) { + return 'Invalid time value'; + } + + return dayjs(startDate).isSame(endDate, units ?? 'year'); +} + +// ---------------------------------------------------------------------- + +/** output: + * Same day: 26 Apr 2024 + * Same month: 25 - 26 Apr 2024 + * Same month: 25 - 26 Apr 2024 + * Same year: 25 Apr - 26 May 2024 + */ +export function fDateRangeShortLabel(startDate, endDate, initial) { + const isValid = dayjs(startDate).isValid() && dayjs(endDate).isValid(); + + const isAfter = fIsAfter(startDate, endDate); + + if (!isValid || isAfter) { + return 'Invalid time value'; + } + + let label = `${fDate(startDate)} - ${fDate(endDate)}`; + + if (initial) { + return label; + } + + const isSameYear = fIsSame(startDate, endDate, 'year'); + const isSameMonth = fIsSame(startDate, endDate, 'month'); + const isSameDay = fIsSame(startDate, endDate, 'day'); + + if (isSameYear && !isSameMonth) { + label = `${fDate(startDate, 'DD MMM')} - ${fDate(endDate)}`; + } else if (isSameYear && isSameMonth && !isSameDay) { + label = `${fDate(startDate, 'DD')} - ${fDate(endDate)}`; + } else if (isSameYear && isSameMonth && isSameDay) { + label = `${fDate(endDate)}`; + } + + return label; +} + +/** output: '2024-05-28T05:55:31+00:00' + */ +export function fAdd({ + years = 0, + months = 0, + days = 0, + hours = 0, + minutes = 0, + seconds = 0, + milliseconds = 0, +}) { + const result = dayjs() + .add( + dayjs.duration({ + years, + months, + days, + hours, + minutes, + seconds, + milliseconds, + }) + ) + .format(); + + return result; +} + +/** output: '2024-05-28T05:55:31+00:00' + */ +export function fSub({ + years = 0, + months = 0, + days = 0, + hours = 0, + minutes = 0, + seconds = 0, + milliseconds = 0, +}) { + const result = dayjs() + .subtract( + dayjs.duration({ + years, + months, + days, + hours, + minutes, + seconds, + milliseconds, + }) + ) + .format(); + + return result; +} diff --git a/front_minimal/src/utils/helper.js b/front_minimal/src/utils/helper.js new file mode 100644 index 0000000..161858c --- /dev/null +++ b/front_minimal/src/utils/helper.js @@ -0,0 +1,125 @@ +/** + * https://github.com/you-dont-need/You-Dont-Need-Lodash-Underscore?tab=readme-ov-file#_flatten + * https://github.com/you-dont-need-x/you-dont-need-lodash + */ + +// ---------------------------------------------------------------------- + +export function flattenArray(list, key = 'children') { + let children = []; + + const flatten = list?.map((item) => { + if (item[key] && item[key].length) { + children = [...children, ...item[key]]; + } + return item; + }); + + return flatten?.concat(children.length ? flattenArray(children, key) : children); +} + +// ---------------------------------------------------------------------- + +export function flattenDeep(array) { + const isArray = array && Array.isArray(array); + + if (isArray) { + return array.flat(Infinity); + } + return []; +} + +// ---------------------------------------------------------------------- + +export function orderBy(array, properties, orders) { + return array.slice().sort((a, b) => { + for (let i = 0; i < properties.length; i += 1) { + const property = properties[i]; + const order = orders && orders[i] === 'desc' ? -1 : 1; + + const aValue = a[property]; + const bValue = b[property]; + + if (aValue < bValue) return -1 * order; + if (aValue > bValue) return 1 * order; + } + return 0; + }); +} + +// ---------------------------------------------------------------------- + +export function keyBy(array, key) { + return (array || []).reduce((result, item) => { + const keyValue = key ? item[key] : item; + + return { ...result, [String(keyValue)]: item }; + }, {}); +} + +// ---------------------------------------------------------------------- + +export function sumBy(array, iteratee) { + return array.reduce((sum, item) => sum + iteratee(item), 0); +} + +// ---------------------------------------------------------------------- + +export function isEqual(a, b) { + if (a === null || a === undefined || b === null || b === undefined) { + return a === b; + } + + if (typeof a !== typeof b) { + return false; + } + + if (typeof a === 'string' || typeof a === 'number' || typeof a === 'boolean') { + return a === b; + } + + if (Array.isArray(a) && Array.isArray(b)) { + if (a.length !== b.length) { + return false; + } + + return a.every((item, index) => isEqual(item, b[index])); + } + + if (typeof a === 'object' && typeof b === 'object') { + const keysA = Object.keys(a); + const keysB = Object.keys(b); + + if (keysA.length !== keysB.length) { + return false; + } + + return keysA.every((key) => isEqual(a[key], b[key])); + } + + return false; +} + +// ---------------------------------------------------------------------- + +function isObject(item) { + return item && typeof item === 'object' && !Array.isArray(item); +} + +export const merge = (target, ...sources) => { + if (!sources.length) return target; + + const source = sources.shift(); + + // eslint-disable-next-line no-restricted-syntax + for (const key in source) { + if (isObject(source[key])) { + if (!target[key]) Object.assign(target, { [key]: {} }); + merge(target[key], source[key]); + } else { + Object.assign(target, { [key]: source[key] }); + } + } + + return merge(target, ...sources); +}; diff --git a/front_minimal/src/utils/storage-available.js b/front_minimal/src/utils/storage-available.js new file mode 100644 index 0000000..ccb37f2 --- /dev/null +++ b/front_minimal/src/utils/storage-available.js @@ -0,0 +1,26 @@ +// ---------------------------------------------------------------------- + +export function localStorageAvailable() { + try { + const key = '__some_random_key_you_are_not_going_to_use__'; + window.localStorage.setItem(key, key); + window.localStorage.removeItem(key); + return true; + } catch (error) { + return false; + } +} + +// ---------------------------------------------------------------------- + +export function localStorageGetItem(key, defaultValue = '') { + const storageAvailable = localStorageAvailable(); + + let value; + + if (storageAvailable) { + value = localStorage.getItem(key) || defaultValue; + } + + return value; +} diff --git a/front_minimal/src/utils/uuidv4.js b/front_minimal/src/utils/uuidv4.js new file mode 100644 index 0000000..bdedf30 --- /dev/null +++ b/front_minimal/src/utils/uuidv4.js @@ -0,0 +1,11 @@ +/* eslint-disable no-bitwise */ + +// ---------------------------------------------------------------------- + +export function uuidv4() { + return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, (c) => { + const r = (Math.random() * 16) | 0; + const v = c === 'x' ? r : (r & 0x3) | 0x8; + return v.toString(16); + }); +} diff --git a/front_minimal/src/utils/with-loading-props.jsx b/front_minimal/src/utils/with-loading-props.jsx new file mode 100644 index 0000000..564ef71 --- /dev/null +++ b/front_minimal/src/utils/with-loading-props.jsx @@ -0,0 +1,19 @@ +import { useContext, createContext } from 'react'; + +// ---------------------------------------------------------------------- + +export function withLoadingProps(loader) { + const LoadingPropsContext = createContext({}); + + const useLoadingProps = () => useContext(LoadingPropsContext); + + const DynamicComponent = loader(useLoadingProps); + + const WithLoadingPropsComponent = (props) => ( + + + + ); + + return WithLoadingPropsComponent; +} diff --git a/front_minimal/yarn.lock b/front_minimal/yarn.lock new file mode 100644 index 0000000..e392ff2 --- /dev/null +++ b/front_minimal/yarn.lock @@ -0,0 +1,8795 @@ +# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. +# yarn lockfile v1 + + +"@aashutoshrathi/word-wrap@^1.2.3": + version "1.2.6" + resolved "https://registry.npmjs.org/@aashutoshrathi/word-wrap/-/word-wrap-1.2.6.tgz" + integrity sha512-1Yjs2SvM8TflER/OD3cOjhWWOZb58A2t7wpE2S9XfBYTiIl+XFhQG2bjy4Pu1I+EAlCNUzRDYDdFwFYUKvXcIA== + +"@ampproject/remapping@^2.2.0": + version "2.2.1" + resolved "https://registry.npmjs.org/@ampproject/remapping/-/remapping-2.2.1.tgz" + integrity sha512-lFMjJTrFL3j7L9yBxwYfCq2k6qqwHyzuUl/XBnif78PWTJYyL/dfowQHWE3sp6U6ZzqWiiIZnpTMO96zhkjwtg== + dependencies: + "@jridgewell/gen-mapping" "^0.3.0" + "@jridgewell/trace-mapping" "^0.3.9" + +"@auth0/auth0-react@^2.2.4": + version "2.2.4" + resolved "https://registry.npmjs.org/@auth0/auth0-react/-/auth0-react-2.2.4.tgz" + integrity sha512-l29PQC0WdgkCoOc6WeMAY26gsy/yXJICW0jHfj0nz8rZZphYKrLNqTRWFFCMJY+sagza9tSgB1kG/UvQYgGh9A== + dependencies: + "@auth0/auth0-spa-js" "^2.1.3" + +"@auth0/auth0-spa-js@^2.1.3": + version "2.1.3" + resolved "https://registry.npmjs.org/@auth0/auth0-spa-js/-/auth0-spa-js-2.1.3.tgz" + integrity sha512-NMTBNuuG4g3rame1aCnNS5qFYIzsTUV5qTFPRfTyYFS1feS6jsCBR+eTq9YkxCp1yuoM2UIcjunPaoPl77U9xQ== + +"@aws-amplify/analytics@7.0.35": + version "7.0.35" + resolved "https://registry.npmjs.org/@aws-amplify/analytics/-/analytics-7.0.35.tgz" + integrity sha512-+PjJSQz59VlOGF4HdvLkCzNpYkkvFrob+I4yLK9jYDj+sZzbKiECK+IjqWpOy4iO1sZo36+rpET6EPAQOBCQbA== + dependencies: + "@aws-sdk/client-firehose" "3.398.0" + "@aws-sdk/client-kinesis" "3.398.0" + "@aws-sdk/client-personalize-events" "3.398.0" + "@smithy/util-utf8" "2.0.0" + tslib "^2.5.0" + +"@aws-amplify/api-graphql@4.1.6": + version "4.1.6" + resolved "https://registry.npmjs.org/@aws-amplify/api-graphql/-/api-graphql-4.1.6.tgz" + integrity sha512-FwsmqUracVPYW2sUqpdBrUSxCYYEWcye8/ZedvFvF5baAB1hwVtt3XMzpP50iCJnb+ueNxw0Rbc5dpkt+ZQ6nQ== + dependencies: + "@aws-amplify/api-rest" "4.0.35" + "@aws-amplify/core" "6.3.2" + "@aws-amplify/data-schema" "^1.0.0" + "@aws-sdk/types" "3.387.0" + graphql "15.8.0" + rxjs "^7.8.1" + tslib "^2.5.0" + uuid "^9.0.0" + +"@aws-amplify/api-rest@4.0.35": + version "4.0.35" + resolved "https://registry.npmjs.org/@aws-amplify/api-rest/-/api-rest-4.0.35.tgz" + integrity sha512-e39VxlCIKqbI1KWIKFIG0a3/grJGK5BKM3qobJXEyxDhtljr1PZy8URUahpyIV0IJtD4XEj+IXIAN1e0rQztCw== + dependencies: + tslib "^2.5.0" + +"@aws-amplify/api@6.0.37": + version "6.0.37" + resolved "https://registry.npmjs.org/@aws-amplify/api/-/api-6.0.37.tgz" + integrity sha512-fwHWBdjbljJ5nUmWdREm1Ydw04KEAw7WfTZmkEaRJ4LZo6sPu5e5ucb/7mKUzt/xrlKBjKkqSkFusBUkz+S24w== + dependencies: + "@aws-amplify/api-graphql" "4.1.6" + "@aws-amplify/api-rest" "4.0.35" + tslib "^2.5.0" + +"@aws-amplify/auth@6.3.5": + version "6.3.5" + resolved "https://registry.npmjs.org/@aws-amplify/auth/-/auth-6.3.5.tgz" + integrity sha512-vPg+ipug3S1Q698ixWg+q7GV5qOrJJSMZQ0oTLmy1sPcb/o7SJLd6DmwrmguDfgue6x6JDELSAZjaKKJZerA3g== + dependencies: + tslib "^2.5.0" + +"@aws-amplify/core@^6.1.0", "@aws-amplify/core@6.3.2": + version "6.3.2" + resolved "https://registry.npmjs.org/@aws-amplify/core/-/core-6.3.2.tgz" + integrity sha512-ulRpIIBVIbnouwNyd9kSwXXcPbwLP+jq2ZYbc6xjpH/8Vo+PwzinTecdi01lUdZC6wRJCKZYNoGYwdA+QAR2qw== + dependencies: + "@aws-crypto/sha256-js" "5.2.0" + "@aws-sdk/types" "3.398.0" + "@smithy/util-hex-encoding" "2.0.0" + "@types/uuid" "^9.0.0" + js-cookie "^3.0.5" + rxjs "^7.8.1" + tslib "^2.5.0" + uuid "^9.0.0" + +"@aws-amplify/data-schema-types@*": + version "1.0.1" + resolved "https://registry.npmjs.org/@aws-amplify/data-schema-types/-/data-schema-types-1.0.1.tgz" + integrity sha512-+hRNzVuVkhjLl7Oxcse087y/PYKSjCETHE0KnRNYzQy5f/dzYw1sE8ui76bk5TR2O+vs7f8P42Ti90sWOgSzSQ== + dependencies: + graphql "15.8.0" + rxjs "^7.8.1" + +"@aws-amplify/data-schema@^1.0.0": + version "1.3.1" + resolved "https://registry.npmjs.org/@aws-amplify/data-schema/-/data-schema-1.3.1.tgz" + integrity sha512-GJa1bficIFNKWpRQTbLx+JBCr3Oqm/2t20I1v8Q9qzZKm9dZs8tcnsGBXiEmxRK2uPM7cyXqxHIbPWn7xs7z7A== + dependencies: + "@aws-amplify/data-schema-types" "*" + "@types/aws-lambda" "^8.10.134" + rxjs "^7.8.1" + +"@aws-amplify/datastore@5.0.37": + version "5.0.37" + resolved "https://registry.npmjs.org/@aws-amplify/datastore/-/datastore-5.0.37.tgz" + integrity sha512-J7h4wZ+Iu8dKWnick60ScxI5RVldCIXeOLd3NVubjp1exBZbfy84WwrWVsJuJMDYfBsPFaBHtyCuT8Ibf3IIVg== + dependencies: + "@aws-amplify/api" "6.0.37" + buffer "4.9.2" + idb "5.0.6" + immer "9.0.6" + rxjs "^7.8.1" + ulid "^2.3.0" + +"@aws-amplify/notifications@2.0.35": + version "2.0.35" + resolved "https://registry.npmjs.org/@aws-amplify/notifications/-/notifications-2.0.35.tgz" + integrity sha512-2UPLZH/ibUwu+J2DLKpKgU7ZixkVzmqUFJ2OFSx6NI6M0kfBHi4OY1PVQ3h/60h27pbGDSf/nxOBuNG8YLzgCw== + dependencies: + lodash "^4.17.21" + tslib "^2.5.0" + +"@aws-amplify/storage@6.4.6": + version "6.4.6" + resolved "https://registry.npmjs.org/@aws-amplify/storage/-/storage-6.4.6.tgz" + integrity sha512-q4KyYTLX1/vp02n37aCcD9XqklNeWS5/dbyLeDwzYV+xCF7O9djpiF0v413KNJ8jBWcPosyqGD2xepn07R3VcA== + dependencies: + "@aws-sdk/types" "3.398.0" + "@smithy/md5-js" "2.0.7" + buffer "4.9.2" + fast-xml-parser "^4.2.5" + tslib "^2.5.0" + +"@aws-crypto/crc32@3.0.0": + version "3.0.0" + resolved "https://registry.npmjs.org/@aws-crypto/crc32/-/crc32-3.0.0.tgz" + integrity sha512-IzSgsrxUcsrejQbPVilIKy16kAT52EwB6zSaI+M3xxIhKh5+aldEyvI+z6erM7TCLB2BJsFrtHjp6/4/sr+3dA== + dependencies: + "@aws-crypto/util" "^3.0.0" + "@aws-sdk/types" "^3.222.0" + tslib "^1.11.1" + +"@aws-crypto/ie11-detection@^3.0.0": + version "3.0.0" + resolved "https://registry.npmjs.org/@aws-crypto/ie11-detection/-/ie11-detection-3.0.0.tgz" + integrity sha512-341lBBkiY1DfDNKai/wXM3aujNBkXR7tq1URPQDL9wi3AUbI80NR74uF1TXHMm7po1AcnFk8iu2S2IeU/+/A+Q== + dependencies: + tslib "^1.11.1" + +"@aws-crypto/sha256-browser@3.0.0": + version "3.0.0" + resolved "https://registry.npmjs.org/@aws-crypto/sha256-browser/-/sha256-browser-3.0.0.tgz" + integrity sha512-8VLmW2B+gjFbU5uMeqtQM6Nj0/F1bro80xQXCW6CQBWgosFWXTx77aeOF5CAIAmbOK64SdMBJdNr6J41yP5mvQ== + dependencies: + "@aws-crypto/ie11-detection" "^3.0.0" + "@aws-crypto/sha256-js" "^3.0.0" + "@aws-crypto/supports-web-crypto" "^3.0.0" + "@aws-crypto/util" "^3.0.0" + "@aws-sdk/types" "^3.222.0" + "@aws-sdk/util-locate-window" "^3.0.0" + "@aws-sdk/util-utf8-browser" "^3.0.0" + tslib "^1.11.1" + +"@aws-crypto/sha256-js@^3.0.0": + version "3.0.0" + resolved "https://registry.npmjs.org/@aws-crypto/sha256-js/-/sha256-js-3.0.0.tgz" + integrity sha512-PnNN7os0+yd1XvXAy23CFOmTbMaDxgxXtTKHybrJ39Y8kGzBATgBFibWJKH6BhytLI/Zyszs87xCOBNyBig6vQ== + dependencies: + "@aws-crypto/util" "^3.0.0" + "@aws-sdk/types" "^3.222.0" + tslib "^1.11.1" + +"@aws-crypto/sha256-js@3.0.0": + version "3.0.0" + resolved "https://registry.npmjs.org/@aws-crypto/sha256-js/-/sha256-js-3.0.0.tgz" + integrity sha512-PnNN7os0+yd1XvXAy23CFOmTbMaDxgxXtTKHybrJ39Y8kGzBATgBFibWJKH6BhytLI/Zyszs87xCOBNyBig6vQ== + dependencies: + "@aws-crypto/util" "^3.0.0" + "@aws-sdk/types" "^3.222.0" + tslib "^1.11.1" + +"@aws-crypto/sha256-js@5.2.0": + version "5.2.0" + resolved "https://registry.npmjs.org/@aws-crypto/sha256-js/-/sha256-js-5.2.0.tgz" + integrity sha512-FFQQyu7edu4ufvIZ+OadFpHHOt+eSTBaYaki44c+akjg7qZg9oOQeLlk77F6tSYqjDAFClrHJk9tMf0HdVyOvA== + dependencies: + "@aws-crypto/util" "^5.2.0" + "@aws-sdk/types" "^3.222.0" + tslib "^2.6.2" + +"@aws-crypto/supports-web-crypto@^3.0.0": + version "3.0.0" + resolved "https://registry.npmjs.org/@aws-crypto/supports-web-crypto/-/supports-web-crypto-3.0.0.tgz" + integrity sha512-06hBdMwUAb2WFTuGG73LSC0wfPu93xWwo5vL2et9eymgmu3Id5vFAHBbajVWiGhPO37qcsdCap/FqXvJGJWPIg== + dependencies: + tslib "^1.11.1" + +"@aws-crypto/util@^3.0.0": + version "3.0.0" + resolved "https://registry.npmjs.org/@aws-crypto/util/-/util-3.0.0.tgz" + integrity sha512-2OJlpeJpCR48CC8r+uKVChzs9Iungj9wkZrl8Z041DWEWvyIHILYKCPNzJghKsivj+S3mLo6BVc7mBNzdxA46w== + dependencies: + "@aws-sdk/types" "^3.222.0" + "@aws-sdk/util-utf8-browser" "^3.0.0" + tslib "^1.11.1" + +"@aws-crypto/util@^5.2.0": + version "5.2.0" + resolved "https://registry.npmjs.org/@aws-crypto/util/-/util-5.2.0.tgz" + integrity sha512-4RkU9EsI6ZpBve5fseQlGNUWKMa1RLPQ1dnjnQoe07ldfIzcsGb5hC5W0Dm7u423KWzawlrpbjXBrXCEv9zazQ== + dependencies: + "@aws-sdk/types" "^3.222.0" + "@smithy/util-utf8" "^2.0.0" + tslib "^2.6.2" + +"@aws-sdk/client-firehose@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/client-firehose/-/client-firehose-3.398.0.tgz" + integrity sha512-qOWNLAD7K+7LofQCeBe56xP/+XJ7C0Wmkkczra2QuA4dveYBrBftxMJcWQjiA2SY4C0GjlMcBoSdXNCtinJnIQ== + dependencies: + "@aws-crypto/sha256-browser" "3.0.0" + "@aws-crypto/sha256-js" "3.0.0" + "@aws-sdk/client-sts" "3.398.0" + "@aws-sdk/credential-provider-node" "3.398.0" + "@aws-sdk/middleware-host-header" "3.398.0" + "@aws-sdk/middleware-logger" "3.398.0" + "@aws-sdk/middleware-recursion-detection" "3.398.0" + "@aws-sdk/middleware-signing" "3.398.0" + "@aws-sdk/middleware-user-agent" "3.398.0" + "@aws-sdk/types" "3.398.0" + "@aws-sdk/util-endpoints" "3.398.0" + "@aws-sdk/util-user-agent-browser" "3.398.0" + "@aws-sdk/util-user-agent-node" "3.398.0" + "@smithy/config-resolver" "^2.0.5" + "@smithy/fetch-http-handler" "^2.0.5" + "@smithy/hash-node" "^2.0.5" + "@smithy/invalid-dependency" "^2.0.5" + "@smithy/middleware-content-length" "^2.0.5" + "@smithy/middleware-endpoint" "^2.0.5" + "@smithy/middleware-retry" "^2.0.5" + "@smithy/middleware-serde" "^2.0.5" + "@smithy/middleware-stack" "^2.0.0" + "@smithy/node-config-provider" "^2.0.5" + "@smithy/node-http-handler" "^2.0.5" + "@smithy/protocol-http" "^2.0.5" + "@smithy/smithy-client" "^2.0.5" + "@smithy/types" "^2.2.2" + "@smithy/url-parser" "^2.0.5" + "@smithy/util-base64" "^2.0.0" + "@smithy/util-body-length-browser" "^2.0.0" + "@smithy/util-body-length-node" "^2.1.0" + "@smithy/util-defaults-mode-browser" "^2.0.5" + "@smithy/util-defaults-mode-node" "^2.0.5" + "@smithy/util-retry" "^2.0.0" + "@smithy/util-utf8" "^2.0.0" + tslib "^2.5.0" + +"@aws-sdk/client-kinesis@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/client-kinesis/-/client-kinesis-3.398.0.tgz" + integrity sha512-zaOw+MwwdMpUdeUF8UVG19xcBDpQ1+8/Q2CEwu4OilTBMpcz9El+FaMVyOW4IWpVJMlDJfroZPxKkuITCHxgXA== + dependencies: + "@aws-crypto/sha256-browser" "3.0.0" + "@aws-crypto/sha256-js" "3.0.0" + "@aws-sdk/client-sts" "3.398.0" + "@aws-sdk/credential-provider-node" "3.398.0" + "@aws-sdk/middleware-host-header" "3.398.0" + "@aws-sdk/middleware-logger" "3.398.0" + "@aws-sdk/middleware-recursion-detection" "3.398.0" + "@aws-sdk/middleware-signing" "3.398.0" + "@aws-sdk/middleware-user-agent" "3.398.0" + "@aws-sdk/types" "3.398.0" + "@aws-sdk/util-endpoints" "3.398.0" + "@aws-sdk/util-user-agent-browser" "3.398.0" + "@aws-sdk/util-user-agent-node" "3.398.0" + "@smithy/config-resolver" "^2.0.5" + "@smithy/eventstream-serde-browser" "^2.0.5" + "@smithy/eventstream-serde-config-resolver" "^2.0.5" + "@smithy/eventstream-serde-node" "^2.0.5" + "@smithy/fetch-http-handler" "^2.0.5" + "@smithy/hash-node" "^2.0.5" + "@smithy/invalid-dependency" "^2.0.5" + "@smithy/middleware-content-length" "^2.0.5" + "@smithy/middleware-endpoint" "^2.0.5" + "@smithy/middleware-retry" "^2.0.5" + "@smithy/middleware-serde" "^2.0.5" + "@smithy/middleware-stack" "^2.0.0" + "@smithy/node-config-provider" "^2.0.5" + "@smithy/node-http-handler" "^2.0.5" + "@smithy/protocol-http" "^2.0.5" + "@smithy/smithy-client" "^2.0.5" + "@smithy/types" "^2.2.2" + "@smithy/url-parser" "^2.0.5" + "@smithy/util-base64" "^2.0.0" + "@smithy/util-body-length-browser" "^2.0.0" + "@smithy/util-body-length-node" "^2.1.0" + "@smithy/util-defaults-mode-browser" "^2.0.5" + "@smithy/util-defaults-mode-node" "^2.0.5" + "@smithy/util-retry" "^2.0.0" + "@smithy/util-utf8" "^2.0.0" + "@smithy/util-waiter" "^2.0.5" + tslib "^2.5.0" + +"@aws-sdk/client-personalize-events@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/client-personalize-events/-/client-personalize-events-3.398.0.tgz" + integrity sha512-dynXr8ZVMC2FxQS5QRr7cu90xAGfwgfZM5XDW2jm81UPK5Qqo2FbbEF4wvdXXbnkbvU5rsmxL1IjQiMGm+lWVg== + dependencies: + "@aws-crypto/sha256-browser" "3.0.0" + "@aws-crypto/sha256-js" "3.0.0" + "@aws-sdk/client-sts" "3.398.0" + "@aws-sdk/credential-provider-node" "3.398.0" + "@aws-sdk/middleware-host-header" "3.398.0" + "@aws-sdk/middleware-logger" "3.398.0" + "@aws-sdk/middleware-recursion-detection" "3.398.0" + "@aws-sdk/middleware-signing" "3.398.0" + "@aws-sdk/middleware-user-agent" "3.398.0" + "@aws-sdk/types" "3.398.0" + "@aws-sdk/util-endpoints" "3.398.0" + "@aws-sdk/util-user-agent-browser" "3.398.0" + "@aws-sdk/util-user-agent-node" "3.398.0" + "@smithy/config-resolver" "^2.0.5" + "@smithy/fetch-http-handler" "^2.0.5" + "@smithy/hash-node" "^2.0.5" + "@smithy/invalid-dependency" "^2.0.5" + "@smithy/middleware-content-length" "^2.0.5" + "@smithy/middleware-endpoint" "^2.0.5" + "@smithy/middleware-retry" "^2.0.5" + "@smithy/middleware-serde" "^2.0.5" + "@smithy/middleware-stack" "^2.0.0" + "@smithy/node-config-provider" "^2.0.5" + "@smithy/node-http-handler" "^2.0.5" + "@smithy/protocol-http" "^2.0.5" + "@smithy/smithy-client" "^2.0.5" + "@smithy/types" "^2.2.2" + "@smithy/url-parser" "^2.0.5" + "@smithy/util-base64" "^2.0.0" + "@smithy/util-body-length-browser" "^2.0.0" + "@smithy/util-body-length-node" "^2.1.0" + "@smithy/util-defaults-mode-browser" "^2.0.5" + "@smithy/util-defaults-mode-node" "^2.0.5" + "@smithy/util-retry" "^2.0.0" + "@smithy/util-utf8" "^2.0.0" + tslib "^2.5.0" + +"@aws-sdk/client-sso@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/client-sso/-/client-sso-3.398.0.tgz" + integrity sha512-CygL0jhfibw4kmWXG/3sfZMFNjcXo66XUuPC4BqZBk8Rj5vFoxp1vZeMkDLzTIk97Nvo5J5Bh+QnXKhub6AckQ== + dependencies: + "@aws-crypto/sha256-browser" "3.0.0" + "@aws-crypto/sha256-js" "3.0.0" + "@aws-sdk/middleware-host-header" "3.398.0" + "@aws-sdk/middleware-logger" "3.398.0" + "@aws-sdk/middleware-recursion-detection" "3.398.0" + "@aws-sdk/middleware-user-agent" "3.398.0" + "@aws-sdk/types" "3.398.0" + "@aws-sdk/util-endpoints" "3.398.0" + "@aws-sdk/util-user-agent-browser" "3.398.0" + "@aws-sdk/util-user-agent-node" "3.398.0" + "@smithy/config-resolver" "^2.0.5" + "@smithy/fetch-http-handler" "^2.0.5" + "@smithy/hash-node" "^2.0.5" + "@smithy/invalid-dependency" "^2.0.5" + "@smithy/middleware-content-length" "^2.0.5" + "@smithy/middleware-endpoint" "^2.0.5" + "@smithy/middleware-retry" "^2.0.5" + "@smithy/middleware-serde" "^2.0.5" + "@smithy/middleware-stack" "^2.0.0" + "@smithy/node-config-provider" "^2.0.5" + "@smithy/node-http-handler" "^2.0.5" + "@smithy/protocol-http" "^2.0.5" + "@smithy/smithy-client" "^2.0.5" + "@smithy/types" "^2.2.2" + "@smithy/url-parser" "^2.0.5" + "@smithy/util-base64" "^2.0.0" + "@smithy/util-body-length-browser" "^2.0.0" + "@smithy/util-body-length-node" "^2.1.0" + "@smithy/util-defaults-mode-browser" "^2.0.5" + "@smithy/util-defaults-mode-node" "^2.0.5" + "@smithy/util-retry" "^2.0.0" + "@smithy/util-utf8" "^2.0.0" + tslib "^2.5.0" + +"@aws-sdk/client-sts@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/client-sts/-/client-sts-3.398.0.tgz" + integrity sha512-/3Pa9wLMvBZipKraq3AtbmTfXW6q9kyvhwOno64f1Fz7kFb8ijQFMGoATS70B2pGEZTlxkUqJFWDiisT6Q6dFg== + dependencies: + "@aws-crypto/sha256-browser" "3.0.0" + "@aws-crypto/sha256-js" "3.0.0" + "@aws-sdk/credential-provider-node" "3.398.0" + "@aws-sdk/middleware-host-header" "3.398.0" + "@aws-sdk/middleware-logger" "3.398.0" + "@aws-sdk/middleware-recursion-detection" "3.398.0" + "@aws-sdk/middleware-sdk-sts" "3.398.0" + "@aws-sdk/middleware-signing" "3.398.0" + "@aws-sdk/middleware-user-agent" "3.398.0" + "@aws-sdk/types" "3.398.0" + "@aws-sdk/util-endpoints" "3.398.0" + "@aws-sdk/util-user-agent-browser" "3.398.0" + "@aws-sdk/util-user-agent-node" "3.398.0" + "@smithy/config-resolver" "^2.0.5" + "@smithy/fetch-http-handler" "^2.0.5" + "@smithy/hash-node" "^2.0.5" + "@smithy/invalid-dependency" "^2.0.5" + "@smithy/middleware-content-length" "^2.0.5" + "@smithy/middleware-endpoint" "^2.0.5" + "@smithy/middleware-retry" "^2.0.5" + "@smithy/middleware-serde" "^2.0.5" + "@smithy/middleware-stack" "^2.0.0" + "@smithy/node-config-provider" "^2.0.5" + "@smithy/node-http-handler" "^2.0.5" + "@smithy/protocol-http" "^2.0.5" + "@smithy/smithy-client" "^2.0.5" + "@smithy/types" "^2.2.2" + "@smithy/url-parser" "^2.0.5" + "@smithy/util-base64" "^2.0.0" + "@smithy/util-body-length-browser" "^2.0.0" + "@smithy/util-body-length-node" "^2.1.0" + "@smithy/util-defaults-mode-browser" "^2.0.5" + "@smithy/util-defaults-mode-node" "^2.0.5" + "@smithy/util-retry" "^2.0.0" + "@smithy/util-utf8" "^2.0.0" + fast-xml-parser "4.2.5" + tslib "^2.5.0" + +"@aws-sdk/credential-provider-env@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/credential-provider-env/-/credential-provider-env-3.398.0.tgz" + integrity sha512-Z8Yj5z7FroAsR6UVML+XUdlpoqEe9Dnle8c2h8/xWwIC2feTfIBhjLhRVxfbpbM1pLgBSNEcZ7U8fwq5l7ESVQ== + dependencies: + "@aws-sdk/types" "3.398.0" + "@smithy/property-provider" "^2.0.0" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/credential-provider-ini@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/credential-provider-ini/-/credential-provider-ini-3.398.0.tgz" + integrity sha512-AsK1lStK3nB9Cn6S6ODb1ktGh7SRejsNVQVKX3t5d3tgOaX+aX1Iwy8FzM/ZEN8uCloeRifUGIY9uQFygg5mSw== + dependencies: + "@aws-sdk/credential-provider-env" "3.398.0" + "@aws-sdk/credential-provider-process" "3.398.0" + "@aws-sdk/credential-provider-sso" "3.398.0" + "@aws-sdk/credential-provider-web-identity" "3.398.0" + "@aws-sdk/types" "3.398.0" + "@smithy/credential-provider-imds" "^2.0.0" + "@smithy/property-provider" "^2.0.0" + "@smithy/shared-ini-file-loader" "^2.0.0" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/credential-provider-node@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/credential-provider-node/-/credential-provider-node-3.398.0.tgz" + integrity sha512-odmI/DSKfuWUYeDnGTCEHBbC8/MwnF6yEq874zl6+owoVv0ZsYP8qBHfiJkYqrwg7wQ7Pi40sSAPC1rhesGwzg== + dependencies: + "@aws-sdk/credential-provider-env" "3.398.0" + "@aws-sdk/credential-provider-ini" "3.398.0" + "@aws-sdk/credential-provider-process" "3.398.0" + "@aws-sdk/credential-provider-sso" "3.398.0" + "@aws-sdk/credential-provider-web-identity" "3.398.0" + "@aws-sdk/types" "3.398.0" + "@smithy/credential-provider-imds" "^2.0.0" + "@smithy/property-provider" "^2.0.0" + "@smithy/shared-ini-file-loader" "^2.0.0" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/credential-provider-process@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/credential-provider-process/-/credential-provider-process-3.398.0.tgz" + integrity sha512-WrkBL1W7TXN508PA9wRXPFtzmGpVSW98gDaHEaa8GolAPHMPa5t2QcC/z/cFpglzrcVv8SA277zu9Z8tELdZhg== + dependencies: + "@aws-sdk/types" "3.398.0" + "@smithy/property-provider" "^2.0.0" + "@smithy/shared-ini-file-loader" "^2.0.0" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/credential-provider-sso@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/credential-provider-sso/-/credential-provider-sso-3.398.0.tgz" + integrity sha512-2Dl35587xbnzR/GGZqA2MnFs8+kS4wbHQO9BioU0okA+8NRueohNMdrdQmQDdSNK4BfIpFspiZmFkXFNyEAfgw== + dependencies: + "@aws-sdk/client-sso" "3.398.0" + "@aws-sdk/token-providers" "3.398.0" + "@aws-sdk/types" "3.398.0" + "@smithy/property-provider" "^2.0.0" + "@smithy/shared-ini-file-loader" "^2.0.0" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/credential-provider-web-identity@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/credential-provider-web-identity/-/credential-provider-web-identity-3.398.0.tgz" + integrity sha512-iG3905Alv9pINbQ8/MIsshgqYMbWx+NDQWpxbIW3W0MkSH3iAqdVpSCteYidYX9G/jv2Um1nW3y360ib20bvNg== + dependencies: + "@aws-sdk/types" "3.398.0" + "@smithy/property-provider" "^2.0.0" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/middleware-host-header@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/middleware-host-header/-/middleware-host-header-3.398.0.tgz" + integrity sha512-m+5laWdBaxIZK2ko0OwcCHJZJ5V1MgEIt8QVQ3k4/kOkN9ICjevOYmba751pHoTnbOYB7zQd6D2OT3EYEEsUcA== + dependencies: + "@aws-sdk/types" "3.398.0" + "@smithy/protocol-http" "^2.0.5" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/middleware-logger@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/middleware-logger/-/middleware-logger-3.398.0.tgz" + integrity sha512-CiJjW+FL12elS6Pn7/UVjVK8HWHhXMfvHZvOwx/Qkpy340sIhkuzOO6fZEruECDTZhl2Wqn81XdJ1ZQ4pRKpCg== + dependencies: + "@aws-sdk/types" "3.398.0" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/middleware-recursion-detection@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/middleware-recursion-detection/-/middleware-recursion-detection-3.398.0.tgz" + integrity sha512-7QpOqPQAZNXDXv6vsRex4R8dLniL0E/80OPK4PPFsrCh9btEyhN9Begh4i1T+5lL28hmYkztLOkTQ2N5J3hgRQ== + dependencies: + "@aws-sdk/types" "3.398.0" + "@smithy/protocol-http" "^2.0.5" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/middleware-sdk-sts@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/middleware-sdk-sts/-/middleware-sdk-sts-3.398.0.tgz" + integrity sha512-+JH76XHEgfVihkY+GurohOQ5Z83zVN1nYcQzwCFnCDTh4dG4KwhnZKG+WPw6XJECocY0R+H0ivofeALHvVWJtQ== + dependencies: + "@aws-sdk/middleware-signing" "3.398.0" + "@aws-sdk/types" "3.398.0" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/middleware-signing@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/middleware-signing/-/middleware-signing-3.398.0.tgz" + integrity sha512-O0KqXAix1TcvZBFt1qoFkHMUNJOSgjJTYS7lFTRKSwgsD27bdW2TM2r9R8DAccWFt5Amjkdt+eOwQMIXPGTm8w== + dependencies: + "@aws-sdk/types" "3.398.0" + "@smithy/property-provider" "^2.0.0" + "@smithy/protocol-http" "^2.0.5" + "@smithy/signature-v4" "^2.0.0" + "@smithy/types" "^2.2.2" + "@smithy/util-middleware" "^2.0.0" + tslib "^2.5.0" + +"@aws-sdk/middleware-user-agent@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/middleware-user-agent/-/middleware-user-agent-3.398.0.tgz" + integrity sha512-nF1jg0L+18b5HvTcYzwyFgfZQQMELJINFqI0mi4yRKaX7T5a3aGp5RVLGGju/6tAGTuFbfBoEhkhU3kkxexPYQ== + dependencies: + "@aws-sdk/types" "3.398.0" + "@aws-sdk/util-endpoints" "3.398.0" + "@smithy/protocol-http" "^2.0.5" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/token-providers@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/token-providers/-/token-providers-3.398.0.tgz" + integrity sha512-nrYgjzavGCKJL/48Vt0EL+OlIc5UZLfNGpgyUW9cv3XZwl+kXV0QB+HH0rHZZLfpbBgZ2RBIJR9uD5ieu/6hpQ== + dependencies: + "@aws-crypto/sha256-browser" "3.0.0" + "@aws-crypto/sha256-js" "3.0.0" + "@aws-sdk/middleware-host-header" "3.398.0" + "@aws-sdk/middleware-logger" "3.398.0" + "@aws-sdk/middleware-recursion-detection" "3.398.0" + "@aws-sdk/middleware-user-agent" "3.398.0" + "@aws-sdk/types" "3.398.0" + "@aws-sdk/util-endpoints" "3.398.0" + "@aws-sdk/util-user-agent-browser" "3.398.0" + "@aws-sdk/util-user-agent-node" "3.398.0" + "@smithy/config-resolver" "^2.0.5" + "@smithy/fetch-http-handler" "^2.0.5" + "@smithy/hash-node" "^2.0.5" + "@smithy/invalid-dependency" "^2.0.5" + "@smithy/middleware-content-length" "^2.0.5" + "@smithy/middleware-endpoint" "^2.0.5" + "@smithy/middleware-retry" "^2.0.5" + "@smithy/middleware-serde" "^2.0.5" + "@smithy/middleware-stack" "^2.0.0" + "@smithy/node-config-provider" "^2.0.5" + "@smithy/node-http-handler" "^2.0.5" + "@smithy/property-provider" "^2.0.0" + "@smithy/protocol-http" "^2.0.5" + "@smithy/shared-ini-file-loader" "^2.0.0" + "@smithy/smithy-client" "^2.0.5" + "@smithy/types" "^2.2.2" + "@smithy/url-parser" "^2.0.5" + "@smithy/util-base64" "^2.0.0" + "@smithy/util-body-length-browser" "^2.0.0" + "@smithy/util-body-length-node" "^2.1.0" + "@smithy/util-defaults-mode-browser" "^2.0.5" + "@smithy/util-defaults-mode-node" "^2.0.5" + "@smithy/util-retry" "^2.0.0" + "@smithy/util-utf8" "^2.0.0" + tslib "^2.5.0" + +"@aws-sdk/types@^3.222.0", "@aws-sdk/types@3.387.0": + version "3.387.0" + resolved "https://registry.npmjs.org/@aws-sdk/types/-/types-3.387.0.tgz" + integrity sha512-YTjFabNwjTF+6yl88f0/tWff018qmmgMmjlw45s6sdVKueWxdxV68U7gepNLF2nhaQPZa6FDOBoA51NaviVs0Q== + dependencies: + "@smithy/types" "^2.1.0" + tslib "^2.5.0" + +"@aws-sdk/types@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/types/-/types-3.398.0.tgz" + integrity sha512-r44fkS+vsEgKCuEuTV+TIk0t0m5ZlXHNjSDYEUvzLStbbfUFiNus/YG4UCa0wOk9R7VuQI67badsvvPeVPCGDQ== + dependencies: + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/util-endpoints@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/util-endpoints/-/util-endpoints-3.398.0.tgz" + integrity sha512-Fy0gLYAei/Rd6BrXG4baspCnWTUSd0NdokU1pZh4KlfEAEN1i8SPPgfiO5hLk7+2inqtCmqxVJlfqbMVe9k4bw== + dependencies: + "@aws-sdk/types" "3.398.0" + tslib "^2.5.0" + +"@aws-sdk/util-locate-window@^3.0.0": + version "3.568.0" + resolved "https://registry.npmjs.org/@aws-sdk/util-locate-window/-/util-locate-window-3.568.0.tgz" + integrity sha512-3nh4TINkXYr+H41QaPelCceEB2FXP3fxp93YZXB/kqJvX0U9j0N0Uk45gvsjmEPzG8XxkPEeLIfT2I1M7A6Lig== + dependencies: + tslib "^2.6.2" + +"@aws-sdk/util-user-agent-browser@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/util-user-agent-browser/-/util-user-agent-browser-3.398.0.tgz" + integrity sha512-A3Tzx1tkDHlBT+IgxmsMCHbV8LM7SwwCozq2ZjJRx0nqw3MCrrcxQFXldHeX/gdUMO+0Oocb7HGSnVODTq+0EA== + dependencies: + "@aws-sdk/types" "3.398.0" + "@smithy/types" "^2.2.2" + bowser "^2.11.0" + tslib "^2.5.0" + +"@aws-sdk/util-user-agent-node@3.398.0": + version "3.398.0" + resolved "https://registry.npmjs.org/@aws-sdk/util-user-agent-node/-/util-user-agent-node-3.398.0.tgz" + integrity sha512-RTVQofdj961ej4//fEkppFf4KXqKGMTCqJYghx3G0C/MYXbg7MGl7LjfNGtJcboRE8pfHHQ/TUWBDA7RIAPPlQ== + dependencies: + "@aws-sdk/types" "3.398.0" + "@smithy/node-config-provider" "^2.0.5" + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@aws-sdk/util-utf8-browser@^3.0.0": + version "3.259.0" + resolved "https://registry.npmjs.org/@aws-sdk/util-utf8-browser/-/util-utf8-browser-3.259.0.tgz" + integrity sha512-UvFa/vR+e19XookZF8RzFZBrw2EUkQWxiBW0yYQAhvk3C+QVGl0H3ouca8LDBlBfQKXwmW3huo/59H8rwb1wJw== + dependencies: + tslib "^2.3.1" + +"@babel/code-frame@^7.0.0", "@babel/code-frame@^7.22.13", "@babel/code-frame@^7.23.4": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.23.4.tgz" + integrity sha512-r1IONyb6Ia+jYR2vvIDhdWdlTGhqbBoFqLTQidzZ4kepUFH15ejXvFHxCVbtl7BOXIudsIubf4E81xeA3h3IXA== + dependencies: + "@babel/highlight" "^7.23.4" + chalk "^2.4.2" + +"@babel/compat-data@^7.22.6", "@babel/compat-data@^7.22.9", "@babel/compat-data@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.23.3.tgz" + integrity sha512-BmR4bWbDIoFJmJ9z2cZ8Gmm2MXgEDgjdWgpKmKWUt54UGFJdlj31ECtbaDvCG/qVdG3AQ1SfpZEs01lUFbzLOQ== + +"@babel/core@^7.0.0", "@babel/core@^7.0.0-0", "@babel/core@^7.0.0-0 || ^8.0.0-0 <8.0.0", "@babel/core@^7.12.0", "@babel/core@^7.13.0", "@babel/core@^7.21.3", "@babel/core@^7.4.0 || ^8.0.0-0 <8.0.0": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/core/-/core-7.23.3.tgz" + integrity sha512-Jg+msLuNuCJDyBvFv5+OKOUjWMZgd85bKjbICd3zWrKAo+bJ49HJufi7CQE0q0uR8NGyO6xkCACScNqyjHSZew== + dependencies: + "@ampproject/remapping" "^2.2.0" + "@babel/code-frame" "^7.22.13" + "@babel/generator" "^7.23.3" + "@babel/helper-compilation-targets" "^7.22.15" + "@babel/helper-module-transforms" "^7.23.3" + "@babel/helpers" "^7.23.2" + "@babel/parser" "^7.23.3" + "@babel/template" "^7.22.15" + "@babel/traverse" "^7.23.3" + "@babel/types" "^7.23.3" + convert-source-map "^2.0.0" + debug "^4.1.0" + gensync "^1.0.0-beta.2" + json5 "^2.2.3" + semver "^6.3.1" + +"@babel/generator@^7.23.3", "@babel/generator@^7.23.4": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/generator/-/generator-7.23.4.tgz" + integrity sha512-esuS49Cga3HcThFNebGhlgsrVLkvhqvYDTzgjfFFlHJcIfLe5jFmRRfCQ1KuBfc4Jrtn3ndLgKWAKjBE+IraYQ== + dependencies: + "@babel/types" "^7.23.4" + "@jridgewell/gen-mapping" "^0.3.2" + "@jridgewell/trace-mapping" "^0.3.17" + jsesc "^2.5.1" + +"@babel/helper-annotate-as-pure@^7.22.5": + version "7.22.5" + resolved "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.22.5.tgz" + integrity sha512-LvBTxu8bQSQkcyKOU+a1btnNFQ1dMAd0R6PyW3arXes06F6QLWLIrd681bxRPIXlrMGR3XYnW9JyML7dP3qgxg== + dependencies: + "@babel/types" "^7.22.5" + +"@babel/helper-builder-binary-assignment-operator-visitor@^7.22.15": + version "7.22.15" + resolved "https://registry.npmjs.org/@babel/helper-builder-binary-assignment-operator-visitor/-/helper-builder-binary-assignment-operator-visitor-7.22.15.tgz" + integrity sha512-QkBXwGgaoC2GtGZRoma6kv7Szfv06khvhFav67ZExau2RaXzy8MpHSMO2PNoP2XtmQphJQRHFfg77Bq731Yizw== + dependencies: + "@babel/types" "^7.22.15" + +"@babel/helper-compilation-targets@^7.22.15", "@babel/helper-compilation-targets@^7.22.6": + version "7.22.15" + resolved "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.22.15.tgz" + integrity sha512-y6EEzULok0Qvz8yyLkCvVX+02ic+By2UdOhylwUOvOn9dvYc9mKICJuuU1n1XBI02YWsNsnrY1kc6DVbjcXbtw== + dependencies: + "@babel/compat-data" "^7.22.9" + "@babel/helper-validator-option" "^7.22.15" + browserslist "^4.21.9" + lru-cache "^5.1.1" + semver "^6.3.1" + +"@babel/helper-create-class-features-plugin@^7.22.15": + version "7.22.15" + resolved "https://registry.npmjs.org/@babel/helper-create-class-features-plugin/-/helper-create-class-features-plugin-7.22.15.tgz" + integrity sha512-jKkwA59IXcvSaiK2UN45kKwSC9o+KuoXsBDvHvU/7BecYIp8GQ2UwrVvFgJASUT+hBnwJx6MhvMCuMzwZZ7jlg== + dependencies: + "@babel/helper-annotate-as-pure" "^7.22.5" + "@babel/helper-environment-visitor" "^7.22.5" + "@babel/helper-function-name" "^7.22.5" + "@babel/helper-member-expression-to-functions" "^7.22.15" + "@babel/helper-optimise-call-expression" "^7.22.5" + "@babel/helper-replace-supers" "^7.22.9" + "@babel/helper-skip-transparent-expression-wrappers" "^7.22.5" + "@babel/helper-split-export-declaration" "^7.22.6" + semver "^6.3.1" + +"@babel/helper-create-regexp-features-plugin@^7.18.6", "@babel/helper-create-regexp-features-plugin@^7.22.15", "@babel/helper-create-regexp-features-plugin@^7.22.5": + version "7.22.15" + resolved "https://registry.npmjs.org/@babel/helper-create-regexp-features-plugin/-/helper-create-regexp-features-plugin-7.22.15.tgz" + integrity sha512-29FkPLFjn4TPEa3RE7GpW+qbE8tlsu3jntNYNfcGsc49LphF1PQIiD+vMZ1z1xVOKt+93khA9tc2JBs3kBjA7w== + dependencies: + "@babel/helper-annotate-as-pure" "^7.22.5" + regexpu-core "^5.3.1" + semver "^6.3.1" + +"@babel/helper-define-polyfill-provider@^0.4.3": + version "0.4.3" + resolved "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.4.3.tgz" + integrity sha512-WBrLmuPP47n7PNwsZ57pqam6G/RGo1vw/87b0Blc53tZNGZ4x7YvZ6HgQe2vo1W/FR20OgjeZuGXzudPiXHFug== + dependencies: + "@babel/helper-compilation-targets" "^7.22.6" + "@babel/helper-plugin-utils" "^7.22.5" + debug "^4.1.1" + lodash.debounce "^4.0.8" + resolve "^1.14.2" + +"@babel/helper-environment-visitor@^7.22.20", "@babel/helper-environment-visitor@^7.22.5": + version "7.22.20" + resolved "https://registry.npmjs.org/@babel/helper-environment-visitor/-/helper-environment-visitor-7.22.20.tgz" + integrity sha512-zfedSIzFhat/gFhWfHtgWvlec0nqB9YEIVrpuwjruLlXfUSnA8cJB0miHKwqDnQ7d32aKo2xt88/xZptwxbfhA== + +"@babel/helper-function-name@^7.22.5", "@babel/helper-function-name@^7.23.0": + version "7.23.0" + resolved "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.23.0.tgz" + integrity sha512-OErEqsrxjZTJciZ4Oo+eoZqeW9UIiOcuYKRJA4ZAgV9myA+pOXhhmpfNCKjEH/auVfEYVFJ6y1Tc4r0eIApqiw== + dependencies: + "@babel/template" "^7.22.15" + "@babel/types" "^7.23.0" + +"@babel/helper-hoist-variables@^7.22.5": + version "7.22.5" + resolved "https://registry.npmjs.org/@babel/helper-hoist-variables/-/helper-hoist-variables-7.22.5.tgz" + integrity sha512-wGjk9QZVzvknA6yKIUURb8zY3grXCcOZt+/7Wcy8O2uctxhplmUPkOdlgoNhmdVee2c92JXbf1xpMtVNbfoxRw== + dependencies: + "@babel/types" "^7.22.5" + +"@babel/helper-member-expression-to-functions@^7.22.15": + version "7.23.0" + resolved "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.23.0.tgz" + integrity sha512-6gfrPwh7OuT6gZyJZvd6WbTfrqAo7vm4xCzAXOusKqq/vWdKXphTpj5klHKNmRUU6/QRGlBsyU9mAIPaWHlqJA== + dependencies: + "@babel/types" "^7.23.0" + +"@babel/helper-module-imports@^7.16.7", "@babel/helper-module-imports@^7.22.15": + version "7.22.15" + resolved "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.22.15.tgz" + integrity sha512-0pYVBnDKZO2fnSPCrgM/6WMc7eS20Fbok+0r88fp+YtWVLZrp4CkafFGIp+W0VKw4a22sgebPT99y+FDNMdP4w== + dependencies: + "@babel/types" "^7.22.15" + +"@babel/helper-module-transforms@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.23.3.tgz" + integrity sha512-7bBs4ED9OmswdfDzpz4MpWgSrV7FXlc3zIagvLFjS5H+Mk7Snr21vQ6QwrsoCGMfNC4e4LQPdoULEt4ykz0SRQ== + dependencies: + "@babel/helper-environment-visitor" "^7.22.20" + "@babel/helper-module-imports" "^7.22.15" + "@babel/helper-simple-access" "^7.22.5" + "@babel/helper-split-export-declaration" "^7.22.6" + "@babel/helper-validator-identifier" "^7.22.20" + +"@babel/helper-optimise-call-expression@^7.22.5": + version "7.22.5" + resolved "https://registry.npmjs.org/@babel/helper-optimise-call-expression/-/helper-optimise-call-expression-7.22.5.tgz" + integrity sha512-HBwaojN0xFRx4yIvpwGqxiV2tUfl7401jlok564NgB9EHS1y6QT17FmKWm4ztqjeVdXLuC4fSvHc5ePpQjoTbw== + dependencies: + "@babel/types" "^7.22.5" + +"@babel/helper-plugin-utils@^7.0.0", "@babel/helper-plugin-utils@^7.10.4", "@babel/helper-plugin-utils@^7.12.13", "@babel/helper-plugin-utils@^7.14.5", "@babel/helper-plugin-utils@^7.18.6", "@babel/helper-plugin-utils@^7.22.5", "@babel/helper-plugin-utils@^7.8.0", "@babel/helper-plugin-utils@^7.8.3": + version "7.22.5" + resolved "https://registry.npmjs.org/@babel/helper-plugin-utils/-/helper-plugin-utils-7.22.5.tgz" + integrity sha512-uLls06UVKgFG9QD4OeFYLEGteMIAa5kpTPcFL28yuCIIzsf6ZyKZMllKVOCZFhiZ5ptnwX4mtKdWCBE/uT4amg== + +"@babel/helper-remap-async-to-generator@^7.22.20": + version "7.22.20" + resolved "https://registry.npmjs.org/@babel/helper-remap-async-to-generator/-/helper-remap-async-to-generator-7.22.20.tgz" + integrity sha512-pBGyV4uBqOns+0UvhsTO8qgl8hO89PmiDYv+/COyp1aeMcmfrfruz+/nCMFiYyFF/Knn0yfrC85ZzNFjembFTw== + dependencies: + "@babel/helper-annotate-as-pure" "^7.22.5" + "@babel/helper-environment-visitor" "^7.22.20" + "@babel/helper-wrap-function" "^7.22.20" + +"@babel/helper-replace-supers@^7.22.20", "@babel/helper-replace-supers@^7.22.9": + version "7.22.20" + resolved "https://registry.npmjs.org/@babel/helper-replace-supers/-/helper-replace-supers-7.22.20.tgz" + integrity sha512-qsW0In3dbwQUbK8kejJ4R7IHVGwHJlV6lpG6UA7a9hSa2YEiAib+N1T2kr6PEeUT+Fl7najmSOS6SmAwCHK6Tw== + dependencies: + "@babel/helper-environment-visitor" "^7.22.20" + "@babel/helper-member-expression-to-functions" "^7.22.15" + "@babel/helper-optimise-call-expression" "^7.22.5" + +"@babel/helper-simple-access@^7.22.5": + version "7.22.5" + resolved "https://registry.npmjs.org/@babel/helper-simple-access/-/helper-simple-access-7.22.5.tgz" + integrity sha512-n0H99E/K+Bika3++WNL17POvo4rKWZ7lZEp1Q+fStVbUi8nxPQEBOlTmCOxW/0JsS56SKKQ+ojAe2pHKJHN35w== + dependencies: + "@babel/types" "^7.22.5" + +"@babel/helper-skip-transparent-expression-wrappers@^7.22.5": + version "7.22.5" + resolved "https://registry.npmjs.org/@babel/helper-skip-transparent-expression-wrappers/-/helper-skip-transparent-expression-wrappers-7.22.5.tgz" + integrity sha512-tK14r66JZKiC43p8Ki33yLBVJKlQDFoA8GYN67lWCDCqoL6EMMSuM9b+Iff2jHaM/RRFYl7K+iiru7hbRqNx8Q== + dependencies: + "@babel/types" "^7.22.5" + +"@babel/helper-split-export-declaration@^7.22.6": + version "7.22.6" + resolved "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.22.6.tgz" + integrity sha512-AsUnxuLhRYsisFiaJwvp1QF+I3KjD5FOxut14q/GzovUe6orHLesW2C7d754kRm53h5gqrz6sFl6sxc4BVtE/g== + dependencies: + "@babel/types" "^7.22.5" + +"@babel/helper-string-parser@^7.23.4": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/helper-string-parser/-/helper-string-parser-7.23.4.tgz" + integrity sha512-803gmbQdqwdf4olxrX4AJyFBV/RTr3rSmOj0rKwesmzlfhYNDEs+/iOcznzpNWlJlIlTJC2QfPFcHB6DlzdVLQ== + +"@babel/helper-validator-identifier@^7.22.20": + version "7.22.20" + resolved "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.22.20.tgz" + integrity sha512-Y4OZ+ytlatR8AI+8KZfKuL5urKp7qey08ha31L8b3BwewJAoJamTzyvxPR/5D+KkdJCGPq/+8TukHBlY10FX9A== + +"@babel/helper-validator-option@^7.22.15": + version "7.22.15" + resolved "https://registry.npmjs.org/@babel/helper-validator-option/-/helper-validator-option-7.22.15.tgz" + integrity sha512-bMn7RmyFjY/mdECUbgn9eoSY4vqvacUnS9i9vGAGttgFWesO6B4CYWA7XlpbWgBt71iv/hfbPlynohStqnu5hA== + +"@babel/helper-wrap-function@^7.22.20": + version "7.22.20" + resolved "https://registry.npmjs.org/@babel/helper-wrap-function/-/helper-wrap-function-7.22.20.tgz" + integrity sha512-pms/UwkOpnQe/PDAEdV/d7dVCoBbB+R4FvYoHGZz+4VPcg7RtYy2KP7S2lbuWM6FCSgob5wshfGESbC/hzNXZw== + dependencies: + "@babel/helper-function-name" "^7.22.5" + "@babel/template" "^7.22.15" + "@babel/types" "^7.22.19" + +"@babel/helpers@^7.23.2": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/helpers/-/helpers-7.23.4.tgz" + integrity sha512-HfcMizYz10cr3h29VqyfGL6ZWIjTwWfvYBMsBVGwpcbhNGe3wQ1ZXZRPzZoAHhd9OqHadHqjQ89iVKINXnbzuw== + dependencies: + "@babel/template" "^7.22.15" + "@babel/traverse" "^7.23.4" + "@babel/types" "^7.23.4" + +"@babel/highlight@^7.23.4": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/highlight/-/highlight-7.23.4.tgz" + integrity sha512-acGdbYSfp2WheJoJm/EBBBLh/ID8KDc64ISZ9DYtBmC8/Q204PZJLHyzeB5qMzJ5trcOkybd78M4x2KWsUq++A== + dependencies: + "@babel/helper-validator-identifier" "^7.22.20" + chalk "^2.4.2" + js-tokens "^4.0.0" + +"@babel/parser@^7.22.15", "@babel/parser@^7.23.3", "@babel/parser@^7.23.4": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/parser/-/parser-7.23.4.tgz" + integrity sha512-vf3Xna6UEprW+7t6EtOmFpHNAuxw3xqPZghy+brsnusscJRW5BMUzzHZc5ICjULee81WeUV2jjakG09MDglJXQ== + +"@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression/-/plugin-bugfix-safari-id-destructuring-collision-in-function-expression-7.23.3.tgz" + integrity sha512-iRkKcCqb7iGnq9+3G6rZ+Ciz5VywC4XNRHe57lKM+jOeYAoR0lVqdeeDRfh0tQcTfw/+vBhHn926FmQhLtlFLQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining/-/plugin-bugfix-v8-spread-parameters-in-optional-chaining-7.23.3.tgz" + integrity sha512-WwlxbfMNdVEpQjZmK5mhm7oSwD3dS6eU+Iwsi4Knl9wAletWem7kaRsGOG+8UEbRyqxY4SS5zvtfXwX+jMxUwQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-skip-transparent-expression-wrappers" "^7.22.5" + "@babel/plugin-transform-optional-chaining" "^7.23.3" + +"@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly/-/plugin-bugfix-v8-static-class-fields-redefine-readonly-7.23.3.tgz" + integrity sha512-XaJak1qcityzrX0/IU5nKHb34VaibwP3saKqG6a/tppelgllOH13LUann4ZCIBcVOeE6H18K4Vx9QKkVww3z/w== + dependencies: + "@babel/helper-environment-visitor" "^7.22.20" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-proposal-private-property-in-object@7.21.0-placeholder-for-preset-env.2": + version "7.21.0-placeholder-for-preset-env.2" + resolved "https://registry.npmjs.org/@babel/plugin-proposal-private-property-in-object/-/plugin-proposal-private-property-in-object-7.21.0-placeholder-for-preset-env.2.tgz" + integrity sha512-SOSkfJDddaM7mak6cPEpswyTRnuRltl429hMraQEglW+OkovnCzsiszTmsrlY//qLFjCpQDFRvjdm2wA5pPm9w== + +"@babel/plugin-syntax-async-generators@^7.8.4": + version "7.8.4" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-async-generators/-/plugin-syntax-async-generators-7.8.4.tgz" + integrity sha512-tycmZxkGfZaxhMRbXlPXuVFpdWlXpir2W4AMhSJgRKzk/eDlIXOhb2LHWoLpDF7TEHylV5zNhykX6KAgHJmTNw== + dependencies: + "@babel/helper-plugin-utils" "^7.8.0" + +"@babel/plugin-syntax-class-properties@^7.12.13": + version "7.12.13" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-class-properties/-/plugin-syntax-class-properties-7.12.13.tgz" + integrity sha512-fm4idjKla0YahUNgFNLCB0qySdsoPiZP3iQE3rky0mBUtMZ23yDJ9SJdg6dXTSDnulOVqiF3Hgr9nbXvXTQZYA== + dependencies: + "@babel/helper-plugin-utils" "^7.12.13" + +"@babel/plugin-syntax-class-static-block@^7.14.5": + version "7.14.5" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-class-static-block/-/plugin-syntax-class-static-block-7.14.5.tgz" + integrity sha512-b+YyPmr6ldyNnM6sqYeMWE+bgJcJpO6yS4QD7ymxgH34GBPNDM/THBh8iunyvKIZztiwLH4CJZ0RxTk9emgpjw== + dependencies: + "@babel/helper-plugin-utils" "^7.14.5" + +"@babel/plugin-syntax-dynamic-import@^7.8.3": + version "7.8.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-dynamic-import/-/plugin-syntax-dynamic-import-7.8.3.tgz" + integrity sha512-5gdGbFon+PszYzqs83S3E5mpi7/y/8M9eC90MRTZfduQOYW76ig6SOSPNe41IG5LoP3FGBn2N0RjVDSQiS94kQ== + dependencies: + "@babel/helper-plugin-utils" "^7.8.0" + +"@babel/plugin-syntax-export-namespace-from@^7.8.3": + version "7.8.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-export-namespace-from/-/plugin-syntax-export-namespace-from-7.8.3.tgz" + integrity sha512-MXf5laXo6c1IbEbegDmzGPwGNTsHZmEy6QGznu5Sh2UCWvueywb2ee+CCE4zQiZstxU9BMoQO9i6zUFSY0Kj0Q== + dependencies: + "@babel/helper-plugin-utils" "^7.8.3" + +"@babel/plugin-syntax-import-assertions@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-import-assertions/-/plugin-syntax-import-assertions-7.23.3.tgz" + integrity sha512-lPgDSU+SJLK3xmFDTV2ZRQAiM7UuUjGidwBywFavObCiZc1BeAAcMtHJKUya92hPHO+at63JJPLygilZard8jw== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-syntax-import-attributes@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-import-attributes/-/plugin-syntax-import-attributes-7.23.3.tgz" + integrity sha512-pawnE0P9g10xgoP7yKr6CK63K2FMsTE+FZidZO/1PwRdzmAPVs+HS1mAURUsgaoxammTJvULUdIkEK0gOcU2tA== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-syntax-import-meta@^7.10.4": + version "7.10.4" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-import-meta/-/plugin-syntax-import-meta-7.10.4.tgz" + integrity sha512-Yqfm+XDx0+Prh3VSeEQCPU81yC+JWZ2pDPFSS4ZdpfZhp4MkFMaDC1UqseovEKwSUpnIL7+vK+Clp7bfh0iD7g== + dependencies: + "@babel/helper-plugin-utils" "^7.10.4" + +"@babel/plugin-syntax-json-strings@^7.8.3": + version "7.8.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-json-strings/-/plugin-syntax-json-strings-7.8.3.tgz" + integrity sha512-lY6kdGpWHvjoe2vk4WrAapEuBR69EMxZl+RoGRhrFGNYVK8mOPAW8VfbT/ZgrFbXlDNiiaxQnAtgVCZ6jv30EA== + dependencies: + "@babel/helper-plugin-utils" "^7.8.0" + +"@babel/plugin-syntax-jsx@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-jsx/-/plugin-syntax-jsx-7.23.3.tgz" + integrity sha512-EB2MELswq55OHUoRZLGg/zC7QWUKfNLpE57m/S2yr1uEneIgsTgrSzXP3NXEsMkVn76OlaVVnzN+ugObuYGwhg== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-syntax-logical-assignment-operators@^7.10.4": + version "7.10.4" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-logical-assignment-operators/-/plugin-syntax-logical-assignment-operators-7.10.4.tgz" + integrity sha512-d8waShlpFDinQ5MtvGU9xDAOzKH47+FFoney2baFIoMr952hKOLp1HR7VszoZvOsV/4+RRszNY7D17ba0te0ig== + dependencies: + "@babel/helper-plugin-utils" "^7.10.4" + +"@babel/plugin-syntax-nullish-coalescing-operator@^7.8.3": + version "7.8.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-nullish-coalescing-operator/-/plugin-syntax-nullish-coalescing-operator-7.8.3.tgz" + integrity sha512-aSff4zPII1u2QD7y+F8oDsz19ew4IGEJg9SVW+bqwpwtfFleiQDMdzA/R+UlWDzfnHFCxxleFT0PMIrR36XLNQ== + dependencies: + "@babel/helper-plugin-utils" "^7.8.0" + +"@babel/plugin-syntax-numeric-separator@^7.10.4": + version "7.10.4" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-numeric-separator/-/plugin-syntax-numeric-separator-7.10.4.tgz" + integrity sha512-9H6YdfkcK/uOnY/K7/aA2xpzaAgkQn37yzWUMRK7OaPOqOpGS1+n0H5hxT9AUw9EsSjPW8SVyMJwYRtWs3X3ug== + dependencies: + "@babel/helper-plugin-utils" "^7.10.4" + +"@babel/plugin-syntax-object-rest-spread@^7.8.3": + version "7.8.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-object-rest-spread/-/plugin-syntax-object-rest-spread-7.8.3.tgz" + integrity sha512-XoqMijGZb9y3y2XskN+P1wUGiVwWZ5JmoDRwx5+3GmEplNyVM2s2Dg8ILFQm8rWM48orGy5YpI5Bl8U1y7ydlA== + dependencies: + "@babel/helper-plugin-utils" "^7.8.0" + +"@babel/plugin-syntax-optional-catch-binding@^7.8.3": + version "7.8.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-optional-catch-binding/-/plugin-syntax-optional-catch-binding-7.8.3.tgz" + integrity sha512-6VPD0Pc1lpTqw0aKoeRTMiB+kWhAoT24PA+ksWSBrFtl5SIRVpZlwN3NNPQjehA2E/91FV3RjLWoVTglWcSV3Q== + dependencies: + "@babel/helper-plugin-utils" "^7.8.0" + +"@babel/plugin-syntax-optional-chaining@^7.8.3": + version "7.8.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-optional-chaining/-/plugin-syntax-optional-chaining-7.8.3.tgz" + integrity sha512-KoK9ErH1MBlCPxV0VANkXW2/dw4vlbGDrFgz8bmUsBGYkFRcbRwMh6cIJubdPrkxRwuGdtCk0v/wPTKbQgBjkg== + dependencies: + "@babel/helper-plugin-utils" "^7.8.0" + +"@babel/plugin-syntax-private-property-in-object@^7.14.5": + version "7.14.5" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-private-property-in-object/-/plugin-syntax-private-property-in-object-7.14.5.tgz" + integrity sha512-0wVnp9dxJ72ZUJDV27ZfbSj6iHLoytYZmh3rFcxNnvsJF3ktkzLDZPy/mA17HGsaQT3/DQsWYX1f1QGWkCoVUg== + dependencies: + "@babel/helper-plugin-utils" "^7.14.5" + +"@babel/plugin-syntax-top-level-await@^7.14.5": + version "7.14.5" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-top-level-await/-/plugin-syntax-top-level-await-7.14.5.tgz" + integrity sha512-hx++upLv5U1rgYfwe1xBQUhRmU41NEvpUvrp8jkrSCdvGSnM5/qdRMtylJ6PG5OFkBaHkbTAKTnd3/YyESRHFw== + dependencies: + "@babel/helper-plugin-utils" "^7.14.5" + +"@babel/plugin-syntax-typescript@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-typescript/-/plugin-syntax-typescript-7.23.3.tgz" + integrity sha512-9EiNjVJOMwCO+43TqoTrgQ8jMwcAd0sWyXi9RPfIsLTj4R2MADDDQXELhffaUx/uJv2AYcxBgPwH6j4TIA4ytQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-syntax-unicode-sets-regex@^7.18.6": + version "7.18.6" + resolved "https://registry.npmjs.org/@babel/plugin-syntax-unicode-sets-regex/-/plugin-syntax-unicode-sets-regex-7.18.6.tgz" + integrity sha512-727YkEAPwSIQTv5im8QHz3upqp92JTWhidIC81Tdx4VJYIte/VndKf1qKrfnnhPLiPghStWfvC/iFaMCQu7Nqg== + dependencies: + "@babel/helper-create-regexp-features-plugin" "^7.18.6" + "@babel/helper-plugin-utils" "^7.18.6" + +"@babel/plugin-transform-arrow-functions@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-arrow-functions/-/plugin-transform-arrow-functions-7.23.3.tgz" + integrity sha512-NzQcQrzaQPkaEwoTm4Mhyl8jI1huEL/WWIEvudjTCMJ9aBZNpsJbMASx7EQECtQQPS/DcnFpo0FIh3LvEO9cxQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-async-generator-functions@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-async-generator-functions/-/plugin-transform-async-generator-functions-7.23.4.tgz" + integrity sha512-efdkfPhHYTtn0G6n2ddrESE91fgXxjlqLsnUtPWnJs4a4mZIbUaK7ffqKIIUKXSHwcDvaCVX6GXkaJJFqtX7jw== + dependencies: + "@babel/helper-environment-visitor" "^7.22.20" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-remap-async-to-generator" "^7.22.20" + "@babel/plugin-syntax-async-generators" "^7.8.4" + +"@babel/plugin-transform-async-to-generator@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.23.3.tgz" + integrity sha512-A7LFsKi4U4fomjqXJlZg/u0ft/n8/7n7lpffUP/ZULx/DtV9SGlNKZolHH6PE8Xl1ngCc0M11OaeZptXVkfKSw== + dependencies: + "@babel/helper-module-imports" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-remap-async-to-generator" "^7.22.20" + +"@babel/plugin-transform-block-scoped-functions@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-block-scoped-functions/-/plugin-transform-block-scoped-functions-7.23.3.tgz" + integrity sha512-vI+0sIaPIO6CNuM9Kk5VmXcMVRiOpDh7w2zZt9GXzmE/9KD70CUEVhvPR/etAeNK/FAEkhxQtXOzVF3EuRL41A== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-block-scoping@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-block-scoping/-/plugin-transform-block-scoping-7.23.4.tgz" + integrity sha512-0QqbP6B6HOh7/8iNR4CQU2Th/bbRtBp4KS9vcaZd1fZ0wSh5Fyssg0UCIHwxh+ka+pNDREbVLQnHCMHKZfPwfw== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-class-properties@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-class-properties/-/plugin-transform-class-properties-7.23.3.tgz" + integrity sha512-uM+AN8yCIjDPccsKGlw271xjJtGii+xQIF/uMPS8H15L12jZTsLfF4o5vNO7d/oUguOyfdikHGc/yi9ge4SGIg== + dependencies: + "@babel/helper-create-class-features-plugin" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-class-static-block@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-class-static-block/-/plugin-transform-class-static-block-7.23.4.tgz" + integrity sha512-nsWu/1M+ggti1SOALj3hfx5FXzAY06fwPJsUZD4/A5e1bWi46VUIWtD+kOX6/IdhXGsXBWllLFDSnqSCdUNydQ== + dependencies: + "@babel/helper-create-class-features-plugin" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-class-static-block" "^7.14.5" + +"@babel/plugin-transform-classes@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-classes/-/plugin-transform-classes-7.23.3.tgz" + integrity sha512-FGEQmugvAEu2QtgtU0uTASXevfLMFfBeVCIIdcQhn/uBQsMTjBajdnAtanQlOcuihWh10PZ7+HWvc7NtBwP74w== + dependencies: + "@babel/helper-annotate-as-pure" "^7.22.5" + "@babel/helper-compilation-targets" "^7.22.15" + "@babel/helper-environment-visitor" "^7.22.20" + "@babel/helper-function-name" "^7.23.0" + "@babel/helper-optimise-call-expression" "^7.22.5" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-replace-supers" "^7.22.20" + "@babel/helper-split-export-declaration" "^7.22.6" + globals "^11.1.0" + +"@babel/plugin-transform-computed-properties@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-computed-properties/-/plugin-transform-computed-properties-7.23.3.tgz" + integrity sha512-dTj83UVTLw/+nbiHqQSFdwO9CbTtwq1DsDqm3CUEtDrZNET5rT5E6bIdTlOftDTDLMYxvxHNEYO4B9SLl8SLZw== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/template" "^7.22.15" + +"@babel/plugin-transform-destructuring@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.23.3.tgz" + integrity sha512-n225npDqjDIr967cMScVKHXJs7rout1q+tt50inyBCPkyZ8KxeI6d+GIbSBTT/w/9WdlWDOej3V9HE5Lgk57gw== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-dotall-regex@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-dotall-regex/-/plugin-transform-dotall-regex-7.23.3.tgz" + integrity sha512-vgnFYDHAKzFaTVp+mneDsIEbnJ2Np/9ng9iviHw3P/KVcgONxpNULEW/51Z/BaFojG2GI2GwwXck5uV1+1NOYQ== + dependencies: + "@babel/helper-create-regexp-features-plugin" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-duplicate-keys@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-duplicate-keys/-/plugin-transform-duplicate-keys-7.23.3.tgz" + integrity sha512-RrqQ+BQmU3Oyav3J+7/myfvRCq7Tbz+kKLLshUmMwNlDHExbGL7ARhajvoBJEvc+fCguPPu887N+3RRXBVKZUA== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-dynamic-import@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-dynamic-import/-/plugin-transform-dynamic-import-7.23.4.tgz" + integrity sha512-V6jIbLhdJK86MaLh4Jpghi8ho5fGzt3imHOBu/x0jlBaPYqDoWz4RDXjmMOfnh+JWNaQleEAByZLV0QzBT4YQQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-dynamic-import" "^7.8.3" + +"@babel/plugin-transform-exponentiation-operator@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-exponentiation-operator/-/plugin-transform-exponentiation-operator-7.23.3.tgz" + integrity sha512-5fhCsl1odX96u7ILKHBj4/Y8vipoqwsJMh4csSA8qFfxrZDEA4Ssku2DyNvMJSmZNOEBT750LfFPbtrnTP90BQ== + dependencies: + "@babel/helper-builder-binary-assignment-operator-visitor" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-export-namespace-from@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-export-namespace-from/-/plugin-transform-export-namespace-from-7.23.4.tgz" + integrity sha512-GzuSBcKkx62dGzZI1WVgTWvkkz84FZO5TC5T8dl/Tht/rAla6Dg/Mz9Yhypg+ezVACf/rgDuQt3kbWEv7LdUDQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-export-namespace-from" "^7.8.3" + +"@babel/plugin-transform-for-of@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.23.3.tgz" + integrity sha512-X8jSm8X1CMwxmK878qsUGJRmbysKNbdpTv/O1/v0LuY/ZkZrng5WYiekYSdg9m09OTmDDUWeEDsTE+17WYbAZw== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-function-name@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-function-name/-/plugin-transform-function-name-7.23.3.tgz" + integrity sha512-I1QXp1LxIvt8yLaib49dRW5Okt7Q4oaxao6tFVKS/anCdEOMtYwWVKoiOA1p34GOWIZjUK0E+zCp7+l1pfQyiw== + dependencies: + "@babel/helper-compilation-targets" "^7.22.15" + "@babel/helper-function-name" "^7.23.0" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-json-strings@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-json-strings/-/plugin-transform-json-strings-7.23.4.tgz" + integrity sha512-81nTOqM1dMwZ/aRXQ59zVubN9wHGqk6UtqRK+/q+ciXmRy8fSolhGVvG09HHRGo4l6fr/c4ZhXUQH0uFW7PZbg== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-json-strings" "^7.8.3" + +"@babel/plugin-transform-literals@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-literals/-/plugin-transform-literals-7.23.3.tgz" + integrity sha512-wZ0PIXRxnwZvl9AYpqNUxpZ5BiTGrYt7kueGQ+N5FiQ7RCOD4cm8iShd6S6ggfVIWaJf2EMk8eRzAh52RfP4rQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-logical-assignment-operators@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-logical-assignment-operators/-/plugin-transform-logical-assignment-operators-7.23.4.tgz" + integrity sha512-Mc/ALf1rmZTP4JKKEhUwiORU+vcfarFVLfcFiolKUo6sewoxSEgl36ak5t+4WamRsNr6nzjZXQjM35WsU+9vbg== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-logical-assignment-operators" "^7.10.4" + +"@babel/plugin-transform-member-expression-literals@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-member-expression-literals/-/plugin-transform-member-expression-literals-7.23.3.tgz" + integrity sha512-sC3LdDBDi5x96LA+Ytekz2ZPk8i/Ck+DEuDbRAll5rknJ5XRTSaPKEYwomLcs1AA8wg9b3KjIQRsnApj+q51Ag== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-modules-amd@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.23.3.tgz" + integrity sha512-vJYQGxeKM4t8hYCKVBlZX/gtIY2I7mRGFNcm85sgXGMTBcoV3QdVtdpbcWEbzbfUIUZKwvgFT82mRvaQIebZzw== + dependencies: + "@babel/helper-module-transforms" "^7.23.3" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-modules-commonjs@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.23.3.tgz" + integrity sha512-aVS0F65LKsdNOtcz6FRCpE4OgsP2OFnW46qNxNIX9h3wuzaNcSQsJysuMwqSibC98HPrf2vCgtxKNwS0DAlgcA== + dependencies: + "@babel/helper-module-transforms" "^7.23.3" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-simple-access" "^7.22.5" + +"@babel/plugin-transform-modules-systemjs@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.23.3.tgz" + integrity sha512-ZxyKGTkF9xT9YJuKQRo19ewf3pXpopuYQd8cDXqNzc3mUNbOME0RKMoZxviQk74hwzfQsEe66dE92MaZbdHKNQ== + dependencies: + "@babel/helper-hoist-variables" "^7.22.5" + "@babel/helper-module-transforms" "^7.23.3" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-validator-identifier" "^7.22.20" + +"@babel/plugin-transform-modules-umd@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-modules-umd/-/plugin-transform-modules-umd-7.23.3.tgz" + integrity sha512-zHsy9iXX2nIsCBFPud3jKn1IRPWg3Ing1qOZgeKV39m1ZgIdpJqvlWVeiHBZC6ITRG0MfskhYe9cLgntfSFPIg== + dependencies: + "@babel/helper-module-transforms" "^7.23.3" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-named-capturing-groups-regex@^7.22.5": + version "7.22.5" + resolved "https://registry.npmjs.org/@babel/plugin-transform-named-capturing-groups-regex/-/plugin-transform-named-capturing-groups-regex-7.22.5.tgz" + integrity sha512-YgLLKmS3aUBhHaxp5hi1WJTgOUb/NCuDHzGT9z9WTt3YG+CPRhJs6nprbStx6DnWM4dh6gt7SU3sZodbZ08adQ== + dependencies: + "@babel/helper-create-regexp-features-plugin" "^7.22.5" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-new-target@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-new-target/-/plugin-transform-new-target-7.23.3.tgz" + integrity sha512-YJ3xKqtJMAT5/TIZnpAR3I+K+WaDowYbN3xyxI8zxx/Gsypwf9B9h0VB+1Nh6ACAAPRS5NSRje0uVv5i79HYGQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-nullish-coalescing-operator@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-nullish-coalescing-operator/-/plugin-transform-nullish-coalescing-operator-7.23.4.tgz" + integrity sha512-jHE9EVVqHKAQx+VePv5LLGHjmHSJR76vawFPTdlxR/LVJPfOEGxREQwQfjuZEOPTwG92X3LINSh3M40Rv4zpVA== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-nullish-coalescing-operator" "^7.8.3" + +"@babel/plugin-transform-numeric-separator@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-numeric-separator/-/plugin-transform-numeric-separator-7.23.4.tgz" + integrity sha512-mps6auzgwjRrwKEZA05cOwuDc9FAzoyFS4ZsG/8F43bTLf/TgkJg7QXOrPO1JO599iA3qgK9MXdMGOEC8O1h6Q== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-numeric-separator" "^7.10.4" + +"@babel/plugin-transform-object-rest-spread@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-object-rest-spread/-/plugin-transform-object-rest-spread-7.23.4.tgz" + integrity sha512-9x9K1YyeQVw0iOXJlIzwm8ltobIIv7j2iLyP2jIhEbqPRQ7ScNgwQufU2I0Gq11VjyG4gI4yMXt2VFags+1N3g== + dependencies: + "@babel/compat-data" "^7.23.3" + "@babel/helper-compilation-targets" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-object-rest-spread" "^7.8.3" + "@babel/plugin-transform-parameters" "^7.23.3" + +"@babel/plugin-transform-object-super@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-object-super/-/plugin-transform-object-super-7.23.3.tgz" + integrity sha512-BwQ8q0x2JG+3lxCVFohg+KbQM7plfpBwThdW9A6TMtWwLsbDA01Ek2Zb/AgDN39BiZsExm4qrXxjk+P1/fzGrA== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-replace-supers" "^7.22.20" + +"@babel/plugin-transform-optional-catch-binding@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-optional-catch-binding/-/plugin-transform-optional-catch-binding-7.23.4.tgz" + integrity sha512-XIq8t0rJPHf6Wvmbn9nFxU6ao4c7WhghTR5WyV8SrJfUFzyxhCm4nhC+iAp3HFhbAKLfYpgzhJ6t4XCtVwqO5A== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-optional-catch-binding" "^7.8.3" + +"@babel/plugin-transform-optional-chaining@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-optional-chaining/-/plugin-transform-optional-chaining-7.23.4.tgz" + integrity sha512-ZU8y5zWOfjM5vZ+asjgAPwDaBjJzgufjES89Rs4Lpq63O300R/kOz30WCLo6BxxX6QVEilwSlpClnG5cZaikTA== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-skip-transparent-expression-wrappers" "^7.22.5" + "@babel/plugin-syntax-optional-chaining" "^7.8.3" + +"@babel/plugin-transform-parameters@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-parameters/-/plugin-transform-parameters-7.23.3.tgz" + integrity sha512-09lMt6UsUb3/34BbECKVbVwrT9bO6lILWln237z7sLaWnMsTi7Yc9fhX5DLpkJzAGfaReXI22wP41SZmnAA3Vw== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-private-methods@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-private-methods/-/plugin-transform-private-methods-7.23.3.tgz" + integrity sha512-UzqRcRtWsDMTLrRWFvUBDwmw06tCQH9Rl1uAjfh6ijMSmGYQ+fpdB+cnqRC8EMh5tuuxSv0/TejGL+7vyj+50g== + dependencies: + "@babel/helper-create-class-features-plugin" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-private-property-in-object@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-private-property-in-object/-/plugin-transform-private-property-in-object-7.23.4.tgz" + integrity sha512-9G3K1YqTq3F4Vt88Djx1UZ79PDyj+yKRnUy7cZGSMe+a7jkwD259uKKuUzQlPkGam7R+8RJwh5z4xO27fA1o2A== + dependencies: + "@babel/helper-annotate-as-pure" "^7.22.5" + "@babel/helper-create-class-features-plugin" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-private-property-in-object" "^7.14.5" + +"@babel/plugin-transform-property-literals@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-property-literals/-/plugin-transform-property-literals-7.23.3.tgz" + integrity sha512-jR3Jn3y7cZp4oEWPFAlRsSWjxKe4PZILGBSd4nis1TsC5qeSpb+nrtihJuDhNI7QHiVbUaiXa0X2RZY3/TI6Nw== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-react-constant-elements@^7.21.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-react-constant-elements/-/plugin-transform-react-constant-elements-7.23.3.tgz" + integrity sha512-zP0QKq/p6O42OL94udMgSfKXyse4RyJ0JqbQ34zDAONWjyrEsghYEyTSK5FIpmXmCpB55SHokL1cRRKHv8L2Qw== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-react-display-name@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-react-display-name/-/plugin-transform-react-display-name-7.23.3.tgz" + integrity sha512-GnvhtVfA2OAtzdX58FJxU19rhoGeQzyVndw3GgtdECQvQFXPEZIOVULHVZGAYmOgmqjXpVpfocAbSjh99V/Fqw== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-react-jsx-development@^7.22.5": + version "7.22.5" + resolved "https://registry.npmjs.org/@babel/plugin-transform-react-jsx-development/-/plugin-transform-react-jsx-development-7.22.5.tgz" + integrity sha512-bDhuzwWMuInwCYeDeMzyi7TaBgRQei6DqxhbyniL7/VG4RSS7HtSL2QbY4eESy1KJqlWt8g3xeEBGPuo+XqC8A== + dependencies: + "@babel/plugin-transform-react-jsx" "^7.22.5" + +"@babel/plugin-transform-react-jsx@^7.22.15", "@babel/plugin-transform-react-jsx@^7.22.5": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-react-jsx/-/plugin-transform-react-jsx-7.23.4.tgz" + integrity sha512-5xOpoPguCZCRbo/JeHlloSkTA8Bld1J/E1/kLfD1nsuiW1m8tduTA1ERCgIZokDflX/IBzKcqR3l7VlRgiIfHA== + dependencies: + "@babel/helper-annotate-as-pure" "^7.22.5" + "@babel/helper-module-imports" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-jsx" "^7.23.3" + "@babel/types" "^7.23.4" + +"@babel/plugin-transform-react-pure-annotations@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-react-pure-annotations/-/plugin-transform-react-pure-annotations-7.23.3.tgz" + integrity sha512-qMFdSS+TUhB7Q/3HVPnEdYJDQIk57jkntAwSuz9xfSE4n+3I+vHYCli3HoHawN1Z3RfCz/y1zXA/JXjG6cVImQ== + dependencies: + "@babel/helper-annotate-as-pure" "^7.22.5" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-regenerator@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-regenerator/-/plugin-transform-regenerator-7.23.3.tgz" + integrity sha512-KP+75h0KghBMcVpuKisx3XTu9Ncut8Q8TuvGO4IhY+9D5DFEckQefOuIsB/gQ2tG71lCke4NMrtIPS8pOj18BQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + regenerator-transform "^0.15.2" + +"@babel/plugin-transform-reserved-words@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-reserved-words/-/plugin-transform-reserved-words-7.23.3.tgz" + integrity sha512-QnNTazY54YqgGxwIexMZva9gqbPa15t/x9VS+0fsEFWplwVpXYZivtgl43Z1vMpc1bdPP2PP8siFeVcnFvA3Cg== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-shorthand-properties@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-shorthand-properties/-/plugin-transform-shorthand-properties-7.23.3.tgz" + integrity sha512-ED2fgqZLmexWiN+YNFX26fx4gh5qHDhn1O2gvEhreLW2iI63Sqm4llRLCXALKrCnbN4Jy0VcMQZl/SAzqug/jg== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-spread@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-spread/-/plugin-transform-spread-7.23.3.tgz" + integrity sha512-VvfVYlrlBVu+77xVTOAoxQ6mZbnIq5FM0aGBSFEcIh03qHf+zNqA4DC/3XMUozTg7bZV3e3mZQ0i13VB6v5yUg== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-skip-transparent-expression-wrappers" "^7.22.5" + +"@babel/plugin-transform-sticky-regex@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-sticky-regex/-/plugin-transform-sticky-regex-7.23.3.tgz" + integrity sha512-HZOyN9g+rtvnOU3Yh7kSxXrKbzgrm5X4GncPY1QOquu7epga5MxKHVpYu2hvQnry/H+JjckSYRb93iNfsioAGg== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-template-literals@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.23.3.tgz" + integrity sha512-Flok06AYNp7GV2oJPZZcP9vZdszev6vPBkHLwxwSpaIqx75wn6mUd3UFWsSsA0l8nXAKkyCmL/sR02m8RYGeHg== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-typeof-symbol@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.23.3.tgz" + integrity sha512-4t15ViVnaFdrPC74be1gXBSMzXk3B4Us9lP7uLRQHTFpV5Dvt33pn+2MyyNxmN3VTTm3oTrZVMUmuw3oBnQ2oQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-typescript@^7.23.3": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/plugin-transform-typescript/-/plugin-transform-typescript-7.23.4.tgz" + integrity sha512-39hCCOl+YUAyMOu6B9SmUTiHUU0t/CxJNUmY3qRdJujbqi+lrQcL11ysYUsAvFWPBdhihrv1z0oRG84Yr3dODQ== + dependencies: + "@babel/helper-annotate-as-pure" "^7.22.5" + "@babel/helper-create-class-features-plugin" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/plugin-syntax-typescript" "^7.23.3" + +"@babel/plugin-transform-unicode-escapes@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-unicode-escapes/-/plugin-transform-unicode-escapes-7.23.3.tgz" + integrity sha512-OMCUx/bU6ChE3r4+ZdylEqAjaQgHAgipgW8nsCfu5pGqDcFytVd91AwRvUJSBZDz0exPGgnjoqhgRYLRjFZc9Q== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-unicode-property-regex@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-unicode-property-regex/-/plugin-transform-unicode-property-regex-7.23.3.tgz" + integrity sha512-KcLIm+pDZkWZQAFJ9pdfmh89EwVfmNovFBcXko8szpBeF8z68kWIPeKlmSOkT9BXJxs2C0uk+5LxoxIv62MROA== + dependencies: + "@babel/helper-create-regexp-features-plugin" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-unicode-regex@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-unicode-regex/-/plugin-transform-unicode-regex-7.23.3.tgz" + integrity sha512-wMHpNA4x2cIA32b/ci3AfwNgheiva2W0WUKWTK7vBHBhDKfPsc5cFGNWm69WBqpwd86u1qwZ9PWevKqm1A3yAw== + dependencies: + "@babel/helper-create-regexp-features-plugin" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/plugin-transform-unicode-sets-regex@^7.23.3": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/plugin-transform-unicode-sets-regex/-/plugin-transform-unicode-sets-regex-7.23.3.tgz" + integrity sha512-W7lliA/v9bNR83Qc3q1ip9CQMZ09CcHDbHfbLRDNuAhn1Mvkr1ZNF7hPmztMQvtTGVLJ9m8IZqWsTkXOml8dbw== + dependencies: + "@babel/helper-create-regexp-features-plugin" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + +"@babel/preset-env@^7.20.2": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.23.3.tgz" + integrity sha512-ovzGc2uuyNfNAs/jyjIGxS8arOHS5FENZaNn4rtE7UdKMMkqHCvboHfcuhWLZNX5cB44QfcGNWjaevxMzzMf+Q== + dependencies: + "@babel/compat-data" "^7.23.3" + "@babel/helper-compilation-targets" "^7.22.15" + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-validator-option" "^7.22.15" + "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression" "^7.23.3" + "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining" "^7.23.3" + "@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly" "^7.23.3" + "@babel/plugin-proposal-private-property-in-object" "7.21.0-placeholder-for-preset-env.2" + "@babel/plugin-syntax-async-generators" "^7.8.4" + "@babel/plugin-syntax-class-properties" "^7.12.13" + "@babel/plugin-syntax-class-static-block" "^7.14.5" + "@babel/plugin-syntax-dynamic-import" "^7.8.3" + "@babel/plugin-syntax-export-namespace-from" "^7.8.3" + "@babel/plugin-syntax-import-assertions" "^7.23.3" + "@babel/plugin-syntax-import-attributes" "^7.23.3" + "@babel/plugin-syntax-import-meta" "^7.10.4" + "@babel/plugin-syntax-json-strings" "^7.8.3" + "@babel/plugin-syntax-logical-assignment-operators" "^7.10.4" + "@babel/plugin-syntax-nullish-coalescing-operator" "^7.8.3" + "@babel/plugin-syntax-numeric-separator" "^7.10.4" + "@babel/plugin-syntax-object-rest-spread" "^7.8.3" + "@babel/plugin-syntax-optional-catch-binding" "^7.8.3" + "@babel/plugin-syntax-optional-chaining" "^7.8.3" + "@babel/plugin-syntax-private-property-in-object" "^7.14.5" + "@babel/plugin-syntax-top-level-await" "^7.14.5" + "@babel/plugin-syntax-unicode-sets-regex" "^7.18.6" + "@babel/plugin-transform-arrow-functions" "^7.23.3" + "@babel/plugin-transform-async-generator-functions" "^7.23.3" + "@babel/plugin-transform-async-to-generator" "^7.23.3" + "@babel/plugin-transform-block-scoped-functions" "^7.23.3" + "@babel/plugin-transform-block-scoping" "^7.23.3" + "@babel/plugin-transform-class-properties" "^7.23.3" + "@babel/plugin-transform-class-static-block" "^7.23.3" + "@babel/plugin-transform-classes" "^7.23.3" + "@babel/plugin-transform-computed-properties" "^7.23.3" + "@babel/plugin-transform-destructuring" "^7.23.3" + "@babel/plugin-transform-dotall-regex" "^7.23.3" + "@babel/plugin-transform-duplicate-keys" "^7.23.3" + "@babel/plugin-transform-dynamic-import" "^7.23.3" + "@babel/plugin-transform-exponentiation-operator" "^7.23.3" + "@babel/plugin-transform-export-namespace-from" "^7.23.3" + "@babel/plugin-transform-for-of" "^7.23.3" + "@babel/plugin-transform-function-name" "^7.23.3" + "@babel/plugin-transform-json-strings" "^7.23.3" + "@babel/plugin-transform-literals" "^7.23.3" + "@babel/plugin-transform-logical-assignment-operators" "^7.23.3" + "@babel/plugin-transform-member-expression-literals" "^7.23.3" + "@babel/plugin-transform-modules-amd" "^7.23.3" + "@babel/plugin-transform-modules-commonjs" "^7.23.3" + "@babel/plugin-transform-modules-systemjs" "^7.23.3" + "@babel/plugin-transform-modules-umd" "^7.23.3" + "@babel/plugin-transform-named-capturing-groups-regex" "^7.22.5" + "@babel/plugin-transform-new-target" "^7.23.3" + "@babel/plugin-transform-nullish-coalescing-operator" "^7.23.3" + "@babel/plugin-transform-numeric-separator" "^7.23.3" + "@babel/plugin-transform-object-rest-spread" "^7.23.3" + "@babel/plugin-transform-object-super" "^7.23.3" + "@babel/plugin-transform-optional-catch-binding" "^7.23.3" + "@babel/plugin-transform-optional-chaining" "^7.23.3" + "@babel/plugin-transform-parameters" "^7.23.3" + "@babel/plugin-transform-private-methods" "^7.23.3" + "@babel/plugin-transform-private-property-in-object" "^7.23.3" + "@babel/plugin-transform-property-literals" "^7.23.3" + "@babel/plugin-transform-regenerator" "^7.23.3" + "@babel/plugin-transform-reserved-words" "^7.23.3" + "@babel/plugin-transform-shorthand-properties" "^7.23.3" + "@babel/plugin-transform-spread" "^7.23.3" + "@babel/plugin-transform-sticky-regex" "^7.23.3" + "@babel/plugin-transform-template-literals" "^7.23.3" + "@babel/plugin-transform-typeof-symbol" "^7.23.3" + "@babel/plugin-transform-unicode-escapes" "^7.23.3" + "@babel/plugin-transform-unicode-property-regex" "^7.23.3" + "@babel/plugin-transform-unicode-regex" "^7.23.3" + "@babel/plugin-transform-unicode-sets-regex" "^7.23.3" + "@babel/preset-modules" "0.1.6-no-external-plugins" + babel-plugin-polyfill-corejs2 "^0.4.6" + babel-plugin-polyfill-corejs3 "^0.8.5" + babel-plugin-polyfill-regenerator "^0.5.3" + core-js-compat "^3.31.0" + semver "^6.3.1" + +"@babel/preset-modules@0.1.6-no-external-plugins": + version "0.1.6-no-external-plugins" + resolved "https://registry.npmjs.org/@babel/preset-modules/-/preset-modules-0.1.6-no-external-plugins.tgz" + integrity sha512-HrcgcIESLm9aIR842yhJ5RWan/gebQUJ6E/E5+rf0y9o6oj7w0Br+sWuL6kEQ/o/AdfvR1Je9jG18/gnpwjEyA== + dependencies: + "@babel/helper-plugin-utils" "^7.0.0" + "@babel/types" "^7.4.4" + esutils "^2.0.2" + +"@babel/preset-react@^7.18.6": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/preset-react/-/preset-react-7.23.3.tgz" + integrity sha512-tbkHOS9axH6Ysf2OUEqoSZ6T3Fa2SrNH6WTWSPBboxKzdxNc9qOICeLXkNG0ZEwbQ1HY8liwOce4aN/Ceyuq6w== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-validator-option" "^7.22.15" + "@babel/plugin-transform-react-display-name" "^7.23.3" + "@babel/plugin-transform-react-jsx" "^7.22.15" + "@babel/plugin-transform-react-jsx-development" "^7.22.5" + "@babel/plugin-transform-react-pure-annotations" "^7.23.3" + +"@babel/preset-typescript@^7.21.0": + version "7.23.3" + resolved "https://registry.npmjs.org/@babel/preset-typescript/-/preset-typescript-7.23.3.tgz" + integrity sha512-17oIGVlqz6CchO9RFYn5U6ZpWRZIngayYCtrPRSgANSwC2V1Jb+iP74nVxzzXJte8b8BYxrL1yY96xfhTBrNNQ== + dependencies: + "@babel/helper-plugin-utils" "^7.22.5" + "@babel/helper-validator-option" "^7.22.15" + "@babel/plugin-syntax-jsx" "^7.23.3" + "@babel/plugin-transform-modules-commonjs" "^7.23.3" + "@babel/plugin-transform-typescript" "^7.23.3" + +"@babel/regjsgen@^0.8.0": + version "0.8.0" + resolved "https://registry.npmjs.org/@babel/regjsgen/-/regjsgen-0.8.0.tgz" + integrity sha512-x/rqGMdzj+fWZvCOYForTghzbtqPDZ5gPwaoNGHdgDfF2QA/XZbCBp4Moo5scrkAMPhB7z26XM/AaHuIJdgauA== + +"@babel/runtime@^7.12.5", "@babel/runtime@^7.18.3", "@babel/runtime@^7.20.13", "@babel/runtime@^7.23.2", "@babel/runtime@^7.23.9", "@babel/runtime@^7.24.7", "@babel/runtime@^7.5.5", "@babel/runtime@^7.8.4", "@babel/runtime@^7.8.7": + version "7.24.7" + resolved "https://registry.npmjs.org/@babel/runtime/-/runtime-7.24.7.tgz" + integrity sha512-UwgBRMjJP+xv857DCngvqXI3Iq6J4v0wXmwc6sapg+zyhbwmQX67LUEFrkK5tbyJ30jGuG3ZvWpBiB9LCy1kWw== + dependencies: + regenerator-runtime "^0.14.0" + +"@babel/template@^7.22.15": + version "7.22.15" + resolved "https://registry.npmjs.org/@babel/template/-/template-7.22.15.tgz" + integrity sha512-QPErUVm4uyJa60rkI73qneDacvdvzxshT3kksGqlGWYdOTIUOwJ7RDUL8sGqslY1uXWSL6xMFKEXDS3ox2uF0w== + dependencies: + "@babel/code-frame" "^7.22.13" + "@babel/parser" "^7.22.15" + "@babel/types" "^7.22.15" + +"@babel/traverse@^7.23.3", "@babel/traverse@^7.23.4": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/traverse/-/traverse-7.23.4.tgz" + integrity sha512-IYM8wSUwunWTB6tFC2dkKZhxbIjHoWemdK+3f8/wq8aKhbUscxD5MX72ubd90fxvFknaLPeGw5ycU84V1obHJg== + dependencies: + "@babel/code-frame" "^7.23.4" + "@babel/generator" "^7.23.4" + "@babel/helper-environment-visitor" "^7.22.20" + "@babel/helper-function-name" "^7.23.0" + "@babel/helper-hoist-variables" "^7.22.5" + "@babel/helper-split-export-declaration" "^7.22.6" + "@babel/parser" "^7.23.4" + "@babel/types" "^7.23.4" + debug "^4.1.0" + globals "^11.1.0" + +"@babel/types@^7.21.3", "@babel/types@^7.22.15", "@babel/types@^7.22.19", "@babel/types@^7.22.5", "@babel/types@^7.23.0", "@babel/types@^7.23.3", "@babel/types@^7.23.4", "@babel/types@^7.4.4": + version "7.23.4" + resolved "https://registry.npmjs.org/@babel/types/-/types-7.23.4.tgz" + integrity sha512-7uIFwVYpoplT5jp/kVv6EF93VaJ8H+Yn5IczYiaAi98ajzjfoZfslet/e0sLh+wVBjb2qqIut1b0S26VSafsSQ== + dependencies: + "@babel/helper-string-parser" "^7.23.4" + "@babel/helper-validator-identifier" "^7.22.20" + to-fast-properties "^2.0.0" + +"@dnd-kit/accessibility@^3.1.0": + version "3.1.0" + resolved "https://registry.npmjs.org/@dnd-kit/accessibility/-/accessibility-3.1.0.tgz" + integrity sha512-ea7IkhKvlJUv9iSHJOnxinBcoOI3ppGnnL+VDJ75O45Nss6HtZd8IdN8touXPDtASfeI2T2LImb8VOZcL47wjQ== + dependencies: + tslib "^2.0.0" + +"@dnd-kit/core@^6.1.0": + version "6.1.0" + resolved "https://registry.npmjs.org/@dnd-kit/core/-/core-6.1.0.tgz" + integrity sha512-J3cQBClB4TVxwGo3KEjssGEXNJqGVWx17aRTZ1ob0FliR5IjYgTxl5YJbKTzA6IzrtelotH19v6y7uoIRUZPSg== + dependencies: + "@dnd-kit/accessibility" "^3.1.0" + "@dnd-kit/utilities" "^3.2.2" + tslib "^2.0.0" + +"@dnd-kit/sortable@^8.0.0": + version "8.0.0" + resolved "https://registry.npmjs.org/@dnd-kit/sortable/-/sortable-8.0.0.tgz" + integrity sha512-U3jk5ebVXe1Lr7c2wU7SBZjcWdQP+j7peHJfCspnA81enlu88Mgd7CC8Q+pub9ubP7eKVETzJW+IBAhsqbSu/g== + dependencies: + "@dnd-kit/utilities" "^3.2.2" + tslib "^2.0.0" + +"@dnd-kit/utilities@^3.2.2": + version "3.2.2" + resolved "https://registry.npmjs.org/@dnd-kit/utilities/-/utilities-3.2.2.tgz" + integrity sha512-+MKAJEOfaBe5SmV6t34p80MMKhjvUz0vRrvVJbPT0WElzaOJ/1xs+D+KDv+tD/NE5ujfrChEcshd4fLn0wpiqg== + dependencies: + tslib "^2.0.0" + +"@emotion/babel-plugin@^11.11.0": + version "11.11.0" + resolved "https://registry.npmjs.org/@emotion/babel-plugin/-/babel-plugin-11.11.0.tgz" + integrity sha512-m4HEDZleaaCH+XgDDsPF15Ht6wTLsgDTeR3WYj9Q/k76JtWhrJjcP4+/XlG8LGT/Rol9qUfOIztXeA84ATpqPQ== + dependencies: + "@babel/helper-module-imports" "^7.16.7" + "@babel/runtime" "^7.18.3" + "@emotion/hash" "^0.9.1" + "@emotion/memoize" "^0.8.1" + "@emotion/serialize" "^1.1.2" + babel-plugin-macros "^3.1.0" + convert-source-map "^1.5.0" + escape-string-regexp "^4.0.0" + find-root "^1.1.0" + source-map "^0.5.7" + stylis "4.2.0" + +"@emotion/cache@^11.11.0": + version "11.11.0" + resolved "https://registry.npmjs.org/@emotion/cache/-/cache-11.11.0.tgz" + integrity sha512-P34z9ssTCBi3e9EI1ZsWpNHcfY1r09ZO0rZbRO2ob3ZQMnFI35jB536qoXbkdesr5EUhYi22anuEJuyxifaqAQ== + dependencies: + "@emotion/memoize" "^0.8.1" + "@emotion/sheet" "^1.2.2" + "@emotion/utils" "^1.2.1" + "@emotion/weak-memoize" "^0.3.1" + stylis "4.2.0" + +"@emotion/css@^11.7.1": + version "11.11.2" + resolved "https://registry.npmjs.org/@emotion/css/-/css-11.11.2.tgz" + integrity sha512-VJxe1ucoMYMS7DkiMdC2T7PWNbrEI0a39YRiyDvK2qq4lXwjRbVP/z4lpG+odCsRzadlR+1ywwrTzhdm5HNdew== + dependencies: + "@emotion/babel-plugin" "^11.11.0" + "@emotion/cache" "^11.11.0" + "@emotion/serialize" "^1.1.2" + "@emotion/sheet" "^1.2.2" + "@emotion/utils" "^1.2.1" + +"@emotion/hash@^0.9.1": + version "0.9.1" + resolved "https://registry.npmjs.org/@emotion/hash/-/hash-0.9.1.tgz" + integrity sha512-gJB6HLm5rYwSLI6PQa+X1t5CFGrv1J1TWG+sOyMCeKz2ojaj6Fnl/rZEspogG+cvqbt4AE/2eIyD2QfLKTBNlQ== + +"@emotion/is-prop-valid@*", "@emotion/is-prop-valid@^1.2.2": + version "1.2.2" + resolved "https://registry.npmjs.org/@emotion/is-prop-valid/-/is-prop-valid-1.2.2.tgz" + integrity sha512-uNsoYd37AFmaCdXlg6EYD1KaPOaRWRByMCYzbKUX4+hhMfrxdVSelShywL4JVaAeM/eHUOSprYBQls+/neX3pw== + dependencies: + "@emotion/memoize" "^0.8.1" + +"@emotion/memoize@^0.8.1": + version "0.8.1" + resolved "https://registry.npmjs.org/@emotion/memoize/-/memoize-0.8.1.tgz" + integrity sha512-W2P2c/VRW1/1tLox0mVUalvnWXxavmv/Oum2aPsRcoDJuob75FC3Y8FbpfLwUegRcxINtGUMPq0tFCvYNTBXNA== + +"@emotion/react@^11.0.0-rc.0", "@emotion/react@^11.11.3", "@emotion/react@^11.11.4", "@emotion/react@^11.4.1", "@emotion/react@^11.5.0", "@emotion/react@^11.9.0": + version "11.11.4" + resolved "https://registry.npmjs.org/@emotion/react/-/react-11.11.4.tgz" + integrity sha512-t8AjMlF0gHpvvxk5mAtCqR4vmxiGHCeJBaQO6gncUSdklELOgtwjerNY2yuJNfwnc6vi16U/+uMF+afIawJ9iw== + dependencies: + "@babel/runtime" "^7.18.3" + "@emotion/babel-plugin" "^11.11.0" + "@emotion/cache" "^11.11.0" + "@emotion/serialize" "^1.1.3" + "@emotion/use-insertion-effect-with-fallbacks" "^1.0.1" + "@emotion/utils" "^1.2.1" + "@emotion/weak-memoize" "^0.3.1" + hoist-non-react-statics "^3.3.1" + +"@emotion/serialize@^1.1.2", "@emotion/serialize@^1.1.3", "@emotion/serialize@^1.1.4": + version "1.1.4" + resolved "https://registry.npmjs.org/@emotion/serialize/-/serialize-1.1.4.tgz" + integrity sha512-RIN04MBT8g+FnDwgvIUi8czvr1LU1alUMI05LekWB5DGyTm8cCBMCRpq3GqaiyEDRptEXOyXnvZ58GZYu4kBxQ== + dependencies: + "@emotion/hash" "^0.9.1" + "@emotion/memoize" "^0.8.1" + "@emotion/unitless" "^0.8.1" + "@emotion/utils" "^1.2.1" + csstype "^3.0.2" + +"@emotion/sheet@^1.2.2": + version "1.2.2" + resolved "https://registry.npmjs.org/@emotion/sheet/-/sheet-1.2.2.tgz" + integrity sha512-0QBtGvaqtWi+nx6doRwDdBIzhNdZrXUppvTM4dtZZWEGTXL/XE/yJxLMGlDT1Gt+UHH5IX1n+jkXyytE/av7OA== + +"@emotion/styled@^11.11.0", "@emotion/styled@^11.11.5", "@emotion/styled@^11.3.0", "@emotion/styled@^11.8.1": + version "11.11.5" + resolved "https://registry.npmjs.org/@emotion/styled/-/styled-11.11.5.tgz" + integrity sha512-/ZjjnaNKvuMPxcIiUkf/9SHoG4Q196DRl1w82hQ3WCsjo1IUR8uaGWrC6a87CrYAW0Kb/pK7hk8BnLgLRi9KoQ== + dependencies: + "@babel/runtime" "^7.18.3" + "@emotion/babel-plugin" "^11.11.0" + "@emotion/is-prop-valid" "^1.2.2" + "@emotion/serialize" "^1.1.4" + "@emotion/use-insertion-effect-with-fallbacks" "^1.0.1" + "@emotion/utils" "^1.2.1" + +"@emotion/unitless@^0.8.1": + version "0.8.1" + resolved "https://registry.npmjs.org/@emotion/unitless/-/unitless-0.8.1.tgz" + integrity sha512-KOEGMu6dmJZtpadb476IsZBclKvILjopjUii3V+7MnXIQCYh8W3NgNcgwo21n9LXZX6EDIKvqfjYxXebDwxKmQ== + +"@emotion/use-insertion-effect-with-fallbacks@^1.0.1": + version "1.0.1" + resolved "https://registry.npmjs.org/@emotion/use-insertion-effect-with-fallbacks/-/use-insertion-effect-with-fallbacks-1.0.1.tgz" + integrity sha512-jT/qyKZ9rzLErtrjGgdkMBn2OP8wl0G3sQlBb3YPryvKHsjvINUhVaPFfP+fpBcOkmrVOVEEHQFJ7nbj2TH2gw== + +"@emotion/utils@^1.2.1": + version "1.2.1" + resolved "https://registry.npmjs.org/@emotion/utils/-/utils-1.2.1.tgz" + integrity sha512-Y2tGf3I+XVnajdItskUCn6LX+VUDmP6lTL4fcqsXAv43dnlbZiuW4MWQW38rW/BVWSE7Q/7+XQocmpnRYILUmg== + +"@emotion/weak-memoize@^0.3.1": + version "0.3.1" + resolved "https://registry.npmjs.org/@emotion/weak-memoize/-/weak-memoize-0.3.1.tgz" + integrity sha512-EsBwpc7hBUJWAsNPBmJy4hxWx12v6bshQsldrVmjxJoc3isbxhOrF2IcCpaXxfvq03NwkI7sbsOLXbYuqF/8Ww== + +"@eslint-community/eslint-utils@^4.2.0", "@eslint-community/eslint-utils@^4.4.0": + version "4.4.0" + resolved "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.4.0.tgz" + integrity sha512-1/sA4dwrzBAyeUoQ6oxahHKmrZvsnLCg4RfxW3ZFGGmQkSNQPFNLV9CUEFQP1x9EYXHTo5p6xdhZM1Ne9p/AfA== + dependencies: + eslint-visitor-keys "^3.3.0" + +"@eslint-community/regexpp@^4.6.1": + version "4.10.0" + resolved "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.10.0.tgz" + integrity sha512-Cu96Sd2By9mCNTx2iyKOmq10v22jUVQv0lQnlGNy16oE9589yE+QADPbrMGCkA51cKZSg3Pu/aTJVTGfL/qjUA== + +"@eslint/eslintrc@^2.1.4": + version "2.1.4" + resolved "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-2.1.4.tgz" + integrity sha512-269Z39MS6wVJtsoUl10L60WdkhJVdPG24Q4eZTH3nnF6lpvSShEK3wQjDX9JRWAUPvPh7COouPpU9IrqaZFvtQ== + dependencies: + ajv "^6.12.4" + debug "^4.3.2" + espree "^9.6.0" + globals "^13.19.0" + ignore "^5.2.0" + import-fresh "^3.2.1" + js-yaml "^4.1.0" + minimatch "^3.1.2" + strip-json-comments "^3.1.1" + +"@eslint/js@8.57.0": + version "8.57.0" + resolved "https://registry.npmjs.org/@eslint/js/-/js-8.57.0.tgz" + integrity sha512-Ys+3g2TaW7gADOJzPt83SJtCDhMjndcDMFVQ/Tj9iA1BfJzFKD9mAUXT3OenpuPHbI6P/myECxRJrofUsDx/5g== + +"@fastify/busboy@^2.0.0": + version "2.1.1" + resolved "https://registry.npmjs.org/@fastify/busboy/-/busboy-2.1.1.tgz" + integrity sha512-vBZP4NlzfOlerQTnba4aqZoMhE/a9HY7HRqoOPaETQcSQuWEIyZMHGfVu6w9wGtGK5fED5qRs2DteVCjOH60sA== + +"@firebase/analytics-compat@0.2.10": + version "0.2.10" + resolved "https://registry.npmjs.org/@firebase/analytics-compat/-/analytics-compat-0.2.10.tgz" + integrity sha512-ia68RcLQLLMFWrM10JfmFod7eJGwqr4/uyrtzHpTDnxGX/6gNCBTOuxdAbyWIqXI5XmcMQdz9hDijGKOHgDfPw== + dependencies: + "@firebase/analytics" "0.10.4" + "@firebase/analytics-types" "0.8.2" + "@firebase/component" "0.6.7" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/analytics-types@0.8.2": + version "0.8.2" + resolved "https://registry.npmjs.org/@firebase/analytics-types/-/analytics-types-0.8.2.tgz" + integrity sha512-EnzNNLh+9/sJsimsA/FGqzakmrAUKLeJvjRHlg8df1f97NLUlFidk9600y0ZgWOp3CAxn6Hjtk+08tixlUOWyw== + +"@firebase/analytics@0.10.4": + version "0.10.4" + resolved "https://registry.npmjs.org/@firebase/analytics/-/analytics-0.10.4.tgz" + integrity sha512-OJEl/8Oye/k+vJ1zV/1L6eGpc1XzAj+WG2TPznJ7PszL7sOFLBXkL9IjHfOCGDGpXeO3btozy/cYUqv4zgNeHg== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/installations" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/app-check-compat@0.3.11": + version "0.3.11" + resolved "https://registry.npmjs.org/@firebase/app-check-compat/-/app-check-compat-0.3.11.tgz" + integrity sha512-t01zaH3RJpKEey0nGduz3Is+uSz7Sj4U5nwOV6lWb+86s5xtxpIvBJzu/lKxJfYyfZ29eJwpdjEgT1/lm4iQyA== + dependencies: + "@firebase/app-check" "0.8.4" + "@firebase/app-check-types" "0.5.2" + "@firebase/component" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/app-check-interop-types@0.3.2": + version "0.3.2" + resolved "https://registry.npmjs.org/@firebase/app-check-interop-types/-/app-check-interop-types-0.3.2.tgz" + integrity sha512-LMs47Vinv2HBMZi49C09dJxp0QT5LwDzFaVGf/+ITHe3BlIhUiLNttkATSXplc89A2lAaeTqjgqVkiRfUGyQiQ== + +"@firebase/app-check-types@0.5.2": + version "0.5.2" + resolved "https://registry.npmjs.org/@firebase/app-check-types/-/app-check-types-0.5.2.tgz" + integrity sha512-FSOEzTzL5bLUbD2co3Zut46iyPWML6xc4x+78TeaXMSuJap5QObfb+rVvZJtla3asN4RwU7elaQaduP+HFizDA== + +"@firebase/app-check@0.8.4": + version "0.8.4" + resolved "https://registry.npmjs.org/@firebase/app-check/-/app-check-0.8.4.tgz" + integrity sha512-2tjRDaxcM5G7BEpytiDcIl+NovV99q8yEqRMKDbn4J4i/XjjuThuB4S+4PkmTnZiCbdLXQiBhkVxNlUDcfog5Q== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/app-compat@0.2.35", "@firebase/app-compat@0.x": + version "0.2.35" + resolved "https://registry.npmjs.org/@firebase/app-compat/-/app-compat-0.2.35.tgz" + integrity sha512-vgay/WRjeH0r97/Q6L6df2CMx7oyNFDsE5yPQ9oR1G+zx2eT0s8vNNh0WlKqQxUEWaOLRnXhQ8gy7uu0cBgTRg== + dependencies: + "@firebase/app" "0.10.5" + "@firebase/component" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/app-types@0.9.2", "@firebase/app-types@0.x": + version "0.9.2" + resolved "https://registry.npmjs.org/@firebase/app-types/-/app-types-0.9.2.tgz" + integrity sha512-oMEZ1TDlBz479lmABwWsWjzHwheQKiAgnuKxE0pz0IXCVx7/rtlkx1fQ6GfgK24WCrxDKMplZrT50Kh04iMbXQ== + +"@firebase/app@0.10.5", "@firebase/app@0.x": + version "0.10.5" + resolved "https://registry.npmjs.org/@firebase/app/-/app-0.10.5.tgz" + integrity sha512-iY/fNot+hWPk9sTX8aHMqlcX9ynRvpGkskWAdUZ2eQQdLo8d1hSFYcYNwPv0Q/frGMasw8udKWMcFOEpC9fG8g== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + idb "7.1.1" + tslib "^2.1.0" + +"@firebase/auth-compat@0.5.9": + version "0.5.9" + resolved "https://registry.npmjs.org/@firebase/auth-compat/-/auth-compat-0.5.9.tgz" + integrity sha512-RX8Zh/3zz2CsVbmYfgHkfUm4fAEPCl+KHVIImNygV5jTGDF6oKOhBIpf4Yigclyu8ESQKZ4elyN0MBYm9/7zGw== + dependencies: + "@firebase/auth" "1.7.4" + "@firebase/auth-types" "0.12.2" + "@firebase/component" "0.6.7" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + undici "5.28.4" + +"@firebase/auth-interop-types@0.2.3": + version "0.2.3" + resolved "https://registry.npmjs.org/@firebase/auth-interop-types/-/auth-interop-types-0.2.3.tgz" + integrity sha512-Fc9wuJGgxoxQeavybiuwgyi+0rssr76b+nHpj+eGhXFYAdudMWyfBHvFL/I5fEHniUM/UQdFzi9VXJK2iZF7FQ== + +"@firebase/auth-types@0.12.2": + version "0.12.2" + resolved "https://registry.npmjs.org/@firebase/auth-types/-/auth-types-0.12.2.tgz" + integrity sha512-qsEBaRMoGvHO10unlDJhaKSuPn4pyoTtlQuP1ghZfzB6rNQPuhp/N/DcFZxm9i4v0SogjCbf9reWupwIvfmH6w== + +"@firebase/auth@1.7.4": + version "1.7.4" + resolved "https://registry.npmjs.org/@firebase/auth/-/auth-1.7.4.tgz" + integrity sha512-d2Fw17s5QesojwebrA903el20Li9/YGgkoOGJjagM4I1qAT36APa/FcZ+OX86KxbYKCtQKTMqraU8pxG7C2JWA== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + undici "5.28.4" + +"@firebase/component@0.6.7": + version "0.6.7" + resolved "https://registry.npmjs.org/@firebase/component/-/component-0.6.7.tgz" + integrity sha512-baH1AA5zxfaz4O8w0vDwETByrKTQqB5CDjRls79Sa4eAGAoERw4Tnung7XbMl3jbJ4B/dmmtsMrdki0KikwDYA== + dependencies: + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/database-compat@1.0.5": + version "1.0.5" + resolved "https://registry.npmjs.org/@firebase/database-compat/-/database-compat-1.0.5.tgz" + integrity sha512-NDSMaDjQ+TZEMDMmzJwlTL05kh1+0Y84C+kVMaOmNOzRGRM7VHi29I6YUhCetXH+/b1Wh4ZZRyp1CuWkd8s6hg== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/database" "1.0.5" + "@firebase/database-types" "1.0.3" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/database-types@1.0.3": + version "1.0.3" + resolved "https://registry.npmjs.org/@firebase/database-types/-/database-types-1.0.3.tgz" + integrity sha512-39V/Riv2R3O/aUjYKh0xypj7NTNXNAK1bcgY5Kx+hdQPRS/aPTS8/5c0CGFYKgVuFbYlnlnhrCTYsh2uNhGwzA== + dependencies: + "@firebase/app-types" "0.9.2" + "@firebase/util" "1.9.6" + +"@firebase/database@1.0.5": + version "1.0.5" + resolved "https://registry.npmjs.org/@firebase/database/-/database-1.0.5.tgz" + integrity sha512-cAfwBqMQuW6HbhwI3Cb/gDqZg7aR0OmaJ85WUxlnoYW2Tm4eR0hFl5FEijI3/gYPUiUcUPQvTkGV222VkT7KPw== + dependencies: + "@firebase/app-check-interop-types" "0.3.2" + "@firebase/auth-interop-types" "0.2.3" + "@firebase/component" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + faye-websocket "0.11.4" + tslib "^2.1.0" + +"@firebase/firestore-compat@0.3.32": + version "0.3.32" + resolved "https://registry.npmjs.org/@firebase/firestore-compat/-/firestore-compat-0.3.32.tgz" + integrity sha512-at71mwK7a/mUXH0OgyY0+gUzedm/EUydDFYSFsBoO8DYowZ23Mgd6P4Rzq/Ll3zI/3xJN7LGe7Qp4iE/V/3Arg== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/firestore" "4.6.3" + "@firebase/firestore-types" "3.0.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/firestore-types@3.0.2": + version "3.0.2" + resolved "https://registry.npmjs.org/@firebase/firestore-types/-/firestore-types-3.0.2.tgz" + integrity sha512-wp1A+t5rI2Qc/2q7r2ZpjUXkRVPtGMd6zCLsiWurjsQpqPgFin3AhNibKcIzoF2rnToNa/XYtyWXuifjOOwDgg== + +"@firebase/firestore@4.6.3": + version "4.6.3" + resolved "https://registry.npmjs.org/@firebase/firestore/-/firestore-4.6.3.tgz" + integrity sha512-d/+N2iUsiJ/Dc7fApdpdmmTXzwuTCromsdA1lKwYfZtMIOd1fI881NSLwK2wV4I38wkLnvfKJUV6WpU1f3/ONg== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + "@firebase/webchannel-wrapper" "1.0.0" + "@grpc/grpc-js" "~1.9.0" + "@grpc/proto-loader" "^0.7.8" + tslib "^2.1.0" + undici "5.28.4" + +"@firebase/functions-compat@0.3.11": + version "0.3.11" + resolved "https://registry.npmjs.org/@firebase/functions-compat/-/functions-compat-0.3.11.tgz" + integrity sha512-Qn+ts/M6Lj2/6i1cp5V5TRR+Hi9kyXyHbo+w9GguINJ87zxrCe6ulx3TI5AGQkoQa8YFHUhT3DMGmLFiJjWTSQ== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/functions" "0.11.5" + "@firebase/functions-types" "0.6.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/functions-types@0.6.2": + version "0.6.2" + resolved "https://registry.npmjs.org/@firebase/functions-types/-/functions-types-0.6.2.tgz" + integrity sha512-0KiJ9lZ28nS2iJJvimpY4nNccV21rkQyor5Iheu/nq8aKXJqtJdeSlZDspjPSBBiHRzo7/GMUttegnsEITqR+w== + +"@firebase/functions@0.11.5": + version "0.11.5" + resolved "https://registry.npmjs.org/@firebase/functions/-/functions-0.11.5.tgz" + integrity sha512-qrHJ+l62mZiU5UZiVi84t/iLXZlhRuSvBQsa2qvNLgPsEWR7wdpWhRmVdB7AU8ndkSHJjGlMICqrVnz47sgU7Q== + dependencies: + "@firebase/app-check-interop-types" "0.3.2" + "@firebase/auth-interop-types" "0.2.3" + "@firebase/component" "0.6.7" + "@firebase/messaging-interop-types" "0.2.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + undici "5.28.4" + +"@firebase/installations-compat@0.2.7": + version "0.2.7" + resolved "https://registry.npmjs.org/@firebase/installations-compat/-/installations-compat-0.2.7.tgz" + integrity sha512-RPcbD+3nqHbnhVjIOpWK2H5qzZ8pAAAScceiWph0VNTqpKyPQ5tDcp4V5fS0ELpfgsHYvroMLDKfeHxpfvm8cw== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/installations" "0.6.7" + "@firebase/installations-types" "0.5.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/installations-types@0.5.2": + version "0.5.2" + resolved "https://registry.npmjs.org/@firebase/installations-types/-/installations-types-0.5.2.tgz" + integrity sha512-que84TqGRZJpJKHBlF2pkvc1YcXrtEDOVGiDjovP/a3s6W4nlbohGXEsBJo0JCeeg/UG9A+DEZVDUV9GpklUzA== + +"@firebase/installations@0.6.7": + version "0.6.7" + resolved "https://registry.npmjs.org/@firebase/installations/-/installations-0.6.7.tgz" + integrity sha512-i6iGoXRu5mX4rTsiMSSKrgh9pSEzD4hwBEzRh5kEhOTr8xN/wvQcCPZDSMVYKwM2XyCPBLVq0JzjyerwL0Rihg== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/util" "1.9.6" + idb "7.1.1" + tslib "^2.1.0" + +"@firebase/logger@0.4.2": + version "0.4.2" + resolved "https://registry.npmjs.org/@firebase/logger/-/logger-0.4.2.tgz" + integrity sha512-Q1VuA5M1Gjqrwom6I6NUU4lQXdo9IAQieXlujeHZWvRt1b7qQ0KwBaNAjgxG27jgF9/mUwsNmO8ptBCGVYhB0A== + dependencies: + tslib "^2.1.0" + +"@firebase/messaging-compat@0.2.9": + version "0.2.9" + resolved "https://registry.npmjs.org/@firebase/messaging-compat/-/messaging-compat-0.2.9.tgz" + integrity sha512-5jN6wyhwPgBH02zOtmmoOeyfsmoD7ty48D1m0vVPsFg55RqN2Z3Q9gkZ5GmPklFPjTPLcxB1ObcHOZvThTkm7g== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/messaging" "0.12.9" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/messaging-interop-types@0.2.2": + version "0.2.2" + resolved "https://registry.npmjs.org/@firebase/messaging-interop-types/-/messaging-interop-types-0.2.2.tgz" + integrity sha512-l68HXbuD2PPzDUOFb3aG+nZj5KA3INcPwlocwLZOzPp9rFM9yeuI9YLl6DQfguTX5eAGxO0doTR+rDLDvQb5tA== + +"@firebase/messaging@0.12.9": + version "0.12.9" + resolved "https://registry.npmjs.org/@firebase/messaging/-/messaging-0.12.9.tgz" + integrity sha512-IH+JJmzbFGZXV3+TDyKdqqKPVfKRqBBg2BfYYOy7cm7J+SwV+uJMe8EnDKYeQLEQhtpwciPfJ3qQXJs2lbxDTw== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/installations" "0.6.7" + "@firebase/messaging-interop-types" "0.2.2" + "@firebase/util" "1.9.6" + idb "7.1.1" + tslib "^2.1.0" + +"@firebase/performance-compat@0.2.7": + version "0.2.7" + resolved "https://registry.npmjs.org/@firebase/performance-compat/-/performance-compat-0.2.7.tgz" + integrity sha512-cb8ge/5iTstxfIGW+iiY+7l3FtN8gobNh9JSQNZgLC9xmcfBYWEs8IeEWMI6S8T+At0oHc3lv+b2kpRMUWr8zQ== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/performance" "0.6.7" + "@firebase/performance-types" "0.2.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/performance-types@0.2.2": + version "0.2.2" + resolved "https://registry.npmjs.org/@firebase/performance-types/-/performance-types-0.2.2.tgz" + integrity sha512-gVq0/lAClVH5STrIdKnHnCo2UcPLjJlDUoEB/tB4KM+hAeHUxWKnpT0nemUPvxZ5nbdY/pybeyMe8Cs29gEcHA== + +"@firebase/performance@0.6.7": + version "0.6.7" + resolved "https://registry.npmjs.org/@firebase/performance/-/performance-0.6.7.tgz" + integrity sha512-d+Q4ltjdJZqjzcdms5i0UC9KLYX7vKGcygZ+7zHA/Xk+bAbMD2CPU0nWTnlNFWifZWIcXZ/2mAMvaGMW3lypUA== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/installations" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/remote-config-compat@0.2.7": + version "0.2.7" + resolved "https://registry.npmjs.org/@firebase/remote-config-compat/-/remote-config-compat-0.2.7.tgz" + integrity sha512-Fq0oneQ4SluLnfr5/HfzRS1TZf1ANj1rWbCCW3+oC98An3nE+sCdp+FSuHsEVNwgMg4Tkwx9Oom2lkKeU+Vn+w== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/remote-config" "0.4.7" + "@firebase/remote-config-types" "0.3.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/remote-config-types@0.3.2": + version "0.3.2" + resolved "https://registry.npmjs.org/@firebase/remote-config-types/-/remote-config-types-0.3.2.tgz" + integrity sha512-0BC4+Ud7y2aPTyhXJTMTFfrGGLqdYXrUB9sJVAB8NiqJswDTc4/2qrE/yfUbnQJhbSi6ZaTTBKyG3n1nplssaA== + +"@firebase/remote-config@0.4.7": + version "0.4.7" + resolved "https://registry.npmjs.org/@firebase/remote-config/-/remote-config-0.4.7.tgz" + integrity sha512-5oPNrPFLsbsjpq0lUEIXoDF2eJK7vAbyXe/DEuZQxnwJlfR7aQbtUlEkRgQWcicXpyDmAmDLo7q7lDbCYa6CpA== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/installations" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/storage-compat@0.3.8": + version "0.3.8" + resolved "https://registry.npmjs.org/@firebase/storage-compat/-/storage-compat-0.3.8.tgz" + integrity sha512-qDfY9kMb6Ch2hZb40sBjDQ8YPxbjGOxuT+gU1Z0iIVSSpSX0f4YpGJCypUXiA0T11n6InCXB+T/Dknh2yxVTkg== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/storage" "0.12.5" + "@firebase/storage-types" "0.8.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/storage-types@0.8.2": + version "0.8.2" + resolved "https://registry.npmjs.org/@firebase/storage-types/-/storage-types-0.8.2.tgz" + integrity sha512-0vWu99rdey0g53lA7IShoA2Lol1jfnPovzLDUBuon65K7uKG9G+L5uO05brD9pMw+l4HRFw23ah3GwTGpEav6g== + +"@firebase/storage@0.12.5": + version "0.12.5" + resolved "https://registry.npmjs.org/@firebase/storage/-/storage-0.12.5.tgz" + integrity sha512-nGWBOGFNr10j0LA4NJ3/Yh3us/lb0Q1xSIKZ38N6FcS+vY54nqJ7k3zE3PENregHC8+8txRow++A568G3v8hOA== + dependencies: + "@firebase/component" "0.6.7" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + undici "5.28.4" + +"@firebase/util@1.9.6", "@firebase/util@1.x": + version "1.9.6" + resolved "https://registry.npmjs.org/@firebase/util/-/util-1.9.6.tgz" + integrity sha512-IBr1MZbp4d5MjBCXL3TW1dK/PDXX4yOGbiwRNh1oAbE/+ci5Uuvy9KIrsFYY80as1I0iOaD5oOMA9Q8j4TJWcw== + dependencies: + tslib "^2.1.0" + +"@firebase/vertexai-preview@0.0.2": + version "0.0.2" + resolved "https://registry.npmjs.org/@firebase/vertexai-preview/-/vertexai-preview-0.0.2.tgz" + integrity sha512-NOOL63kFQRq45ioi5P+hlqj/4LNmvn1URhGjQdvyV54c1Irvoq26aW861PRRLjrSMIeNeiLtCLD5pe+ediepAg== + dependencies: + "@firebase/app-check-interop-types" "0.3.2" + "@firebase/component" "0.6.7" + "@firebase/logger" "0.4.2" + "@firebase/util" "1.9.6" + tslib "^2.1.0" + +"@firebase/webchannel-wrapper@1.0.0": + version "1.0.0" + resolved "https://registry.npmjs.org/@firebase/webchannel-wrapper/-/webchannel-wrapper-1.0.0.tgz" + integrity sha512-zuWxyfXNbsKbm96HhXzainONPFqRcoZblQ++e9cAIGUuHfl2cFSBzW01jtesqWG/lqaUyX3H8O1y9oWboGNQBA== + +"@floating-ui/core@^1.6.0": + version "1.6.0" + resolved "https://registry.npmjs.org/@floating-ui/core/-/core-1.6.0.tgz" + integrity sha512-PcF++MykgmTj3CIyOQbKA/hDzOAiqI3mhuoN44WRCopIs1sgoDoU4oty4Jtqaj/y3oDU6fnVSm4QG0a3t5i0+g== + dependencies: + "@floating-ui/utils" "^0.2.1" + +"@floating-ui/dom@^1.6.1": + version "1.6.1" + resolved "https://registry.npmjs.org/@floating-ui/dom/-/dom-1.6.1.tgz" + integrity sha512-iA8qE43/H5iGozC3W0YSnVSW42Vh522yyM1gj+BqRwVsTNOyr231PsXDaV04yT39PsO0QL2QpbI/M0ZaLUQgRQ== + dependencies: + "@floating-ui/core" "^1.6.0" + "@floating-ui/utils" "^0.2.1" + +"@floating-ui/react-dom@^2.0.8": + version "2.0.8" + resolved "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.0.8.tgz" + integrity sha512-HOdqOt3R3OGeTKidaLvJKcgg75S6tibQ3Tif4eyd91QnIJWr0NLvoXFpJA/j8HqkFSL68GDca9AuyWEHlhyClw== + dependencies: + "@floating-ui/dom" "^1.6.1" + +"@floating-ui/utils@^0.2.1": + version "0.2.1" + resolved "https://registry.npmjs.org/@floating-ui/utils/-/utils-0.2.1.tgz" + integrity sha512-9TANp6GPoMtYzQdt54kfAyMmz1+osLlXdg2ENroU7zzrtflTLrrC/lgrIfaSe+Wu0b89GKccT7vxXA0MoAIO+Q== + +"@fontsource/barlow@^5.0.13": + version "5.0.13" + resolved "https://registry.npmjs.org/@fontsource/barlow/-/barlow-5.0.13.tgz" + integrity sha512-Jk3/s/0zHPyc7zd7trOskjhVpTGn8k9tlgAUOnfeB7V8xw+E+UGcDRSYw09ahLHrFnjbjrhcJDnXhpEk6b0QlA== + +"@fontsource/dm-sans@^5.0.21": + version "5.0.21" + resolved "https://registry.npmjs.org/@fontsource/dm-sans/-/dm-sans-5.0.21.tgz" + integrity sha512-ydUs1ZAf6fqZfvmEb4EdT7RehZvFBLEOVz6Mn9kmoaVsYR1Ql3kkQvaAGEyMrcCuoBklwPaCqnq6PkHyYzIx6Q== + +"@fontsource/inter@^5.0.18": + version "5.0.18" + resolved "https://registry.npmjs.org/@fontsource/inter/-/inter-5.0.18.tgz" + integrity sha512-YCsoYPTcs713sI7tLtxaPrIhXAXvEetGg5Ry02ivA8qUOb3fQHojbK/X9HLD5OOKvFUNR2Ynkwb1kR1hVKQHpw== + +"@fontsource/nunito-sans@^5.0.13": + version "5.0.13" + resolved "https://registry.npmjs.org/@fontsource/nunito-sans/-/nunito-sans-5.0.13.tgz" + integrity sha512-rsajElysg08MhRPYiCZ1lh/34gTfHx9XzyP10oXPwgiFud7MIHAHjE1PTwYlZZDdceu89UzjxelRx98yie8wCw== + +"@fontsource/public-sans@^5.0.18": + version "5.0.18" + resolved "https://registry.npmjs.org/@fontsource/public-sans/-/public-sans-5.0.18.tgz" + integrity sha512-dYx/ULF7pRkjBO1ncCwIRXWWmI2oCsMsWxheHgjtNANm4+prtfq3gdGy3KOsuNcAhEKn6BQeIyg0hFqeoTpAaQ== + +"@fullcalendar/core@^6.1.14", "@fullcalendar/core@~6.1.14": + version "6.1.14" + resolved "https://registry.npmjs.org/@fullcalendar/core/-/core-6.1.14.tgz" + integrity sha512-hIPRBevm0aMc2aHy1hRIJgXmI1QTvQM1neQa9oxtuqUmF1+ApYC3oAdwcQMTuI7lHHw3pKJDyJFkKLPPnL6HXA== + dependencies: + preact "~10.12.1" + +"@fullcalendar/daygrid@^6.1.14", "@fullcalendar/daygrid@~6.1.14": + version "6.1.14" + resolved "https://registry.npmjs.org/@fullcalendar/daygrid/-/daygrid-6.1.14.tgz" + integrity sha512-DSyjiA1dEM8k3bOCrZpZOmAOZu71KGtH02ze+4QKuhxkmn/zQghmmLRdfzpOrcyJg6xGKkoB4pBcO+2lXar8XQ== + +"@fullcalendar/interaction@^6.1.14": + version "6.1.14" + resolved "https://registry.npmjs.org/@fullcalendar/interaction/-/interaction-6.1.14.tgz" + integrity sha512-rXum5XCjq+WEPNctFeYL/JKZGeU2rlxrElygocdMegcrIBJQW5hnWWVE+i4/1dOmUKF80CbGVlXUyYXoqK2eFg== + +"@fullcalendar/list@^6.1.14": + version "6.1.14" + resolved "https://registry.npmjs.org/@fullcalendar/list/-/list-6.1.14.tgz" + integrity sha512-eV0/6iCumYfvlPzIUTAONWH17/JlQCyCChUz8m06L4E/sOiNjkHGz8vlVTmZKqXzx9oWOOyV/Nm3pCtHmVZh+Q== + +"@fullcalendar/premium-common@~6.1.14": + version "6.1.14" + resolved "https://registry.npmjs.org/@fullcalendar/premium-common/-/premium-common-6.1.14.tgz" + integrity sha512-Fw8GZ6mjZtv6toliSr3iHwIqLIjx3+7fdd828OO4LGzX1wcnCd74CfWqR1tvg+9YLUKmRXNEGgQaN4y5j/XpKg== + +"@fullcalendar/react@^6.1.14": + version "6.1.14" + resolved "https://registry.npmjs.org/@fullcalendar/react/-/react-6.1.14.tgz" + integrity sha512-sXLn2D8aPYLuDH3fy2ZhHTOz5WNSU1NhoECsGBzjUtz2IYHy6m5Y9TqlyqeAqVqFLDRSJAlKAr5LyrIvnD/IMA== + +"@fullcalendar/scrollgrid@~6.1.14": + version "6.1.14" + resolved "https://registry.npmjs.org/@fullcalendar/scrollgrid/-/scrollgrid-6.1.14.tgz" + integrity sha512-LVLdjMgzf0uDNWzB7GWOrZAGF61pa/J0ipJHfG3BTO5Ri5qZbOHpVcPuW94LOFnaGZpbaOG2YQlKygrujAAbvA== + dependencies: + "@fullcalendar/premium-common" "~6.1.14" + +"@fullcalendar/timegrid@^6.1.14": + version "6.1.14" + resolved "https://registry.npmjs.org/@fullcalendar/timegrid/-/timegrid-6.1.14.tgz" + integrity sha512-ZByc3BVAtxWSVfyaNedROLlg/Tb2NQ43+MZZAfBSrVwVm2xyfQ+Bsx3pJyCXsRsUh2TFFTO07q7nMWe0jet3KQ== + dependencies: + "@fullcalendar/daygrid" "~6.1.14" + +"@fullcalendar/timeline@^6.1.14": + version "6.1.14" + resolved "https://registry.npmjs.org/@fullcalendar/timeline/-/timeline-6.1.14.tgz" + integrity sha512-5UvugmoJsXeinrHwH57hMgFWh77KagWtxOkrSL5DwaRj4DTb2loV/pkYD5GJaMjpsZqZcUW0V8kICUzNbkZXag== + dependencies: + "@fullcalendar/premium-common" "~6.1.14" + "@fullcalendar/scrollgrid" "~6.1.14" + +"@gilbarbara/deep-equal@^0.1.1": + version "0.1.2" + resolved "https://registry.npmjs.org/@gilbarbara/deep-equal/-/deep-equal-0.1.2.tgz" + integrity sha512-jk+qzItoEb0D0xSSmrKDDzf9sheQj/BAPxlgNxgmOaA3mxpUa6ndJLYGZKsJnIVEQSD8zcTbyILz7I0HcnBCRA== + +"@gilbarbara/deep-equal@^0.3.1": + version "0.3.1" + resolved "https://registry.npmjs.org/@gilbarbara/deep-equal/-/deep-equal-0.3.1.tgz" + integrity sha512-I7xWjLs2YSVMc5gGx1Z3ZG1lgFpITPndpi8Ku55GeEIKpACCPQNS/OTqQbxgTCfq0Ncvcc+CrFov96itVh6Qvw== + +"@grpc/grpc-js@~1.9.0": + version "1.9.15" + resolved "https://registry.npmjs.org/@grpc/grpc-js/-/grpc-js-1.9.15.tgz" + integrity sha512-nqE7Hc0AzI+euzUwDAy0aY5hCp10r734gMGRdU+qOPX0XSceI2ULrcXB5U2xSc5VkWwalCj4M7GzCAygZl2KoQ== + dependencies: + "@grpc/proto-loader" "^0.7.8" + "@types/node" ">=12.12.47" + +"@grpc/proto-loader@^0.7.8": + version "0.7.13" + resolved "https://registry.npmjs.org/@grpc/proto-loader/-/proto-loader-0.7.13.tgz" + integrity sha512-AiXO/bfe9bmxBjxxtYxFAXGZvMaN5s8kO+jBHAJCON8rJoB5YS/D6X7ZNc6XQkuHNmyl4CYaMI1fJ/Gn27RGGw== + dependencies: + lodash.camelcase "^4.3.0" + long "^5.0.0" + protobufjs "^7.2.5" + yargs "^17.7.2" + +"@hookform/resolvers@^3.6.0": + version "3.6.0" + resolved "https://registry.npmjs.org/@hookform/resolvers/-/resolvers-3.6.0.tgz" + integrity sha512-UBcpyOX3+RR+dNnqBd0lchXpoL8p4xC21XP8H6Meb8uve5Br1GCnmg0PcBoKKqPKgGu9GHQ/oygcmPrQhetwqw== + +"@humanwhocodes/config-array@^0.11.14": + version "0.11.14" + resolved "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.11.14.tgz" + integrity sha512-3T8LkOmg45BV5FICb15QQMsyUSWrQ8AygVfC7ZG32zOalnqrilm018ZVCw0eapXux8FtA33q8PSRSstjee3jSg== + dependencies: + "@humanwhocodes/object-schema" "^2.0.2" + debug "^4.3.1" + minimatch "^3.0.5" + +"@humanwhocodes/module-importer@^1.0.1": + version "1.0.1" + resolved "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz" + integrity sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA== + +"@humanwhocodes/object-schema@^2.0.2": + version "2.0.2" + resolved "https://registry.npmjs.org/@humanwhocodes/object-schema/-/object-schema-2.0.2.tgz" + integrity sha512-6EwiSjwWYP7pTckG6I5eyFANjPhmPjUX9JRLUSfNPC7FX7zK9gyZAfUEaECL6ALTpGX5AjnBq3C9XmVWPitNpw== + +"@iconify/react@^5.0.1": + version "5.0.1" + resolved "https://registry.npmjs.org/@iconify/react/-/react-5.0.1.tgz" + integrity sha512-octpAJRtHZLLS1o6fmz2Ek2Rfwx75kVg48MZyGTqL3QqoxRddEsuLqOt6ADDhRosmlrYnIrVL+7obo1bz2ikNw== + dependencies: + "@iconify/types" "^2.0.0" + +"@iconify/types@^2.0.0": + version "2.0.0" + resolved "https://registry.npmjs.org/@iconify/types/-/types-2.0.0.tgz" + integrity sha512-+wluvCrRhXrhyOmRDJ3q8mux9JkKy5SJ/v8ol2tu4FVjyYvtEzkc/3pK15ET6RKg4b4w4BmTk1+gsCUhf21Ykg== + +"@jridgewell/gen-mapping@^0.3.0", "@jridgewell/gen-mapping@^0.3.2": + version "0.3.3" + resolved "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.3.tgz" + integrity sha512-HLhSWOLRi875zjjMG/r+Nv0oCW8umGb0BgEhyX3dDX3egwZtB8PqLnjz3yedt8R5StBrzcg4aBpnh8UA9D1BoQ== + dependencies: + "@jridgewell/set-array" "^1.0.1" + "@jridgewell/sourcemap-codec" "^1.4.10" + "@jridgewell/trace-mapping" "^0.3.9" + +"@jridgewell/resolve-uri@^3.1.0": + version "3.1.1" + resolved "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.1.tgz" + integrity sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA== + +"@jridgewell/set-array@^1.0.1": + version "1.1.2" + resolved "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.1.2.tgz" + integrity sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw== + +"@jridgewell/sourcemap-codec@^1.4.10", "@jridgewell/sourcemap-codec@^1.4.14": + version "1.4.15" + resolved "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz" + integrity sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg== + +"@jridgewell/trace-mapping@^0.3.17", "@jridgewell/trace-mapping@^0.3.9": + version "0.3.20" + resolved "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.20.tgz" + integrity sha512-R8LcPeWZol2zR8mmH3JeKQ6QRCFb7XgUhV9ZlGhHLGyg4wpPiPZNQOOWhFZhxKw8u//yTbNGI42Bx/3paXEQ+Q== + dependencies: + "@jridgewell/resolve-uri" "^3.1.0" + "@jridgewell/sourcemap-codec" "^1.4.14" + +"@mapbox/jsonlint-lines-primitives@^2.0.2", "@mapbox/jsonlint-lines-primitives@~2.0.2": + version "2.0.2" + resolved "https://registry.npmjs.org/@mapbox/jsonlint-lines-primitives/-/jsonlint-lines-primitives-2.0.2.tgz" + integrity sha512-rY0o9A5ECsTQRVhv7tL/OyDpGAoUB4tTvLiW1DSzQGq4bvTPhNw1VpSNjDJc5GFZ2XuyOtSWSVN05qOtcD71qQ== + +"@mapbox/mapbox-gl-supported@^3.0.0": + version "3.0.0" + resolved "https://registry.npmjs.org/@mapbox/mapbox-gl-supported/-/mapbox-gl-supported-3.0.0.tgz" + integrity sha512-2XghOwu16ZwPJLOFVuIOaLbN0iKMn867evzXFyf0P22dqugezfJwLmdanAgU25ITvz1TvOfVP4jsDImlDJzcWg== + +"@mapbox/point-geometry@^0.1.0", "@mapbox/point-geometry@~0.1.0", "@mapbox/point-geometry@0.1.0": + version "0.1.0" + resolved "https://registry.npmjs.org/@mapbox/point-geometry/-/point-geometry-0.1.0.tgz" + integrity sha512-6j56HdLTwWGO0fJPlrZtdU/B13q8Uwmo18Ck2GnGgN9PCFyKTZ3UbXeEdRFh18i9XQ92eH2VdtpJHpBD3aripQ== + +"@mapbox/tiny-sdf@^2.0.6": + version "2.0.6" + resolved "https://registry.npmjs.org/@mapbox/tiny-sdf/-/tiny-sdf-2.0.6.tgz" + integrity sha512-qMqa27TLw+ZQz5Jk+RcwZGH7BQf5G/TrutJhspsca/3SHwmgKQ1iq+d3Jxz5oysPVYTGP6aXxCo5Lk9Er6YBAA== + +"@mapbox/unitbezier@^0.0.1": + version "0.0.1" + resolved "https://registry.npmjs.org/@mapbox/unitbezier/-/unitbezier-0.0.1.tgz" + integrity sha512-nMkuDXFv60aBr9soUG5q+GvZYL+2KZHVvsqFCzqnkGEf46U2fvmytHaEVc1/YZbiLn8X+eR3QzX1+dwDO1lxlw== + +"@mapbox/vector-tile@^1.3.1": + version "1.3.1" + resolved "https://registry.npmjs.org/@mapbox/vector-tile/-/vector-tile-1.3.1.tgz" + integrity sha512-MCEddb8u44/xfQ3oD+Srl/tNcQoqTw3goGk2oLsrFxOTc3dUp+kAnby3PvAeeBYSMSjSPD1nd1AJA6W49WnoUw== + dependencies: + "@mapbox/point-geometry" "~0.1.0" + +"@mapbox/whoots-js@^3.1.0": + version "3.1.0" + resolved "https://registry.npmjs.org/@mapbox/whoots-js/-/whoots-js-3.1.0.tgz" + integrity sha512-Es6WcD0nO5l+2BOQS4uLfNPYQaNDfbot3X1XUoloz+x0mPDS3eeORZJl06HXjwBG1fOGwCRnzK88LMdxKRrd6Q== + +"@maplibre/maplibre-gl-style-spec@^19.2.1": + version "19.3.3" + resolved "https://registry.npmjs.org/@maplibre/maplibre-gl-style-spec/-/maplibre-gl-style-spec-19.3.3.tgz" + integrity sha512-cOZZOVhDSulgK0meTsTkmNXb1ahVvmTmWmfx9gRBwc6hq98wS9JP35ESIoNq3xqEan+UN+gn8187Z6E4NKhLsw== + dependencies: + "@mapbox/jsonlint-lines-primitives" "~2.0.2" + "@mapbox/unitbezier" "^0.0.1" + json-stringify-pretty-compact "^3.0.0" + minimist "^1.2.8" + rw "^1.3.3" + sort-object "^3.0.3" + +"@mixmark-io/domino@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@mixmark-io/domino/-/domino-2.2.0.tgz" + integrity sha512-Y28PR25bHXUg88kCV7nivXrP2Nj2RueZ3/l/jdx6J9f8J4nsEGcgX0Qe6lt7Pa+J79+kPiJU3LguR6O/6zrLOw== + +"@mui/base@^5.0.0-beta.40", "@mui/base@5.0.0-beta.40": + version "5.0.0-beta.40" + resolved "https://registry.npmjs.org/@mui/base/-/base-5.0.0-beta.40.tgz" + integrity sha512-I/lGHztkCzvwlXpjD2+SNmvNQvB4227xBXhISPjEaJUXGImOQ9f3D2Yj/T3KasSI/h0MLWy74X0J6clhPmsRbQ== + dependencies: + "@babel/runtime" "^7.23.9" + "@floating-ui/react-dom" "^2.0.8" + "@mui/types" "^7.2.14" + "@mui/utils" "^5.15.14" + "@popperjs/core" "^2.11.8" + clsx "^2.1.0" + prop-types "^15.8.1" + +"@mui/core-downloads-tracker@^5.15.20": + version "5.15.20" + resolved "https://registry.npmjs.org/@mui/core-downloads-tracker/-/core-downloads-tracker-5.15.20.tgz" + integrity sha512-DoL2ppgldL16utL8nNyj/P12f8mCNdx/Hb/AJnX9rLY4b52hCMIx1kH83pbXQ6uMy6n54M3StmEbvSGoj2OFuA== + +"@mui/lab@^5.0.0-alpha.170": + version "5.0.0-alpha.170" + resolved "https://registry.npmjs.org/@mui/lab/-/lab-5.0.0-alpha.170.tgz" + integrity sha512-0bDVECGmrNjd3+bLdcLiwYZ0O4HP5j5WSQm5DV6iA/Z9kr8O6AnvZ1bv9ImQbbX7Gj3pX4o43EKwCutj3EQxQg== + dependencies: + "@babel/runtime" "^7.23.9" + "@mui/base" "5.0.0-beta.40" + "@mui/system" "^5.15.15" + "@mui/types" "^7.2.14" + "@mui/utils" "^5.15.14" + clsx "^2.1.0" + prop-types "^15.8.1" + +"@mui/material-nextjs@^5.15.11": + version "5.15.11" + resolved "https://registry.npmjs.org/@mui/material-nextjs/-/material-nextjs-5.15.11.tgz" + integrity sha512-cp5RWYbBngyi7NKP91R9QITllfxumCVPFjqe4AKzNROVuCot0VpgkafxXqfbv0uFsyUU0ROs0O2M3r17q604Aw== + dependencies: + "@babel/runtime" "^7.23.9" + +"@mui/material@^5.0.0", "@mui/material@^5.15.10", "@mui/material@^5.15.14", "@mui/material@^5.15.20", "@mui/material@>=5.15.0": + version "5.15.20" + resolved "https://registry.npmjs.org/@mui/material/-/material-5.15.20.tgz" + integrity sha512-tVq3l4qoXx/NxUgIx/x3lZiPn/5xDbdTE8VrLczNpfblLYZzlrbxA7kb9mI8NoBF6+w9WE9IrxWnKK5KlPI2bg== + dependencies: + "@babel/runtime" "^7.23.9" + "@mui/base" "5.0.0-beta.40" + "@mui/core-downloads-tracker" "^5.15.20" + "@mui/system" "^5.15.20" + "@mui/types" "^7.2.14" + "@mui/utils" "^5.15.20" + "@types/react-transition-group" "^4.4.10" + clsx "^2.1.0" + csstype "^3.1.3" + prop-types "^15.8.1" + react-is "^18.2.0" + react-transition-group "^4.4.5" + +"@mui/private-theming@^5.15.20": + version "5.15.20" + resolved "https://registry.npmjs.org/@mui/private-theming/-/private-theming-5.15.20.tgz" + integrity sha512-BK8F94AIqSrnaPYXf2KAOjGZJgWfvqAVQ2gVR3EryvQFtuBnG6RwodxrCvd3B48VuMy6Wsk897+lQMUxJyk+6g== + dependencies: + "@babel/runtime" "^7.23.9" + "@mui/utils" "^5.15.20" + prop-types "^15.8.1" + +"@mui/styled-engine@^5.15.14": + version "5.15.14" + resolved "https://registry.npmjs.org/@mui/styled-engine/-/styled-engine-5.15.14.tgz" + integrity sha512-RILkuVD8gY6PvjZjqnWhz8fu68dVkqhM5+jYWfB5yhlSQKg+2rHkmEwm75XIeAqI3qwOndK6zELK5H6Zxn4NHw== + dependencies: + "@babel/runtime" "^7.23.9" + "@emotion/cache" "^11.11.0" + csstype "^3.1.3" + prop-types "^15.8.1" + +"@mui/system@^5.15.15", "@mui/system@^5.15.20": + version "5.15.20" + resolved "https://registry.npmjs.org/@mui/system/-/system-5.15.20.tgz" + integrity sha512-LoMq4IlAAhxzL2VNUDBTQxAb4chnBe8JvRINVNDiMtHE2PiPOoHlhOPutSxEbaL5mkECPVWSv6p8JEV+uykwIA== + dependencies: + "@babel/runtime" "^7.23.9" + "@mui/private-theming" "^5.15.20" + "@mui/styled-engine" "^5.15.14" + "@mui/types" "^7.2.14" + "@mui/utils" "^5.15.20" + clsx "^2.1.0" + csstype "^3.1.3" + prop-types "^15.8.1" + +"@mui/types@^7.2.14": + version "7.2.14" + resolved "https://registry.npmjs.org/@mui/types/-/types-7.2.14.tgz" + integrity sha512-MZsBZ4q4HfzBsywtXgM1Ksj6HDThtiwmOKUXH1pKYISI9gAVXCNHNpo7TlGoGrBaYWZTdNoirIN7JsQcQUjmQQ== + +"@mui/utils@^5.15.14", "@mui/utils@^5.15.20": + version "5.15.20" + resolved "https://registry.npmjs.org/@mui/utils/-/utils-5.15.20.tgz" + integrity sha512-mAbYx0sovrnpAu1zHc3MDIhPqL8RPVC5W5xcO1b7PiSCJPtckIZmBkp8hefamAvUiAV8gpfMOM6Zb+eSisbI2A== + dependencies: + "@babel/runtime" "^7.23.9" + "@types/prop-types" "^15.7.11" + prop-types "^15.8.1" + react-is "^18.2.0" + +"@mui/x-data-grid@^7.7.0": + version "7.7.0" + resolved "https://registry.npmjs.org/@mui/x-data-grid/-/x-data-grid-7.7.0.tgz" + integrity sha512-s3Oii9EKcYPnL7M4g5evNley/J0slLL6xWRi0VwYqTHPGntBAMntUktMZ63bD/xko99f5ZcFoRBYTc55+mJ+AQ== + dependencies: + "@babel/runtime" "^7.24.7" + "@mui/system" "^5.15.15" + "@mui/utils" "^5.15.14" + clsx "^2.1.1" + prop-types "^15.8.1" + reselect "^4.1.8" + +"@mui/x-date-pickers@^7.7.0": + version "7.7.0" + resolved "https://registry.npmjs.org/@mui/x-date-pickers/-/x-date-pickers-7.7.0.tgz" + integrity sha512-huyoA22Vi8iCkee6ro0sX7CcFIcPV/Fl7ZGWwaQC8PTAheXhz823DjMYAiwRU/imF+UFYfUInWQ4XZCIkM+2Dw== + dependencies: + "@babel/runtime" "^7.24.7" + "@mui/base" "^5.0.0-beta.40" + "@mui/system" "^5.15.15" + "@mui/utils" "^5.15.14" + "@types/react-transition-group" "^4.4.10" + clsx "^2.1.1" + prop-types "^15.8.1" + react-transition-group "^4.4.5" + +"@mui/x-tree-view@^7.7.0": + version "7.7.0" + resolved "https://registry.npmjs.org/@mui/x-tree-view/-/x-tree-view-7.7.0.tgz" + integrity sha512-kUTMS77EcNjp1iXZlm4GGFzZHnQdZJfn2L9gvxAaHtNTDSRMS61jpsCcXknIyC797dmRPdALPewNzSOfkThF+Q== + dependencies: + "@babel/runtime" "^7.24.7" + "@mui/base" "^5.0.0-beta.40" + "@mui/system" "^5.15.15" + "@mui/utils" "^5.15.14" + "@types/react-transition-group" "^4.4.10" + clsx "^2.1.1" + prop-types "^15.8.1" + react-transition-group "^4.4.5" + +"@next/env@14.2.4": + version "14.2.4" + resolved "https://registry.npmjs.org/@next/env/-/env-14.2.4.tgz" + integrity sha512-3EtkY5VDkuV2+lNmKlbkibIJxcO4oIHEhBWne6PaAp+76J9KoSsGvNikp6ivzAT8dhhBMYrm6op2pS1ApG0Hzg== + +"@next/swc-win32-x64-msvc@14.2.4": + version "14.2.4" + resolved "https://registry.npmjs.org/@next/swc-win32-x64-msvc/-/swc-win32-x64-msvc-14.2.4.tgz" + integrity sha512-tkLrjBzqFTP8DVrAAQmZelEahfR9OxWpFR++vAI9FBhCiIxtwHwBHC23SBHCTURBtwB4kc/x44imVOnkKGNVGg== + +"@nodelib/fs.scandir@2.1.5": + version "2.1.5" + resolved "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz" + integrity sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g== + dependencies: + "@nodelib/fs.stat" "2.0.5" + run-parallel "^1.1.9" + +"@nodelib/fs.stat@^2.0.2", "@nodelib/fs.stat@2.0.5": + version "2.0.5" + resolved "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz" + integrity sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A== + +"@nodelib/fs.walk@^1.2.3", "@nodelib/fs.walk@^1.2.8": + version "1.2.8" + resolved "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz" + integrity sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg== + dependencies: + "@nodelib/fs.scandir" "2.1.5" + fastq "^1.6.0" + +"@pkgr/core@^0.1.0": + version "0.1.1" + resolved "https://registry.npmjs.org/@pkgr/core/-/core-0.1.1.tgz" + integrity sha512-cq8o4cWH0ibXh9VGi5P20Tu9XF/0fFXl9EUinr9QfTM7a7p0oTA4iJRCQWppXR1Pg8dSM0UCItCkPwsk9qWWYA== + +"@popperjs/core@^2.11.8", "@popperjs/core@^2.9.0": + version "2.11.8" + resolved "https://registry.npmjs.org/@popperjs/core/-/core-2.11.8.tgz" + integrity sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A== + +"@protobufjs/aspromise@^1.1.1", "@protobufjs/aspromise@^1.1.2": + version "1.1.2" + resolved "https://registry.npmjs.org/@protobufjs/aspromise/-/aspromise-1.1.2.tgz" + integrity sha512-j+gKExEuLmKwvz3OgROXtrJ2UG2x8Ch2YZUxahh+s1F2HZ+wAceUNLkvy6zKCPVRkU++ZWQrdxsUeQXmcg4uoQ== + +"@protobufjs/base64@^1.1.2": + version "1.1.2" + resolved "https://registry.npmjs.org/@protobufjs/base64/-/base64-1.1.2.tgz" + integrity sha512-AZkcAA5vnN/v4PDqKyMR5lx7hZttPDgClv83E//FMNhR2TMcLUhfRUBHCmSl0oi9zMgDDqRUJkSxO3wm85+XLg== + +"@protobufjs/codegen@^2.0.4": + version "2.0.4" + resolved "https://registry.npmjs.org/@protobufjs/codegen/-/codegen-2.0.4.tgz" + integrity sha512-YyFaikqM5sH0ziFZCN3xDC7zeGaB/d0IUb9CATugHWbd1FRFwWwt4ld4OYMPWu5a3Xe01mGAULCdqhMlPl29Jg== + +"@protobufjs/eventemitter@^1.1.0": + version "1.1.0" + resolved "https://registry.npmjs.org/@protobufjs/eventemitter/-/eventemitter-1.1.0.tgz" + integrity sha512-j9ednRT81vYJ9OfVuXG6ERSTdEL1xVsNgqpkxMsbIabzSo3goCjDIveeGv5d03om39ML71RdmrGNjG5SReBP/Q== + +"@protobufjs/fetch@^1.1.0": + version "1.1.0" + resolved "https://registry.npmjs.org/@protobufjs/fetch/-/fetch-1.1.0.tgz" + integrity sha512-lljVXpqXebpsijW71PZaCYeIcE5on1w5DlQy5WH6GLbFryLUrBD4932W/E2BSpfRJWseIL4v/KPgBFxDOIdKpQ== + dependencies: + "@protobufjs/aspromise" "^1.1.1" + "@protobufjs/inquire" "^1.1.0" + +"@protobufjs/float@^1.0.2": + version "1.0.2" + resolved "https://registry.npmjs.org/@protobufjs/float/-/float-1.0.2.tgz" + integrity sha512-Ddb+kVXlXst9d+R9PfTIxh1EdNkgoRe5tOX6t01f1lYWOvJnSPDBlG241QLzcyPdoNTsblLUdujGSE4RzrTZGQ== + +"@protobufjs/inquire@^1.1.0": + version "1.1.0" + resolved "https://registry.npmjs.org/@protobufjs/inquire/-/inquire-1.1.0.tgz" + integrity sha512-kdSefcPdruJiFMVSbn801t4vFK7KB/5gd2fYvrxhuJYg8ILrmn9SKSX2tZdV6V+ksulWqS7aXjBcRXl3wHoD9Q== + +"@protobufjs/path@^1.1.2": + version "1.1.2" + resolved "https://registry.npmjs.org/@protobufjs/path/-/path-1.1.2.tgz" + integrity sha512-6JOcJ5Tm08dOHAbdR3GrvP+yUUfkjG5ePsHYczMFLq3ZmMkAD98cDgcT2iA1lJ9NVwFd4tH/iSSoe44YWkltEA== + +"@protobufjs/pool@^1.1.0": + version "1.1.0" + resolved "https://registry.npmjs.org/@protobufjs/pool/-/pool-1.1.0.tgz" + integrity sha512-0kELaGSIDBKvcgS4zkjz1PeddatrjYcmMWOlAuAPwAeccUrPHdUqo/J6LiymHHEiJT5NrF1UVwxY14f+fy4WQw== + +"@protobufjs/utf8@^1.1.0": + version "1.1.0" + resolved "https://registry.npmjs.org/@protobufjs/utf8/-/utf8-1.1.0.tgz" + integrity sha512-Vvn3zZrhQZkkBE8LSuW3em98c0FwgO4nxzv6OdSxPKJIEKY2bGbHn+mhGIPerzI4twdxaP8/0+06HBpwf345Lw== + +"@react-pdf/fns@2.2.1": + version "2.2.1" + resolved "https://registry.npmjs.org/@react-pdf/fns/-/fns-2.2.1.tgz" + integrity sha512-s78aDg0vDYaijU5lLOCsUD+qinQbfOvcNeaoX9AiE7+kZzzCo6B/nX+l48cmt9OosJmvZvE9DWR9cLhrhOi2pA== + dependencies: + "@babel/runtime" "^7.20.13" + +"@react-pdf/font@^2.5.1": + version "2.5.1" + resolved "https://registry.npmjs.org/@react-pdf/font/-/font-2.5.1.tgz" + integrity sha512-Hyb2zBb92Glc3lvhmJfy4dO2Mj29KB26Uk12Ua9EhKAdiuCTLBqgP8Oe1cGwrvDI7xA4OOcwvBMdYh0vhOUHzA== + dependencies: + "@babel/runtime" "^7.20.13" + "@react-pdf/types" "^2.5.0" + cross-fetch "^3.1.5" + fontkit "^2.0.2" + is-url "^1.2.4" + +"@react-pdf/image@^2.3.6": + version "2.3.6" + resolved "https://registry.npmjs.org/@react-pdf/image/-/image-2.3.6.tgz" + integrity sha512-7iZDYZrZlJqNzS6huNl2XdMcLFUo68e6mOdzQeJ63d5eApdthhSHBnkGzHfLhH5t8DCpZNtClmklzuLL63ADfw== + dependencies: + "@babel/runtime" "^7.20.13" + "@react-pdf/png-js" "^2.3.1" + cross-fetch "^3.1.5" + jay-peg "^1.0.2" + +"@react-pdf/layout@^3.12.1": + version "3.12.1" + resolved "https://registry.npmjs.org/@react-pdf/layout/-/layout-3.12.1.tgz" + integrity sha512-BxSeykDxvADlpe4OGtQ7NH46QXq3uImAYsTHOPLCwbXMniQ1O3uCBx7H+HthxkCNshgYVPp9qS3KyvQv/oIZwg== + dependencies: + "@babel/runtime" "^7.20.13" + "@react-pdf/fns" "2.2.1" + "@react-pdf/image" "^2.3.6" + "@react-pdf/pdfkit" "^3.1.10" + "@react-pdf/primitives" "^3.1.1" + "@react-pdf/stylesheet" "^4.2.5" + "@react-pdf/textkit" "^4.4.1" + "@react-pdf/types" "^2.5.0" + cross-fetch "^3.1.5" + emoji-regex "^10.3.0" + queue "^6.0.1" + yoga-layout "^2.0.1" + +"@react-pdf/pdfkit@^3.1.10": + version "3.1.10" + resolved "https://registry.npmjs.org/@react-pdf/pdfkit/-/pdfkit-3.1.10.tgz" + integrity sha512-P/qPBtCFo2HDJD0i6NfbmoBRrsOVO8CIogYsefwG4fklTo50zNgnMM5U1WLckTuX8Qt1ThiQuokmTG5arheblA== + dependencies: + "@babel/runtime" "^7.20.13" + "@react-pdf/png-js" "^2.3.1" + browserify-zlib "^0.2.0" + crypto-js "^4.2.0" + fontkit "^2.0.2" + jay-peg "^1.0.2" + vite-compatible-readable-stream "^3.6.1" + +"@react-pdf/png-js@^2.3.1": + version "2.3.1" + resolved "https://registry.npmjs.org/@react-pdf/png-js/-/png-js-2.3.1.tgz" + integrity sha512-pEZ18I4t1vAUS4lmhvXPmXYP4PHeblpWP/pAlMMRkEyP7tdAeHUN7taQl9sf9OPq7YITMY3lWpYpJU6t4CZgZg== + dependencies: + browserify-zlib "^0.2.0" + +"@react-pdf/primitives@^3.1.1": + version "3.1.1" + resolved "https://registry.npmjs.org/@react-pdf/primitives/-/primitives-3.1.1.tgz" + integrity sha512-miwjxLwTnO3IjoqkTVeTI+9CdyDggwekmSLhVCw+a/7FoQc+gF3J2dSKwsHvAcVFM0gvU8mzCeTofgw0zPDq0w== + +"@react-pdf/render@^3.4.4": + version "3.4.4" + resolved "https://registry.npmjs.org/@react-pdf/render/-/render-3.4.4.tgz" + integrity sha512-CfGxWmVgrY3JgmB1iMnz2W6Ck+8pisZeFt8vGlxP+JfT+0onr208pQvGSV5KwA9LGhAdABxqc/+y17V3vtKdFA== + dependencies: + "@babel/runtime" "^7.20.13" + "@react-pdf/fns" "2.2.1" + "@react-pdf/primitives" "^3.1.1" + "@react-pdf/textkit" "^4.4.1" + "@react-pdf/types" "^2.5.0" + abs-svg-path "^0.1.1" + color-string "^1.9.1" + normalize-svg-path "^1.1.0" + parse-svg-path "^0.1.2" + svg-arc-to-cubic-bezier "^3.2.0" + +"@react-pdf/renderer@^3.4.4": + version "3.4.4" + resolved "https://registry.npmjs.org/@react-pdf/renderer/-/renderer-3.4.4.tgz" + integrity sha512-j1TWMHHXDeHdoQE3xjhBh0MZ2rn7wHIlP/uglr/EJZXqnPbfg6bfLzRJCM6bs+XJV3d8+zLQjHf6sF/fWcBDfg== + dependencies: + "@babel/runtime" "^7.20.13" + "@react-pdf/font" "^2.5.1" + "@react-pdf/layout" "^3.12.1" + "@react-pdf/pdfkit" "^3.1.10" + "@react-pdf/primitives" "^3.1.1" + "@react-pdf/render" "^3.4.4" + "@react-pdf/types" "^2.5.0" + events "^3.3.0" + object-assign "^4.1.1" + prop-types "^15.6.2" + queue "^6.0.1" + scheduler "^0.17.0" + +"@react-pdf/stylesheet@^4.2.5": + version "4.2.5" + resolved "https://registry.npmjs.org/@react-pdf/stylesheet/-/stylesheet-4.2.5.tgz" + integrity sha512-XnmapeCW+hDuNdVwpuvO04WKv71wAs8aH+saIq29Bo2fp1SxznHTcQArTZtK6Wgr/E9BHXeB2iAPpUZuI6G+xA== + dependencies: + "@babel/runtime" "^7.20.13" + "@react-pdf/fns" "2.2.1" + "@react-pdf/types" "^2.5.0" + color-string "^1.9.1" + hsl-to-hex "^1.0.0" + media-engine "^1.0.3" + postcss-value-parser "^4.1.0" + +"@react-pdf/textkit@^4.4.1": + version "4.4.1" + resolved "https://registry.npmjs.org/@react-pdf/textkit/-/textkit-4.4.1.tgz" + integrity sha512-Jl9wdTqIvJ5pX+vAGz0EOhP7ut5Two9H6CzTKo/YYPeD79cM2yTXF3JzTERBC28y7LR0Waq9D2LHQjI+b/EYUQ== + dependencies: + "@babel/runtime" "^7.20.13" + "@react-pdf/fns" "2.2.1" + bidi-js "^1.0.2" + hyphen "^1.6.4" + unicode-properties "^1.4.1" + +"@react-pdf/types@^2.5.0": + version "2.5.0" + resolved "https://registry.npmjs.org/@react-pdf/types/-/types-2.5.0.tgz" + integrity sha512-XsVRkt0hQ60I4e3leAVt+aZR3KJCaJd179BfJHAv4F4x6Vq3yqkry8lcbUWKGKDw1j3/8sW4FsgGR41SFvsG9A== + +"@remirror/core-constants@^2.0.2": + version "2.0.2" + resolved "https://registry.npmjs.org/@remirror/core-constants/-/core-constants-2.0.2.tgz" + integrity sha512-dyHY+sMF0ihPus3O27ODd4+agdHMEmuRdyiZJ2CCWjPV5UFmn17ZbElvk6WOGVE4rdCJKZQCrPV2BcikOMLUGQ== + +"@smithy/abort-controller@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/abort-controller/-/abort-controller-2.2.0.tgz" + integrity sha512-wRlta7GuLWpTqtFfGo+nZyOO1vEvewdNR1R4rTxpC8XU6vG/NDyrFBhwLZsqg1NUoR1noVaXJPC/7ZK47QCySw== + dependencies: + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/config-resolver@^2.0.5", "@smithy/config-resolver@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/config-resolver/-/config-resolver-2.2.0.tgz" + integrity sha512-fsiMgd8toyUba6n1WRmr+qACzXltpdDkPTAaDqc8QqPBUzO+/JKwL6bUBseHVi8tu9l+3JOK+tSf7cay+4B3LA== + dependencies: + "@smithy/node-config-provider" "^2.3.0" + "@smithy/types" "^2.12.0" + "@smithy/util-config-provider" "^2.3.0" + "@smithy/util-middleware" "^2.2.0" + tslib "^2.6.2" + +"@smithy/credential-provider-imds@^2.0.0", "@smithy/credential-provider-imds@^2.3.0": + version "2.3.0" + resolved "https://registry.npmjs.org/@smithy/credential-provider-imds/-/credential-provider-imds-2.3.0.tgz" + integrity sha512-BWB9mIukO1wjEOo1Ojgl6LrG4avcaC7T/ZP6ptmAaW4xluhSIPZhY+/PI5YKzlk+jsm+4sQZB45Bt1OfMeQa3w== + dependencies: + "@smithy/node-config-provider" "^2.3.0" + "@smithy/property-provider" "^2.2.0" + "@smithy/types" "^2.12.0" + "@smithy/url-parser" "^2.2.0" + tslib "^2.6.2" + +"@smithy/eventstream-codec@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/eventstream-codec/-/eventstream-codec-2.2.0.tgz" + integrity sha512-8janZoJw85nJmQZc4L8TuePp2pk1nxLgkxIR0TUjKJ5Dkj5oelB9WtiSSGXCQvNsJl0VSTvK/2ueMXxvpa9GVw== + dependencies: + "@aws-crypto/crc32" "3.0.0" + "@smithy/types" "^2.12.0" + "@smithy/util-hex-encoding" "^2.2.0" + tslib "^2.6.2" + +"@smithy/eventstream-serde-browser@^2.0.5": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/eventstream-serde-browser/-/eventstream-serde-browser-2.2.0.tgz" + integrity sha512-UaPf8jKbcP71BGiO0CdeLmlg+RhWnlN8ipsMSdwvqBFigl5nil3rHOI/5GE3tfiuX8LvY5Z9N0meuU7Rab7jWw== + dependencies: + "@smithy/eventstream-serde-universal" "^2.2.0" + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/eventstream-serde-config-resolver@^2.0.5": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/eventstream-serde-config-resolver/-/eventstream-serde-config-resolver-2.2.0.tgz" + integrity sha512-RHhbTw/JW3+r8QQH7PrganjNCiuiEZmpi6fYUAetFfPLfZ6EkiA08uN3EFfcyKubXQxOwTeJRZSQmDDCdUshaA== + dependencies: + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/eventstream-serde-node@^2.0.5": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/eventstream-serde-node/-/eventstream-serde-node-2.2.0.tgz" + integrity sha512-zpQMtJVqCUMn+pCSFcl9K/RPNtQE0NuMh8sKpCdEHafhwRsjP50Oq/4kMmvxSRy6d8Jslqd8BLvDngrUtmN9iA== + dependencies: + "@smithy/eventstream-serde-universal" "^2.2.0" + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/eventstream-serde-universal@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/eventstream-serde-universal/-/eventstream-serde-universal-2.2.0.tgz" + integrity sha512-pvoe/vvJY0mOpuF84BEtyZoYfbehiFj8KKWk1ds2AT0mTLYFVs+7sBJZmioOFdBXKd48lfrx1vumdPdmGlCLxA== + dependencies: + "@smithy/eventstream-codec" "^2.2.0" + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/fetch-http-handler@^2.0.5", "@smithy/fetch-http-handler@^2.5.0": + version "2.5.0" + resolved "https://registry.npmjs.org/@smithy/fetch-http-handler/-/fetch-http-handler-2.5.0.tgz" + integrity sha512-BOWEBeppWhLn/no/JxUL/ghTfANTjT7kg3Ww2rPqTUY9R4yHPXxJ9JhMe3Z03LN3aPwiwlpDIUcVw1xDyHqEhw== + dependencies: + "@smithy/protocol-http" "^3.3.0" + "@smithy/querystring-builder" "^2.2.0" + "@smithy/types" "^2.12.0" + "@smithy/util-base64" "^2.3.0" + tslib "^2.6.2" + +"@smithy/hash-node@^2.0.5": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/hash-node/-/hash-node-2.2.0.tgz" + integrity sha512-zLWaC/5aWpMrHKpoDF6nqpNtBhlAYKF/7+9yMN7GpdR8CzohnWfGtMznPybnwSS8saaXBMxIGwJqR4HmRp6b3g== + dependencies: + "@smithy/types" "^2.12.0" + "@smithy/util-buffer-from" "^2.2.0" + "@smithy/util-utf8" "^2.3.0" + tslib "^2.6.2" + +"@smithy/invalid-dependency@^2.0.5": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/invalid-dependency/-/invalid-dependency-2.2.0.tgz" + integrity sha512-nEDASdbKFKPXN2O6lOlTgrEEOO9NHIeO+HVvZnkqc8h5U9g3BIhWsvzFo+UcUbliMHvKNPD/zVxDrkP1Sbgp8Q== + dependencies: + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/is-array-buffer@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/is-array-buffer/-/is-array-buffer-2.2.0.tgz" + integrity sha512-GGP3O9QFD24uGeAXYUjwSTXARoqpZykHadOmA8G5vfJPK0/DC67qa//0qvqrJzL1xc8WQWX7/yc7fwudjPHPhA== + dependencies: + tslib "^2.6.2" + +"@smithy/md5-js@2.0.7": + version "2.0.7" + resolved "https://registry.npmjs.org/@smithy/md5-js/-/md5-js-2.0.7.tgz" + integrity sha512-2i2BpXF9pI5D1xekqUsgQ/ohv5+H//G9FlawJrkOJskV18PgJ8LiNbLiskMeYt07yAsSTZR7qtlcAaa/GQLWww== + dependencies: + "@smithy/types" "^2.3.1" + "@smithy/util-utf8" "^2.0.0" + tslib "^2.5.0" + +"@smithy/middleware-content-length@^2.0.5": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/middleware-content-length/-/middleware-content-length-2.2.0.tgz" + integrity sha512-5bl2LG1Ah/7E5cMSC+q+h3IpVHMeOkG0yLRyQT1p2aMJkSrZG7RlXHPuAgb7EyaFeidKEnnd/fNaLLaKlHGzDQ== + dependencies: + "@smithy/protocol-http" "^3.3.0" + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/middleware-endpoint@^2.0.5", "@smithy/middleware-endpoint@^2.5.1": + version "2.5.1" + resolved "https://registry.npmjs.org/@smithy/middleware-endpoint/-/middleware-endpoint-2.5.1.tgz" + integrity sha512-1/8kFp6Fl4OsSIVTWHnNjLnTL8IqpIb/D3sTSczrKFnrE9VMNWxnrRKNvpUHOJ6zpGD5f62TPm7+17ilTJpiCQ== + dependencies: + "@smithy/middleware-serde" "^2.3.0" + "@smithy/node-config-provider" "^2.3.0" + "@smithy/shared-ini-file-loader" "^2.4.0" + "@smithy/types" "^2.12.0" + "@smithy/url-parser" "^2.2.0" + "@smithy/util-middleware" "^2.2.0" + tslib "^2.6.2" + +"@smithy/middleware-retry@^2.0.5": + version "2.3.1" + resolved "https://registry.npmjs.org/@smithy/middleware-retry/-/middleware-retry-2.3.1.tgz" + integrity sha512-P2bGufFpFdYcWvqpyqqmalRtwFUNUA8vHjJR5iGqbfR6mp65qKOLcUd6lTr4S9Gn/enynSrSf3p3FVgVAf6bXA== + dependencies: + "@smithy/node-config-provider" "^2.3.0" + "@smithy/protocol-http" "^3.3.0" + "@smithy/service-error-classification" "^2.1.5" + "@smithy/smithy-client" "^2.5.1" + "@smithy/types" "^2.12.0" + "@smithy/util-middleware" "^2.2.0" + "@smithy/util-retry" "^2.2.0" + tslib "^2.6.2" + uuid "^9.0.1" + +"@smithy/middleware-serde@^2.0.5", "@smithy/middleware-serde@^2.3.0": + version "2.3.0" + resolved "https://registry.npmjs.org/@smithy/middleware-serde/-/middleware-serde-2.3.0.tgz" + integrity sha512-sIADe7ojwqTyvEQBe1nc/GXB9wdHhi9UwyX0lTyttmUWDJLP655ZYE1WngnNyXREme8I27KCaUhyhZWRXL0q7Q== + dependencies: + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/middleware-stack@^2.0.0", "@smithy/middleware-stack@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/middleware-stack/-/middleware-stack-2.2.0.tgz" + integrity sha512-Qntc3jrtwwrsAC+X8wms8zhrTr0sFXnyEGhZd9sLtsJ/6gGQKFzNB+wWbOcpJd7BR8ThNCoKt76BuQahfMvpeA== + dependencies: + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/node-config-provider@^2.0.5", "@smithy/node-config-provider@^2.3.0": + version "2.3.0" + resolved "https://registry.npmjs.org/@smithy/node-config-provider/-/node-config-provider-2.3.0.tgz" + integrity sha512-0elK5/03a1JPWMDPaS726Iw6LpQg80gFut1tNpPfxFuChEEklo2yL823V94SpTZTxmKlXFtFgsP55uh3dErnIg== + dependencies: + "@smithy/property-provider" "^2.2.0" + "@smithy/shared-ini-file-loader" "^2.4.0" + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/node-http-handler@^2.0.5", "@smithy/node-http-handler@^2.5.0": + version "2.5.0" + resolved "https://registry.npmjs.org/@smithy/node-http-handler/-/node-http-handler-2.5.0.tgz" + integrity sha512-mVGyPBzkkGQsPoxQUbxlEfRjrj6FPyA3u3u2VXGr9hT8wilsoQdZdvKpMBFMB8Crfhv5dNkKHIW0Yyuc7eABqA== + dependencies: + "@smithy/abort-controller" "^2.2.0" + "@smithy/protocol-http" "^3.3.0" + "@smithy/querystring-builder" "^2.2.0" + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/property-provider@^2.0.0", "@smithy/property-provider@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/property-provider/-/property-provider-2.2.0.tgz" + integrity sha512-+xiil2lFhtTRzXkx8F053AV46QnIw6e7MV8od5Mi68E1ICOjCeCHw2XfLnDEUHnT9WGUIkwcqavXjfwuJbGlpg== + dependencies: + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/protocol-http@^2.0.5": + version "2.0.5" + resolved "https://registry.npmjs.org/@smithy/protocol-http/-/protocol-http-2.0.5.tgz" + integrity sha512-d2hhHj34mA2V86doiDfrsy2fNTnUOowGaf9hKb0hIPHqvcnShU4/OSc4Uf1FwHkAdYF3cFXTrj5VGUYbEuvMdw== + dependencies: + "@smithy/types" "^2.2.2" + tslib "^2.5.0" + +"@smithy/protocol-http@^3.3.0": + version "3.3.0" + resolved "https://registry.npmjs.org/@smithy/protocol-http/-/protocol-http-3.3.0.tgz" + integrity sha512-Xy5XK1AFWW2nlY/biWZXu6/krgbaf2dg0q492D8M5qthsnU2H+UgFeZLbM76FnH7s6RO/xhQRkj+T6KBO3JzgQ== + dependencies: + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/querystring-builder@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/querystring-builder/-/querystring-builder-2.2.0.tgz" + integrity sha512-L1kSeviUWL+emq3CUVSgdogoM/D9QMFaqxL/dd0X7PCNWmPXqt+ExtrBjqT0V7HLN03Vs9SuiLrG3zy3JGnE5A== + dependencies: + "@smithy/types" "^2.12.0" + "@smithy/util-uri-escape" "^2.2.0" + tslib "^2.6.2" + +"@smithy/querystring-parser@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/querystring-parser/-/querystring-parser-2.2.0.tgz" + integrity sha512-BvHCDrKfbG5Yhbpj4vsbuPV2GgcpHiAkLeIlcA1LtfpMz3jrqizP1+OguSNSj1MwBHEiN+jwNisXLGdajGDQJA== + dependencies: + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/service-error-classification@^2.1.5": + version "2.1.5" + resolved "https://registry.npmjs.org/@smithy/service-error-classification/-/service-error-classification-2.1.5.tgz" + integrity sha512-uBDTIBBEdAQryvHdc5W8sS5YX7RQzF683XrHePVdFmAgKiMofU15FLSM0/HU03hKTnazdNRFa0YHS7+ArwoUSQ== + dependencies: + "@smithy/types" "^2.12.0" + +"@smithy/shared-ini-file-loader@^2.0.0", "@smithy/shared-ini-file-loader@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@smithy/shared-ini-file-loader/-/shared-ini-file-loader-2.4.0.tgz" + integrity sha512-WyujUJL8e1B6Z4PBfAqC/aGY1+C7T0w20Gih3yrvJSk97gpiVfB+y7c46T4Nunk+ZngLq0rOIdeVeIklk0R3OA== + dependencies: + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/signature-v4@^2.0.0": + version "2.3.0" + resolved "https://registry.npmjs.org/@smithy/signature-v4/-/signature-v4-2.3.0.tgz" + integrity sha512-ui/NlpILU+6HAQBfJX8BBsDXuKSNrjTSuOYArRblcrErwKFutjrCNb/OExfVRyj9+26F9J+ZmfWT+fKWuDrH3Q== + dependencies: + "@smithy/is-array-buffer" "^2.2.0" + "@smithy/types" "^2.12.0" + "@smithy/util-hex-encoding" "^2.2.0" + "@smithy/util-middleware" "^2.2.0" + "@smithy/util-uri-escape" "^2.2.0" + "@smithy/util-utf8" "^2.3.0" + tslib "^2.6.2" + +"@smithy/smithy-client@^2.0.5", "@smithy/smithy-client@^2.5.1": + version "2.5.1" + resolved "https://registry.npmjs.org/@smithy/smithy-client/-/smithy-client-2.5.1.tgz" + integrity sha512-jrbSQrYCho0yDaaf92qWgd+7nAeap5LtHTI51KXqmpIFCceKU3K9+vIVTUH72bOJngBMqa4kyu1VJhRcSrk/CQ== + dependencies: + "@smithy/middleware-endpoint" "^2.5.1" + "@smithy/middleware-stack" "^2.2.0" + "@smithy/protocol-http" "^3.3.0" + "@smithy/types" "^2.12.0" + "@smithy/util-stream" "^2.2.0" + tslib "^2.6.2" + +"@smithy/types@^2.1.0", "@smithy/types@^2.12.0", "@smithy/types@^2.2.2", "@smithy/types@^2.3.1": + version "2.12.0" + resolved "https://registry.npmjs.org/@smithy/types/-/types-2.12.0.tgz" + integrity sha512-QwYgloJ0sVNBeBuBs65cIkTbfzV/Q6ZNPCJ99EICFEdJYG50nGIY/uYXp+TbsdJReIuPr0a0kXmCvren3MbRRw== + dependencies: + tslib "^2.6.2" + +"@smithy/url-parser@^2.0.5", "@smithy/url-parser@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/url-parser/-/url-parser-2.2.0.tgz" + integrity sha512-hoA4zm61q1mNTpksiSWp2nEl1dt3j726HdRhiNgVJQMj7mLp7dprtF57mOB6JvEk/x9d2bsuL5hlqZbBuHQylQ== + dependencies: + "@smithy/querystring-parser" "^2.2.0" + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/util-base64@^2.0.0", "@smithy/util-base64@^2.3.0": + version "2.3.0" + resolved "https://registry.npmjs.org/@smithy/util-base64/-/util-base64-2.3.0.tgz" + integrity sha512-s3+eVwNeJuXUwuMbusncZNViuhv2LjVJ1nMwTqSA0XAC7gjKhqqxRdJPhR8+YrkoZ9IiIbFk/yK6ACe/xlF+hw== + dependencies: + "@smithy/util-buffer-from" "^2.2.0" + "@smithy/util-utf8" "^2.3.0" + tslib "^2.6.2" + +"@smithy/util-body-length-browser@^2.0.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/util-body-length-browser/-/util-body-length-browser-2.2.0.tgz" + integrity sha512-dtpw9uQP7W+n3vOtx0CfBD5EWd7EPdIdsQnWTDoFf77e3VUf05uA7R7TGipIo8e4WL2kuPdnsr3hMQn9ziYj5w== + dependencies: + tslib "^2.6.2" + +"@smithy/util-body-length-node@^2.1.0": + version "2.3.0" + resolved "https://registry.npmjs.org/@smithy/util-body-length-node/-/util-body-length-node-2.3.0.tgz" + integrity sha512-ITWT1Wqjubf2CJthb0BuT9+bpzBfXeMokH/AAa5EJQgbv9aPMVfnM76iFIZVFf50hYXGbtiV71BHAthNWd6+dw== + dependencies: + tslib "^2.6.2" + +"@smithy/util-buffer-from@^2.0.0", "@smithy/util-buffer-from@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/util-buffer-from/-/util-buffer-from-2.2.0.tgz" + integrity sha512-IJdWBbTcMQ6DA0gdNhh/BwrLkDR+ADW5Kr1aZmd4k3DIF6ezMV4R2NIAmT08wQJ3yUK82thHWmC/TnK/wpMMIA== + dependencies: + "@smithy/is-array-buffer" "^2.2.0" + tslib "^2.6.2" + +"@smithy/util-config-provider@^2.3.0": + version "2.3.0" + resolved "https://registry.npmjs.org/@smithy/util-config-provider/-/util-config-provider-2.3.0.tgz" + integrity sha512-HZkzrRcuFN1k70RLqlNK4FnPXKOpkik1+4JaBoHNJn+RnJGYqaa3c5/+XtLOXhlKzlRgNvyaLieHTW2VwGN0VQ== + dependencies: + tslib "^2.6.2" + +"@smithy/util-defaults-mode-browser@^2.0.5": + version "2.2.1" + resolved "https://registry.npmjs.org/@smithy/util-defaults-mode-browser/-/util-defaults-mode-browser-2.2.1.tgz" + integrity sha512-RtKW+8j8skk17SYowucwRUjeh4mCtnm5odCL0Lm2NtHQBsYKrNW0od9Rhopu9wF1gHMfHeWF7i90NwBz/U22Kw== + dependencies: + "@smithy/property-provider" "^2.2.0" + "@smithy/smithy-client" "^2.5.1" + "@smithy/types" "^2.12.0" + bowser "^2.11.0" + tslib "^2.6.2" + +"@smithy/util-defaults-mode-node@^2.0.5": + version "2.3.1" + resolved "https://registry.npmjs.org/@smithy/util-defaults-mode-node/-/util-defaults-mode-node-2.3.1.tgz" + integrity sha512-vkMXHQ0BcLFysBMWgSBLSk3+leMpFSyyFj8zQtv5ZyUBx8/owVh1/pPEkzmW/DR/Gy/5c8vjLDD9gZjXNKbrpA== + dependencies: + "@smithy/config-resolver" "^2.2.0" + "@smithy/credential-provider-imds" "^2.3.0" + "@smithy/node-config-provider" "^2.3.0" + "@smithy/property-provider" "^2.2.0" + "@smithy/smithy-client" "^2.5.1" + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/util-hex-encoding@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/util-hex-encoding/-/util-hex-encoding-2.2.0.tgz" + integrity sha512-7iKXR+/4TpLK194pVjKiasIyqMtTYJsgKgM242Y9uzt5dhHnUDvMNb+3xIhRJ9QhvqGii/5cRUt4fJn3dtXNHQ== + dependencies: + tslib "^2.6.2" + +"@smithy/util-hex-encoding@2.0.0": + version "2.0.0" + resolved "https://registry.npmjs.org/@smithy/util-hex-encoding/-/util-hex-encoding-2.0.0.tgz" + integrity sha512-c5xY+NUnFqG6d7HFh1IFfrm3mGl29lC+vF+geHv4ToiuJCBmIfzx6IeHLg+OgRdPFKDXIw6pvi+p3CsscaMcMA== + dependencies: + tslib "^2.5.0" + +"@smithy/util-middleware@^2.0.0", "@smithy/util-middleware@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/util-middleware/-/util-middleware-2.2.0.tgz" + integrity sha512-L1qpleXf9QD6LwLCJ5jddGkgWyuSvWBkJwWAZ6kFkdifdso+sk3L3O1HdmPvCdnCK3IS4qWyPxev01QMnfHSBw== + dependencies: + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/util-retry@^2.0.0", "@smithy/util-retry@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/util-retry/-/util-retry-2.2.0.tgz" + integrity sha512-q9+pAFPTfftHXRytmZ7GzLFFrEGavqapFc06XxzZFcSIGERXMerXxCitjOG1prVDR9QdjqotF40SWvbqcCpf8g== + dependencies: + "@smithy/service-error-classification" "^2.1.5" + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@smithy/util-stream@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/util-stream/-/util-stream-2.2.0.tgz" + integrity sha512-17faEXbYWIRst1aU9SvPZyMdWmqIrduZjVOqCPMIsWFNxs5yQQgFrJL6b2SdiCzyW9mJoDjFtgi53xx7EH+BXA== + dependencies: + "@smithy/fetch-http-handler" "^2.5.0" + "@smithy/node-http-handler" "^2.5.0" + "@smithy/types" "^2.12.0" + "@smithy/util-base64" "^2.3.0" + "@smithy/util-buffer-from" "^2.2.0" + "@smithy/util-hex-encoding" "^2.2.0" + "@smithy/util-utf8" "^2.3.0" + tslib "^2.6.2" + +"@smithy/util-uri-escape@^2.2.0": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/util-uri-escape/-/util-uri-escape-2.2.0.tgz" + integrity sha512-jtmJMyt1xMD/d8OtbVJ2gFZOSKc+ueYJZPW20ULW1GOp/q/YIM0wNh+u8ZFao9UaIGz4WoPW8hC64qlWLIfoDA== + dependencies: + tslib "^2.6.2" + +"@smithy/util-utf8@^2.0.0", "@smithy/util-utf8@2.0.0": + version "2.0.0" + resolved "https://registry.npmjs.org/@smithy/util-utf8/-/util-utf8-2.0.0.tgz" + integrity sha512-rctU1VkziY84n5OXe3bPNpKR001ZCME2JCaBBFgtiM2hfKbHFudc/BkMuPab8hRbLd0j3vbnBTTZ1igBf0wgiQ== + dependencies: + "@smithy/util-buffer-from" "^2.0.0" + tslib "^2.5.0" + +"@smithy/util-utf8@^2.3.0": + version "2.3.0" + resolved "https://registry.npmjs.org/@smithy/util-utf8/-/util-utf8-2.3.0.tgz" + integrity sha512-R8Rdn8Hy72KKcebgLiv8jQcQkXoLMOGGv5uI1/k0l+snqkOzQ1R0ChUBCxWMlBsFMekWjq0wRudIweFs7sKT5A== + dependencies: + "@smithy/util-buffer-from" "^2.2.0" + tslib "^2.6.2" + +"@smithy/util-waiter@^2.0.5": + version "2.2.0" + resolved "https://registry.npmjs.org/@smithy/util-waiter/-/util-waiter-2.2.0.tgz" + integrity sha512-IHk53BVw6MPMi2Gsn+hCng8rFA3ZmR3Rk7GllxDUW9qFJl/hiSvskn7XldkECapQVkIg/1dHpMAxI9xSTaLLSA== + dependencies: + "@smithy/abort-controller" "^2.2.0" + "@smithy/types" "^2.12.0" + tslib "^2.6.2" + +"@supabase/auth-js@2.64.2": + version "2.64.2" + resolved "https://registry.npmjs.org/@supabase/auth-js/-/auth-js-2.64.2.tgz" + integrity sha512-s+lkHEdGiczDrzXJ1YWt2y3bxRi+qIUnXcgkpLSrId7yjBeaXBFygNjTaoZLG02KNcYwbuZ9qkEIqmj2hF7svw== + dependencies: + "@supabase/node-fetch" "^2.6.14" + +"@supabase/functions-js@2.3.1": + version "2.3.1" + resolved "https://registry.npmjs.org/@supabase/functions-js/-/functions-js-2.3.1.tgz" + integrity sha512-QyzNle/rVzlOi4BbVqxLSH828VdGY1RElqGFAj+XeVypj6+PVtMlD21G8SDnsPQDtlqqTtoGRgdMlQZih5hTuw== + dependencies: + "@supabase/node-fetch" "^2.6.14" + +"@supabase/node-fetch@^2.6.14", "@supabase/node-fetch@2.6.15": + version "2.6.15" + resolved "https://registry.npmjs.org/@supabase/node-fetch/-/node-fetch-2.6.15.tgz" + integrity sha512-1ibVeYUacxWYi9i0cf5efil6adJ9WRyZBLivgjs+AUpewx1F3xPi7gLgaASI2SmIQxPoCEjAsLAzKPgMJVgOUQ== + dependencies: + whatwg-url "^5.0.0" + +"@supabase/postgrest-js@1.15.2": + version "1.15.2" + resolved "https://registry.npmjs.org/@supabase/postgrest-js/-/postgrest-js-1.15.2.tgz" + integrity sha512-9/7pUmXExvGuEK1yZhVYXPZnLEkDTwxgMQHXLrN5BwPZZm4iUCL1YEyep/Z2lIZah8d8M433mVAUEGsihUj5KQ== + dependencies: + "@supabase/node-fetch" "^2.6.14" + +"@supabase/realtime-js@2.9.5": + version "2.9.5" + resolved "https://registry.npmjs.org/@supabase/realtime-js/-/realtime-js-2.9.5.tgz" + integrity sha512-TEHlGwNGGmKPdeMtca1lFTYCedrhTAv3nZVoSjrKQ+wkMmaERuCe57zkC5KSWFzLYkb5FVHW8Hrr+PX1DDwplQ== + dependencies: + "@supabase/node-fetch" "^2.6.14" + "@types/phoenix" "^1.5.4" + "@types/ws" "^8.5.10" + ws "^8.14.2" + +"@supabase/storage-js@2.5.5": + version "2.5.5" + resolved "https://registry.npmjs.org/@supabase/storage-js/-/storage-js-2.5.5.tgz" + integrity sha512-OpLoDRjFwClwc2cjTJZG8XviTiQH4Ik8sCiMK5v7et0MDu2QlXjCAW3ljxJB5+z/KazdMOTnySi+hysxWUPu3w== + dependencies: + "@supabase/node-fetch" "^2.6.14" + +"@supabase/supabase-js@^2.43.4": + version "2.43.4" + resolved "https://registry.npmjs.org/@supabase/supabase-js/-/supabase-js-2.43.4.tgz" + integrity sha512-/pLPaxiIsn5Vaz3s32HC6O/VNwfeddnzS0bZRpOW0AKcPuXroD8pT9G8mpiBlZfpKsMmq6k7tlhW7Sr1PAQ1lw== + dependencies: + "@supabase/auth-js" "2.64.2" + "@supabase/functions-js" "2.3.1" + "@supabase/node-fetch" "2.6.15" + "@supabase/postgrest-js" "1.15.2" + "@supabase/realtime-js" "2.9.5" + "@supabase/storage-js" "2.5.5" + +"@svgr/babel-plugin-add-jsx-attribute@8.0.0": + version "8.0.0" + resolved "https://registry.npmjs.org/@svgr/babel-plugin-add-jsx-attribute/-/babel-plugin-add-jsx-attribute-8.0.0.tgz" + integrity sha512-b9MIk7yhdS1pMCZM8VeNfUlSKVRhsHZNMl5O9SfaX0l0t5wjdgu4IDzGB8bpnGBBOjGST3rRFVsaaEtI4W6f7g== + +"@svgr/babel-plugin-remove-jsx-attribute@8.0.0": + version "8.0.0" + resolved "https://registry.npmjs.org/@svgr/babel-plugin-remove-jsx-attribute/-/babel-plugin-remove-jsx-attribute-8.0.0.tgz" + integrity sha512-BcCkm/STipKvbCl6b7QFrMh/vx00vIP63k2eM66MfHJzPr6O2U0jYEViXkHJWqXqQYjdeA9cuCl5KWmlwjDvbA== + +"@svgr/babel-plugin-remove-jsx-empty-expression@8.0.0": + version "8.0.0" + resolved "https://registry.npmjs.org/@svgr/babel-plugin-remove-jsx-empty-expression/-/babel-plugin-remove-jsx-empty-expression-8.0.0.tgz" + integrity sha512-5BcGCBfBxB5+XSDSWnhTThfI9jcO5f0Ai2V24gZpG+wXF14BzwxxdDb4g6trdOux0rhibGs385BeFMSmxtS3uA== + +"@svgr/babel-plugin-replace-jsx-attribute-value@8.0.0": + version "8.0.0" + resolved "https://registry.npmjs.org/@svgr/babel-plugin-replace-jsx-attribute-value/-/babel-plugin-replace-jsx-attribute-value-8.0.0.tgz" + integrity sha512-KVQ+PtIjb1BuYT3ht8M5KbzWBhdAjjUPdlMtpuw/VjT8coTrItWX6Qafl9+ji831JaJcu6PJNKCV0bp01lBNzQ== + +"@svgr/babel-plugin-svg-dynamic-title@8.0.0": + version "8.0.0" + resolved "https://registry.npmjs.org/@svgr/babel-plugin-svg-dynamic-title/-/babel-plugin-svg-dynamic-title-8.0.0.tgz" + integrity sha512-omNiKqwjNmOQJ2v6ge4SErBbkooV2aAWwaPFs2vUY7p7GhVkzRkJ00kILXQvRhA6miHnNpXv7MRnnSjdRjK8og== + +"@svgr/babel-plugin-svg-em-dimensions@8.0.0": + version "8.0.0" + resolved "https://registry.npmjs.org/@svgr/babel-plugin-svg-em-dimensions/-/babel-plugin-svg-em-dimensions-8.0.0.tgz" + integrity sha512-mURHYnu6Iw3UBTbhGwE/vsngtCIbHE43xCRK7kCw4t01xyGqb2Pd+WXekRRoFOBIY29ZoOhUCTEweDMdrjfi9g== + +"@svgr/babel-plugin-transform-react-native-svg@8.1.0": + version "8.1.0" + resolved "https://registry.npmjs.org/@svgr/babel-plugin-transform-react-native-svg/-/babel-plugin-transform-react-native-svg-8.1.0.tgz" + integrity sha512-Tx8T58CHo+7nwJ+EhUwx3LfdNSG9R2OKfaIXXs5soiy5HtgoAEkDay9LIimLOcG8dJQH1wPZp/cnAv6S9CrR1Q== + +"@svgr/babel-plugin-transform-svg-component@8.0.0": + version "8.0.0" + resolved "https://registry.npmjs.org/@svgr/babel-plugin-transform-svg-component/-/babel-plugin-transform-svg-component-8.0.0.tgz" + integrity sha512-DFx8xa3cZXTdb/k3kfPeaixecQLgKh5NVBMwD0AQxOzcZawK4oo1Jh9LbrcACUivsCA7TLG8eeWgrDXjTMhRmw== + +"@svgr/babel-preset@8.1.0": + version "8.1.0" + resolved "https://registry.npmjs.org/@svgr/babel-preset/-/babel-preset-8.1.0.tgz" + integrity sha512-7EYDbHE7MxHpv4sxvnVPngw5fuR6pw79SkcrILHJ/iMpuKySNCl5W1qcwPEpU+LgyRXOaAFgH0KhwD18wwg6ug== + dependencies: + "@svgr/babel-plugin-add-jsx-attribute" "8.0.0" + "@svgr/babel-plugin-remove-jsx-attribute" "8.0.0" + "@svgr/babel-plugin-remove-jsx-empty-expression" "8.0.0" + "@svgr/babel-plugin-replace-jsx-attribute-value" "8.0.0" + "@svgr/babel-plugin-svg-dynamic-title" "8.0.0" + "@svgr/babel-plugin-svg-em-dimensions" "8.0.0" + "@svgr/babel-plugin-transform-react-native-svg" "8.1.0" + "@svgr/babel-plugin-transform-svg-component" "8.0.0" + +"@svgr/core@*", "@svgr/core@8.1.0": + version "8.1.0" + resolved "https://registry.npmjs.org/@svgr/core/-/core-8.1.0.tgz" + integrity sha512-8QqtOQT5ACVlmsvKOJNEaWmRPmcojMOzCz4Hs2BGG/toAp/K38LcsMRyLp349glq5AzJbCEeimEoxaX6v/fLrA== + dependencies: + "@babel/core" "^7.21.3" + "@svgr/babel-preset" "8.1.0" + camelcase "^6.2.0" + cosmiconfig "^8.1.3" + snake-case "^3.0.4" + +"@svgr/hast-util-to-babel-ast@8.0.0": + version "8.0.0" + resolved "https://registry.npmjs.org/@svgr/hast-util-to-babel-ast/-/hast-util-to-babel-ast-8.0.0.tgz" + integrity sha512-EbDKwO9GpfWP4jN9sGdYwPBU0kdomaPIL2Eu4YwmgP+sJeXT+L7bMwJUBnhzfH8Q2qMBqZ4fJwpCyYsAN3mt2Q== + dependencies: + "@babel/types" "^7.21.3" + entities "^4.4.0" + +"@svgr/plugin-jsx@8.1.0": + version "8.1.0" + resolved "https://registry.npmjs.org/@svgr/plugin-jsx/-/plugin-jsx-8.1.0.tgz" + integrity sha512-0xiIyBsLlr8quN+WyuxooNW9RJ0Dpr8uOnH/xrCVO8GLUcwHISwj1AG0k+LFzteTkAA0GbX0kj9q6Dk70PTiPA== + dependencies: + "@babel/core" "^7.21.3" + "@svgr/babel-preset" "8.1.0" + "@svgr/hast-util-to-babel-ast" "8.0.0" + svg-parser "^2.0.4" + +"@svgr/plugin-svgo@8.1.0": + version "8.1.0" + resolved "https://registry.npmjs.org/@svgr/plugin-svgo/-/plugin-svgo-8.1.0.tgz" + integrity sha512-Ywtl837OGO9pTLIN/onoWLmDQ4zFUycI1g76vuKGEz6evR/ZTJlJuz3G/fIkb6OVBJ2g0o6CGJzaEjfmEo3AHA== + dependencies: + cosmiconfig "^8.1.3" + deepmerge "^4.3.1" + svgo "^3.0.2" + +"@svgr/webpack@^8.1.0": + version "8.1.0" + resolved "https://registry.npmjs.org/@svgr/webpack/-/webpack-8.1.0.tgz" + integrity sha512-LnhVjMWyMQV9ZmeEy26maJk+8HTIbd59cH4F2MJ439k9DqejRisfFNGAPvRYlKETuh9LrImlS8aKsBgKjMA8WA== + dependencies: + "@babel/core" "^7.21.3" + "@babel/plugin-transform-react-constant-elements" "^7.21.3" + "@babel/preset-env" "^7.20.2" + "@babel/preset-react" "^7.18.6" + "@babel/preset-typescript" "^7.21.0" + "@svgr/core" "8.1.0" + "@svgr/plugin-jsx" "8.1.0" + "@svgr/plugin-svgo" "8.1.0" + +"@swc/counter@^0.1.3": + version "0.1.3" + resolved "https://registry.npmjs.org/@swc/counter/-/counter-0.1.3.tgz" + integrity sha512-e2BR4lsJkkRlKZ/qCHPw9ZaSxc0MVUd7gtbtaB7aMvHeJVYe8sOB8DBZkP2DtISHGSku9sCK6T6cnY0CtXrOCQ== + +"@swc/helpers@^0.4.2": + version "0.4.36" + resolved "https://registry.npmjs.org/@swc/helpers/-/helpers-0.4.36.tgz" + integrity sha512-5lxnyLEYFskErRPenYItLRSge5DjrJngYKdVjRSrWfza9G6KkgHEXi0vUZiyUeMU5JfXH1YnvXZzSp8ul88o2Q== + dependencies: + legacy-swc-helpers "npm:@swc/helpers@=0.4.14" + tslib "^2.4.0" + +"@swc/helpers@0.5.5": + version "0.5.5" + resolved "https://registry.npmjs.org/@swc/helpers/-/helpers-0.5.5.tgz" + integrity sha512-KGYxvIOXcceOAbEk4bi/dVLEK9z8sZ0uBB3Il5b1rhfClSpcX0yfRO0KmTkqR2cnQDymwLB+25ZyMzICg/cm/A== + dependencies: + "@swc/counter" "^0.1.3" + tslib "^2.4.0" + +"@tiptap/core@^2.0.0", "@tiptap/core@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/core/-/core-2.4.0.tgz" + integrity sha512-YJSahk8pkxpCs8SflCZfTnJpE7IPyUWIylfgXM2DefjRQa5DZ+c6sNY0s/zbxKYFQ6AuHVX40r9pCfcqHChGxQ== + +"@tiptap/extension-blockquote@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-blockquote/-/extension-blockquote-2.4.0.tgz" + integrity sha512-nJJy4KsPgQqWTTDOWzFRdjCfG5+QExfZj44dulgDFNh+E66xhamnbM70PklllXJgEcge7xmT5oKM0gKls5XgFw== + +"@tiptap/extension-bold@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-bold/-/extension-bold-2.4.0.tgz" + integrity sha512-csnW6hMDEHoRfxcPRLSqeJn+j35Lgtt1YRiOwn7DlS66sAECGRuoGfCvQSPij0TCDp4VCR9if5Sf8EymhnQumQ== + +"@tiptap/extension-bubble-menu@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-bubble-menu/-/extension-bubble-menu-2.4.0.tgz" + integrity sha512-s99HmttUtpW3rScWq8rqk4+CGCwergNZbHLTkF6Rp6TSboMwfp+rwL5Q/JkcAG9KGLso1vGyXKbt1xHOvm8zMw== + dependencies: + tippy.js "^6.3.7" + +"@tiptap/extension-bullet-list@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-bullet-list/-/extension-bullet-list-2.4.0.tgz" + integrity sha512-9S5DLIvFRBoExvmZ+/ErpTvs4Wf1yOEs8WXlKYUCcZssK7brTFj99XDwpHFA29HKDwma5q9UHhr2OB2o0JYAdw== + +"@tiptap/extension-code-block-lowlight@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-code-block-lowlight/-/extension-code-block-lowlight-2.4.0.tgz" + integrity sha512-j0SdFq66A97Cn7bQOMqFYBaYsmOltZZ6o4uDZH6fdTvEFbfXTdtTYs2awsNSbW+w/DtivKZCvAX1FRLR3/g/5A== + +"@tiptap/extension-code-block@^2.0.0", "@tiptap/extension-code-block@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-code-block/-/extension-code-block-2.4.0.tgz" + integrity sha512-QWGdv1D56TBGbbJSj2cIiXGJEKguPiAl9ONzJ/Ql1ZksiQsYwx0YHriXX6TOC//T4VIf6NSClHEtwtxWBQ/Csg== + +"@tiptap/extension-code@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-code/-/extension-code-2.4.0.tgz" + integrity sha512-wjhBukuiyJMq4cTcK3RBTzUPV24k5n1eEPlpmzku6ThwwkMdwynnMGMAmSF3fErh3AOyOUPoTTjgMYN2d10SJA== + +"@tiptap/extension-document@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-document/-/extension-document-2.4.0.tgz" + integrity sha512-3jRodQJZDGbXlRPERaloS+IERg/VwzpC1IO6YSJR9jVIsBO6xC29P3cKTQlg1XO7p6ZH/0ksK73VC5BzzTwoHg== + +"@tiptap/extension-dropcursor@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-dropcursor/-/extension-dropcursor-2.4.0.tgz" + integrity sha512-c46HoG2PEEpSZv5rmS5UX/lJ6/kP1iVO0Ax+6JrNfLEIiDULUoi20NqdjolEa38La2VhWvs+o20OviiTOKEE9g== + +"@tiptap/extension-floating-menu@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-floating-menu/-/extension-floating-menu-2.4.0.tgz" + integrity sha512-vLb9v+htbHhXyty0oaXjT3VC8St4xuGSHWUB9GuAJAQ+NajIO6rBPbLUmm9qM0Eh2zico5mpSD1Qtn5FM6xYzg== + dependencies: + tippy.js "^6.3.7" + +"@tiptap/extension-gapcursor@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-gapcursor/-/extension-gapcursor-2.4.0.tgz" + integrity sha512-F4y/0J2lseohkFUw9P2OpKhrJ6dHz69ZScABUvcHxjznJLd6+0Zt7014Lw5PA8/m2d/w0fX8LZQ88pZr4quZPQ== + +"@tiptap/extension-hard-break@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-hard-break/-/extension-hard-break-2.4.0.tgz" + integrity sha512-3+Z6zxevtHza5IsDBZ4lZqvNR3Kvdqwxq/QKCKu9UhJN1DUjsg/l1Jn2NilSQ3NYkBYh2yJjT8CMo9pQIu776g== + +"@tiptap/extension-heading@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-heading/-/extension-heading-2.4.0.tgz" + integrity sha512-fYkyP/VMo7YHO76YVrUjd95Qeo0cubWn/Spavmwm1gLTHH/q7xMtbod2Z/F0wd6QHnc7+HGhO7XAjjKWDjldaw== + +"@tiptap/extension-history@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-history/-/extension-history-2.4.0.tgz" + integrity sha512-gr5qsKAXEVGr1Lyk1598F7drTaEtAxqZiuuSwTCzZzkiwgEQsWMWTWc9F8FlneCEaqe1aIYg6WKWlmYPaFwr0w== + +"@tiptap/extension-horizontal-rule@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-horizontal-rule/-/extension-horizontal-rule-2.4.0.tgz" + integrity sha512-yDgxy+YxagcEsBbdWvbQiXYxsv3noS1VTuGwc9G7ZK9xPmBHJ5y0agOkB7HskwsZvJHoaSqNRsh7oZTkf0VR3g== + +"@tiptap/extension-image@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-image/-/extension-image-2.4.0.tgz" + integrity sha512-NIVhRPMO/ONo8OywEd+8zh0Q6Q7EbFHtBxVsvfOKj9KtZkaXQfUO4MzONTyptkvAchTpj9pIzeaEY5fyU87gFA== + +"@tiptap/extension-italic@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-italic/-/extension-italic-2.4.0.tgz" + integrity sha512-aaW/L9q+KNHHK+X73MPloHeIsT191n3VLd3xm6uUcFDnUNvzYJ/q65/1ZicdtCaOLvTutxdrEvhbkrVREX6a8g== + +"@tiptap/extension-link@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-link/-/extension-link-2.4.0.tgz" + integrity sha512-r3PjT0bjSKAorHAEBPA0icSMOlqALbxVlWU9vAc+Q3ndzt7ht0CTPNewzFF9kjzARABVt1cblXP/2+c0qGzcsg== + dependencies: + linkifyjs "^4.1.0" + +"@tiptap/extension-list-item@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-list-item/-/extension-list-item-2.4.0.tgz" + integrity sha512-reUVUx+2cI2NIAqMZhlJ9uK/+zvRzm1GTmlU2Wvzwc7AwLN4yemj6mBDsmBLEXAKPvitfLh6EkeHaruOGymQtg== + +"@tiptap/extension-ordered-list@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-ordered-list/-/extension-ordered-list-2.4.0.tgz" + integrity sha512-Zo0c9M0aowv+2+jExZiAvhCB83GZMjZsxywmuOrdUbq5EGYKb7q8hDyN3hkrktVHr9UPXdPAYTmLAHztTOHYRA== + +"@tiptap/extension-paragraph@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-paragraph/-/extension-paragraph-2.4.0.tgz" + integrity sha512-+yse0Ow67IRwcACd9K/CzBcxlpr9OFnmf0x9uqpaWt1eHck1sJnti6jrw5DVVkyEBHDh/cnkkV49gvctT/NyCw== + +"@tiptap/extension-placeholder@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-placeholder/-/extension-placeholder-2.4.0.tgz" + integrity sha512-SmWOjgWpmhFt0BPOnL65abCUH0wS5yksUJgtANn5bQoHF4HFSsyl7ETRmgf0ykxdjc7tzOg31FfpWVH4wzKSYg== + +"@tiptap/extension-strike@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-strike/-/extension-strike-2.4.0.tgz" + integrity sha512-pE1uN/fQPOMS3i+zxPYMmPmI3keubnR6ivwM+KdXWOMnBiHl9N4cNpJgq1n2eUUGKLurC2qrQHpnVyGAwBS6Vg== + +"@tiptap/extension-text-align@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-text-align/-/extension-text-align-2.4.0.tgz" + integrity sha512-wpRe2OiLXTK4kTy4RZEPnPjFbK16kYHPAx1552hLXrOdyxbS7Sdbo+w4x7aGLLZZqZdudCFfkdtnqrc7PDVZdA== + +"@tiptap/extension-text@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/extension-text/-/extension-text-2.4.0.tgz" + integrity sha512-LV0bvE+VowE8IgLca7pM8ll7quNH+AgEHRbSrsI3SHKDCYB9gTHMjWaAkgkUVaO1u0IfCrjnCLym/PqFKa+vvg== + +"@tiptap/pm@^2.0.0", "@tiptap/pm@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/pm/-/pm-2.4.0.tgz" + integrity sha512-B1HMEqGS4MzIVXnpgRZDLm30mxDWj51LkBT/if1XD+hj5gm8B9Q0c84bhvODX6KIs+c6z+zsY9VkVu8w9Yfgxg== + dependencies: + prosemirror-changeset "^2.2.1" + prosemirror-collab "^1.3.1" + prosemirror-commands "^1.5.2" + prosemirror-dropcursor "^1.8.1" + prosemirror-gapcursor "^1.3.2" + prosemirror-history "^1.3.2" + prosemirror-inputrules "^1.3.0" + prosemirror-keymap "^1.2.2" + prosemirror-markdown "^1.12.0" + prosemirror-menu "^1.2.4" + prosemirror-model "^1.19.4" + prosemirror-schema-basic "^1.2.2" + prosemirror-schema-list "^1.3.0" + prosemirror-state "^1.4.3" + prosemirror-tables "^1.3.5" + prosemirror-trailing-node "^2.0.7" + prosemirror-transform "^1.8.0" + prosemirror-view "^1.32.7" + +"@tiptap/react@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/react/-/react-2.4.0.tgz" + integrity sha512-baxnIr6Dy+5iGagOEIKFeHzdl1ZRa6Cg+SJ3GDL/BVLpO6KiCM3Mm5ymB726UKP1w7icrBiQD2fGY3Bx8KaiSA== + dependencies: + "@tiptap/extension-bubble-menu" "^2.4.0" + "@tiptap/extension-floating-menu" "^2.4.0" + +"@tiptap/starter-kit@^2.4.0": + version "2.4.0" + resolved "https://registry.npmjs.org/@tiptap/starter-kit/-/starter-kit-2.4.0.tgz" + integrity sha512-DYYzMZdTEnRn9oZhKOeRCcB+TjhNz5icLlvJKoHoOGL9kCbuUyEf8WRR2OSPckI0+KUIPJL3oHRqO4SqSdTjfg== + dependencies: + "@tiptap/core" "^2.4.0" + "@tiptap/extension-blockquote" "^2.4.0" + "@tiptap/extension-bold" "^2.4.0" + "@tiptap/extension-bullet-list" "^2.4.0" + "@tiptap/extension-code" "^2.4.0" + "@tiptap/extension-code-block" "^2.4.0" + "@tiptap/extension-document" "^2.4.0" + "@tiptap/extension-dropcursor" "^2.4.0" + "@tiptap/extension-gapcursor" "^2.4.0" + "@tiptap/extension-hard-break" "^2.4.0" + "@tiptap/extension-heading" "^2.4.0" + "@tiptap/extension-history" "^2.4.0" + "@tiptap/extension-horizontal-rule" "^2.4.0" + "@tiptap/extension-italic" "^2.4.0" + "@tiptap/extension-list-item" "^2.4.0" + "@tiptap/extension-ordered-list" "^2.4.0" + "@tiptap/extension-paragraph" "^2.4.0" + "@tiptap/extension-strike" "^2.4.0" + "@tiptap/extension-text" "^2.4.0" + +"@trysound/sax@0.2.0": + version "0.2.0" + resolved "https://registry.npmjs.org/@trysound/sax/-/sax-0.2.0.tgz" + integrity sha512-L7z9BgrNEcYyUYtF+HaEfiS5ebkh9jXqbszz7pC0hRBPaatV0XjSD3+eHrpqFemQfgwiFF0QPIarnIihIDn7OA== + +"@types/aws-lambda@^8.10.134": + version "8.10.138" + resolved "https://registry.npmjs.org/@types/aws-lambda/-/aws-lambda-8.10.138.tgz" + integrity sha512-71EHMl70TPWIAsFuHd85NHq6S6T2OOjiisPTrH7RgcjzpJpPh4RQJv7PvVvIxc6PIp8CLV7F9B+TdjcAES5vcA== + +"@types/debug@^4.0.0": + version "4.1.12" + resolved "https://registry.npmjs.org/@types/debug/-/debug-4.1.12.tgz" + integrity sha512-vIChWdVG3LG1SMxEvI/AK+FWJthlrqlTu7fbrlywTkkaONwk/UAGaULXRlf8vkzFBLVm0zkMdCquhL5aOjhXPQ== + dependencies: + "@types/ms" "*" + +"@types/geojson@*": + version "7946.0.13" + resolved "https://registry.npmjs.org/@types/geojson/-/geojson-7946.0.13.tgz" + integrity sha512-bmrNrgKMOhM3WsafmbGmC+6dsF2Z308vLFsQ3a/bT8X8Sv5clVYpPars/UPq+sAaJP+5OoLAYgwbkS5QEJdLUQ== + +"@types/hast@^3.0.0": + version "3.0.3" + resolved "https://registry.npmjs.org/@types/hast/-/hast-3.0.3.tgz" + integrity sha512-2fYGlaDy/qyLlhidX42wAH0KBi2TCjKMH8CHmBXgRlJ3Y+OXTiqsPQ6IWarZKwF1JoUcAJdPogv1d4b0COTpmQ== + dependencies: + "@types/unist" "*" + +"@types/json5@^0.0.29": + version "0.0.29" + resolved "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz" + integrity sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ== + +"@types/lodash-es@^4.17.6": + version "4.17.12" + resolved "https://registry.npmjs.org/@types/lodash-es/-/lodash-es-4.17.12.tgz" + integrity sha512-0NgftHUcV4v34VhXm8QBSftKVXtbkBG3ViCjs6+eJ5a6y6Mi/jiFGPc1sC7QK+9BFhWrURE3EOggmWaSxL9OzQ== + dependencies: + "@types/lodash" "*" + +"@types/lodash@*": + version "4.17.1" + resolved "https://registry.npmjs.org/@types/lodash/-/lodash-4.17.1.tgz" + integrity sha512-X+2qazGS3jxLAIz5JDXDzglAF3KpijdhFxlf/V1+hEsOUc+HnWi81L/uv/EvGuV90WY+7mPGFCUDGfQC3Gj95Q== + +"@types/mapbox-gl@>=1.0.0": + version "3.1.0" + resolved "https://registry.npmjs.org/@types/mapbox-gl/-/mapbox-gl-3.1.0.tgz" + integrity sha512-hI6cQDjw1bkJw7MC/eHMqq5TWUamLwsujnUUeiIX2KDRjxRNSYMjnHz07+LATz9I9XIsKumOtUz4gRYnZOJ/FA== + dependencies: + "@types/geojson" "*" + +"@types/mdast@^4.0.0": + version "4.0.3" + resolved "https://registry.npmjs.org/@types/mdast/-/mdast-4.0.3.tgz" + integrity sha512-LsjtqsyF+d2/yFOYaN22dHZI1Cpwkrj+g06G8+qtUKlhovPW89YhqSnfKtMbkgmEtYpH2gydRNULd6y8mciAFg== + dependencies: + "@types/unist" "*" + +"@types/ms@*": + version "0.7.34" + resolved "https://registry.npmjs.org/@types/ms/-/ms-0.7.34.tgz" + integrity sha512-nG96G3Wp6acyAgJqGasjODb+acrI7KltPiRxzHPXnP3NgI28bpQDRv53olbqGXbfcgF5aiiHmO3xpwEpS5Ld9g== + +"@types/node@*", "@types/node@>=12.12.47", "@types/node@>=13.7.0": + version "20.12.12" + resolved "https://registry.npmjs.org/@types/node/-/node-20.12.12.tgz" + integrity sha512-eWLDGF/FOSPtAvEqeRAQ4C8LSA7M1I7i0ky1I8U7kD1J5ITyW3AsRhQrKVoWf5pFKZ2kILsEGJhsI9r93PYnOw== + dependencies: + undici-types "~5.26.4" + +"@types/parse-json@^4.0.0": + version "4.0.2" + resolved "https://registry.npmjs.org/@types/parse-json/-/parse-json-4.0.2.tgz" + integrity sha512-dISoDXWWQwUquiKsyZ4Ng+HX2KsPL7LyHKHQwgGFEA3IaKac4Obd+h2a/a6waisAoepJlBcx9paWqjA8/HVjCw== + +"@types/phoenix@^1.5.4": + version "1.6.4" + resolved "https://registry.npmjs.org/@types/phoenix/-/phoenix-1.6.4.tgz" + integrity sha512-B34A7uot1Cv0XtaHRYDATltAdKx0BvVKNgYNqE4WjtPUa4VQJM7kxeXcVKaH+KS+kCmZ+6w+QaUdcljiheiBJA== + +"@types/prop-types@*", "@types/prop-types@^15.7.11": + version "15.7.11" + resolved "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.11.tgz" + integrity sha512-ga8y9v9uyeiLdpKddhxYQkxNDrfvuPrlFb0N1qnZZByvcElJaXthF1UhvCh9TLWJBEHeNtdnbysW7Y6Uq8CVng== + +"@types/react-transition-group@^4.4.10": + version "4.4.10" + resolved "https://registry.npmjs.org/@types/react-transition-group/-/react-transition-group-4.4.10.tgz" + integrity sha512-hT/+s0VQs2ojCX823m60m5f0sL5idt9SO6Tj6Dg+rdphGPIeJbJ6CxvBYkgkGKrYeDjvIpKTR38UzmtHJOGW3Q== + dependencies: + "@types/react" "*" + +"@types/react@*", "@types/react@^17.0.0 || ^18.0.0", "@types/react@^18.2.55", "@types/react@^18.3.3", "@types/react@>=0.0.0 <=99", "@types/react@>=18": + version "18.3.3" + resolved "https://registry.npmjs.org/@types/react/-/react-18.3.3.tgz" + integrity sha512-hti/R0pS0q1/xx+TsI73XIqk26eBsISZ2R0wUijXIngRK9R/e7Xw/cXVxQK7R5JjW+SV4zGcn5hXjudkN/pLIw== + dependencies: + "@types/prop-types" "*" + csstype "^3.0.2" + +"@types/unist@*", "@types/unist@^3.0.0": + version "3.0.2" + resolved "https://registry.npmjs.org/@types/unist/-/unist-3.0.2.tgz" + integrity sha512-dqId9J8K/vGi5Zr7oo212BGii5m3q5Hxlkwy3WpYuKPklmBEvsbMYYyLxAQpSffdLl/gdW0XUpKWFvYmyoWCoQ== + +"@types/uuid@^9.0.0": + version "9.0.8" + resolved "https://registry.npmjs.org/@types/uuid/-/uuid-9.0.8.tgz" + integrity sha512-jg+97EGIcY9AGHJJRaaPVgetKDsrTgbRjQ5Msgjh/DQKEFl0DtyRr/VCOyD1T2R1MNeWPK/u7JoGhlDZnKBAfA== + +"@types/ws@^8.5.10": + version "8.5.10" + resolved "https://registry.npmjs.org/@types/ws/-/ws-8.5.10.tgz" + integrity sha512-vmQSUcfalpIq0R9q7uTo2lXs6eGIpt9wtnLdMv9LVpIjCA/+ufZRozlVoVelIYixx1ugCBKDhn89vnsEGOCx9A== + dependencies: + "@types/node" "*" + +"@typescript-eslint/scope-manager@7.10.0": + version "7.10.0" + resolved "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-7.10.0.tgz" + integrity sha512-7L01/K8W/VGl7noe2mgH0K7BE29Sq6KAbVmxurj8GGaPDZXPr8EEQ2seOeAS+mEV9DnzxBQB6ax6qQQ5C6P4xg== + dependencies: + "@typescript-eslint/types" "7.10.0" + "@typescript-eslint/visitor-keys" "7.10.0" + +"@typescript-eslint/types@7.10.0": + version "7.10.0" + resolved "https://registry.npmjs.org/@typescript-eslint/types/-/types-7.10.0.tgz" + integrity sha512-7fNj+Ya35aNyhuqrA1E/VayQX9Elwr8NKZ4WueClR3KwJ7Xx9jcCdOrLW04h51de/+gNbyFMs+IDxh5xIwfbNg== + +"@typescript-eslint/typescript-estree@7.10.0": + version "7.10.0" + resolved "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-7.10.0.tgz" + integrity sha512-LXFnQJjL9XIcxeVfqmNj60YhatpRLt6UhdlFwAkjNc6jSUlK8zQOl1oktAP8PlWFzPQC1jny/8Bai3/HPuvN5g== + dependencies: + "@typescript-eslint/types" "7.10.0" + "@typescript-eslint/visitor-keys" "7.10.0" + debug "^4.3.4" + globby "^11.1.0" + is-glob "^4.0.3" + minimatch "^9.0.4" + semver "^7.6.0" + ts-api-utils "^1.3.0" + +"@typescript-eslint/utils@^6.13.0 || ^7.0.0": + version "7.10.0" + resolved "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-7.10.0.tgz" + integrity sha512-olzif1Fuo8R8m/qKkzJqT7qwy16CzPRWBvERS0uvyc+DHd8AKbO4Jb7kpAvVzMmZm8TrHnI7hvjN4I05zow+tg== + dependencies: + "@eslint-community/eslint-utils" "^4.4.0" + "@typescript-eslint/scope-manager" "7.10.0" + "@typescript-eslint/types" "7.10.0" + "@typescript-eslint/typescript-estree" "7.10.0" + +"@typescript-eslint/visitor-keys@7.10.0": + version "7.10.0" + resolved "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-7.10.0.tgz" + integrity sha512-9ntIVgsi6gg6FIq9xjEO4VQJvwOqA3jaBFQJ/6TK5AvEup2+cECI6Fh7QiBxmfMHXU0V0J4RyPeOU1VDNzl9cg== + dependencies: + "@typescript-eslint/types" "7.10.0" + eslint-visitor-keys "^3.4.3" + +"@ungap/structured-clone@^1.0.0", "@ungap/structured-clone@^1.2.0": + version "1.2.0" + resolved "https://registry.npmjs.org/@ungap/structured-clone/-/structured-clone-1.2.0.tgz" + integrity sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ== + +"@yr/monotone-cubic-spline@^1.0.3": + version "1.0.3" + resolved "https://registry.npmjs.org/@yr/monotone-cubic-spline/-/monotone-cubic-spline-1.0.3.tgz" + integrity sha512-FQXkOta0XBSUPHndIKON2Y9JeQz5ZeMqLYZVVK93FliNBFm7LNMIZmY6FrMEB9XPcDbE2bekMbZD6kzDkxwYjA== + +abs-svg-path@^0.1.1: + version "0.1.1" + resolved "https://registry.npmjs.org/abs-svg-path/-/abs-svg-path-0.1.1.tgz" + integrity sha512-d8XPSGjfyzlXC3Xx891DJRyZfqk5JU0BJrDQcsWomFIV1/BIzPW5HDH5iDdWpqWaav0YVIEzT1RHTwWr0FFshA== + +acorn-jsx@^5.3.2: + version "5.3.2" + resolved "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz" + integrity sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ== + +"acorn@^6.0.0 || ^7.0.0 || ^8.0.0", acorn@^8.9.0: + version "8.11.2" + resolved "https://registry.npmjs.org/acorn/-/acorn-8.11.2.tgz" + integrity sha512-nc0Axzp/0FILLEVsm4fNwLCwMttvhEI263QtVPQcbpfZZ3ts0hLsZGOpE6czNlid7CJ9MlyH8reXkpsf3YUY4w== + +ajv@^6.12.4: + version "6.12.6" + resolved "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz" + integrity sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g== + dependencies: + fast-deep-equal "^3.1.1" + fast-json-stable-stringify "^2.0.0" + json-schema-traverse "^0.4.1" + uri-js "^4.2.2" + +ansi-regex@^5.0.1: + version "5.0.1" + resolved "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz" + integrity sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ== + +ansi-styles@^3.2.1: + version "3.2.1" + resolved "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz" + integrity sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA== + dependencies: + color-convert "^1.9.0" + +ansi-styles@^4.0.0: + version "4.3.0" + resolved "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz" + integrity sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg== + dependencies: + color-convert "^2.0.1" + +ansi-styles@^4.1.0: + version "4.3.0" + resolved "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz" + integrity sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg== + dependencies: + color-convert "^2.0.1" + +apexcharts@^3.41.0, apexcharts@^3.49.1: + version "3.49.1" + resolved "https://registry.npmjs.org/apexcharts/-/apexcharts-3.49.1.tgz" + integrity sha512-MqGtlq/KQuO8j0BBsUJYlRG8VBctKwYdwuBtajHgHTmSgUU3Oai+8oYN/rKCXwXzrUlYA+GiMgotAIbXY2BCGw== + dependencies: + "@yr/monotone-cubic-spline" "^1.0.3" + svg.draggable.js "^2.2.2" + svg.easing.js "^2.0.0" + svg.filter.js "^2.0.2" + svg.pathmorphing.js "^0.1.3" + svg.resize.js "^1.4.3" + svg.select.js "^3.0.1" + +argparse@^2.0.1: + version "2.0.1" + resolved "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz" + integrity sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q== + +aria-query@^5.3.0: + version "5.3.0" + resolved "https://registry.npmjs.org/aria-query/-/aria-query-5.3.0.tgz" + integrity sha512-b0P0sZPKtyu8HkeRAfCq0IfURZK+SuwMjY1UXGBU27wpAiTwQAIlq56IbIO+ytk/JjS1fMR14ee5WBBfKi5J6A== + dependencies: + dequal "^2.0.3" + +arr-union@^3.1.0: + version "3.1.0" + resolved "https://registry.npmjs.org/arr-union/-/arr-union-3.1.0.tgz" + integrity sha512-sKpyeERZ02v1FeCZT8lrfJq5u6goHCtpTAzPwJYe7c8SPFOboNjNg1vz2L4VTn9T4PQxEx13TbXLmYUcS6Ug7Q== + +array-buffer-byte-length@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/array-buffer-byte-length/-/array-buffer-byte-length-1.0.1.tgz" + integrity sha512-ahC5W1xgou+KTXix4sAO8Ki12Q+jf4i0+tmk3sC+zgcynshkHxzpXdImBehiUYKKKDwvfFiJl1tZt6ewscS1Mg== + dependencies: + call-bind "^1.0.5" + is-array-buffer "^3.0.4" + +array-includes@^3.1.6, array-includes@^3.1.7, array-includes@^3.1.8: + version "3.1.8" + resolved "https://registry.npmjs.org/array-includes/-/array-includes-3.1.8.tgz" + integrity sha512-itaWrbYbqpGXkGhZPGUulwnhVf5Hpy1xiCFsGqyIGglbBxmG5vSjxQen3/WGOjPpNEv1RtBLKxbmVXm8HpJStQ== + dependencies: + call-bind "^1.0.7" + define-properties "^1.2.1" + es-abstract "^1.23.2" + es-object-atoms "^1.0.0" + get-intrinsic "^1.2.4" + is-string "^1.0.7" + +array-union@^2.1.0: + version "2.1.0" + resolved "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz" + integrity sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw== + +array.prototype.findlast@^1.2.5: + version "1.2.5" + resolved "https://registry.npmjs.org/array.prototype.findlast/-/array.prototype.findlast-1.2.5.tgz" + integrity sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ== + dependencies: + call-bind "^1.0.7" + define-properties "^1.2.1" + es-abstract "^1.23.2" + es-errors "^1.3.0" + es-object-atoms "^1.0.0" + es-shim-unscopables "^1.0.2" + +array.prototype.findlastindex@^1.2.3: + version "1.2.3" + resolved "https://registry.npmjs.org/array.prototype.findlastindex/-/array.prototype.findlastindex-1.2.3.tgz" + integrity sha512-LzLoiOMAxvy+Gd3BAq3B7VeIgPdo+Q8hthvKtXybMvRV0jrXfJM/t8mw7nNlpEcVlVUnCnM2KSX4XU5HmpodOA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + es-shim-unscopables "^1.0.0" + get-intrinsic "^1.2.1" + +array.prototype.flat@^1.3.1, array.prototype.flat@^1.3.2: + version "1.3.2" + resolved "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.3.2.tgz" + integrity sha512-djYB+Zx2vLewY8RWlNCUdHjDXs2XOgm602S9E7P/UpHgfeHL00cRiIF+IN/G/aUJ7kGPb6yO/ErDI5V2s8iycA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + es-shim-unscopables "^1.0.0" + +array.prototype.flatmap@^1.3.2: + version "1.3.2" + resolved "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.2.tgz" + integrity sha512-Ewyx0c9PmpcsByhSW4r+9zDU7sGjFc86qf/kKtuSCRdhfbk0SNLLkaT5qvcHnRGgc5NP/ly/y+qkXkqONX54CQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + es-shim-unscopables "^1.0.0" + +array.prototype.toreversed@^1.1.2: + version "1.1.2" + resolved "https://registry.npmjs.org/array.prototype.toreversed/-/array.prototype.toreversed-1.1.2.tgz" + integrity sha512-wwDCoT4Ck4Cz7sLtgUmzR5UV3YF5mFHUlbChCzZBQZ+0m2cl/DH3tKgvphv1nKgFsJ48oCSg6p91q2Vm0I/ZMA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + es-shim-unscopables "^1.0.0" + +array.prototype.tosorted@^1.1.3: + version "1.1.3" + resolved "https://registry.npmjs.org/array.prototype.tosorted/-/array.prototype.tosorted-1.1.3.tgz" + integrity sha512-/DdH4TiTmOKzyQbp/eadcCVexiCb36xJg7HshYOYJnNZFDj33GEv0P7GxsynpShhq4OLYJzbGcBDkLsDt7MnNg== + dependencies: + call-bind "^1.0.5" + define-properties "^1.2.1" + es-abstract "^1.22.3" + es-errors "^1.1.0" + es-shim-unscopables "^1.0.2" + +arraybuffer.prototype.slice@^1.0.3: + version "1.0.3" + resolved "https://registry.npmjs.org/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.3.tgz" + integrity sha512-bMxMKAjg13EBSVscxTaYA4mRc5t1UAXa2kXiGTNfZ079HIWXEkKmkgFrh/nJqamaLSrXO5H4WFFkPEaLJWbs3A== + dependencies: + array-buffer-byte-length "^1.0.1" + call-bind "^1.0.5" + define-properties "^1.2.1" + es-abstract "^1.22.3" + es-errors "^1.2.1" + get-intrinsic "^1.2.3" + is-array-buffer "^3.0.4" + is-shared-array-buffer "^1.0.2" + +assign-symbols@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/assign-symbols/-/assign-symbols-1.0.0.tgz" + integrity sha512-Q+JC7Whu8HhmTdBph/Tq59IoRtoy6KAm5zzPv00WdujX82lbAL8K7WVjne7vdCsAmbF4AYaDOPyO3k0kl8qIrw== + +ast-types-flow@^0.0.8: + version "0.0.8" + resolved "https://registry.npmjs.org/ast-types-flow/-/ast-types-flow-0.0.8.tgz" + integrity sha512-OH/2E5Fg20h2aPrbe+QL8JZQFko0YZaF+j4mnQ7BGhfavO7OpSLa8a0y9sBwomHdSbkhTS8TQNayBfnW5DwbvQ== + +asynckit@^0.4.0: + version "0.4.0" + resolved "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz" + integrity sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q== + +attr-accept@^2.2.2: + version "2.2.2" + resolved "https://registry.npmjs.org/attr-accept/-/attr-accept-2.2.2.tgz" + integrity sha512-7prDjvt9HmqiZ0cl5CRjtS84sEyhsHP2coDkaZKRKVfCDo9s7iw7ChVmar78Gu9pC4SoR/28wFu/G5JJhTnqEg== + +autosuggest-highlight@^3.3.4: + version "3.3.4" + resolved "https://registry.npmjs.org/autosuggest-highlight/-/autosuggest-highlight-3.3.4.tgz" + integrity sha512-j6RETBD2xYnrVcoV1S5R4t3WxOlWZKyDQjkwnggDPSjF5L4jV98ZltBpvPvbkM1HtoSe5o+bNrTHyjPbieGeYA== + dependencies: + remove-accents "^0.4.2" + +available-typed-arrays@^1.0.7: + version "1.0.7" + resolved "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.7.tgz" + integrity sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ== + dependencies: + possible-typed-array-names "^1.0.0" + +aws-amplify@^6.3.6: + version "6.3.6" + resolved "https://registry.npmjs.org/aws-amplify/-/aws-amplify-6.3.6.tgz" + integrity sha512-haG8Z2PErWS1KoSZ5z+vuQ6Au/cXn0eAMSruur+Ku+vFWXrKUEq0uI8SvAw5rJ6B2BDJEdMMzDnOb+hDuY5lew== + dependencies: + "@aws-amplify/analytics" "7.0.35" + "@aws-amplify/api" "6.0.37" + "@aws-amplify/auth" "6.3.5" + "@aws-amplify/core" "6.3.2" + "@aws-amplify/datastore" "5.0.37" + "@aws-amplify/notifications" "2.0.35" + "@aws-amplify/storage" "6.4.6" + tslib "^2.5.0" + +axe-core@=4.7.0: + version "4.7.0" + resolved "https://registry.npmjs.org/axe-core/-/axe-core-4.7.0.tgz" + integrity sha512-M0JtH+hlOL5pLQwHOLNYZaXuhqmvS8oExsqB1SBYgA4Dk7u/xx+YdGHXaK5pyUfed5mYXdlYiphWq3G8cRi5JQ== + +axios@^1.7.2: + version "1.7.2" + resolved "https://registry.npmjs.org/axios/-/axios-1.7.2.tgz" + integrity sha512-2A8QhOMrbomlDuiLeK9XibIBzuHeRcqqNOHp0Cyp5EoJ1IFDh+XZH3A6BkXtv0K4gFGCI0Y4BM7B1wOEi0Rmgw== + dependencies: + follow-redirects "^1.15.6" + form-data "^4.0.0" + proxy-from-env "^1.1.0" + +axobject-query@^3.2.1: + version "3.2.1" + resolved "https://registry.npmjs.org/axobject-query/-/axobject-query-3.2.1.tgz" + integrity sha512-jsyHu61e6N4Vbz/v18DHwWYKK0bSWLqn47eeDSKPB7m8tqMHF9YJ+mhIk2lVteyZrY8tnSj/jHOv4YiTCuCJgg== + dependencies: + dequal "^2.0.3" + +babel-plugin-macros@^3.1.0: + version "3.1.0" + resolved "https://registry.npmjs.org/babel-plugin-macros/-/babel-plugin-macros-3.1.0.tgz" + integrity sha512-Cg7TFGpIr01vOQNODXOOaGz2NpCU5gl8x1qJFbb6hbZxR7XrcE2vtbAsTAbJ7/xwJtUuJEw8K8Zr/AE0LHlesg== + dependencies: + "@babel/runtime" "^7.12.5" + cosmiconfig "^7.0.0" + resolve "^1.19.0" + +babel-plugin-polyfill-corejs2@^0.4.6: + version "0.4.6" + resolved "https://registry.npmjs.org/babel-plugin-polyfill-corejs2/-/babel-plugin-polyfill-corejs2-0.4.6.tgz" + integrity sha512-jhHiWVZIlnPbEUKSSNb9YoWcQGdlTLq7z1GHL4AjFxaoOUMuuEVJ+Y4pAaQUGOGk93YsVCKPbqbfw3m0SM6H8Q== + dependencies: + "@babel/compat-data" "^7.22.6" + "@babel/helper-define-polyfill-provider" "^0.4.3" + semver "^6.3.1" + +babel-plugin-polyfill-corejs3@^0.8.5: + version "0.8.6" + resolved "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.8.6.tgz" + integrity sha512-leDIc4l4tUgU7str5BWLS2h8q2N4Nf6lGZP6UrNDxdtfF2g69eJ5L0H7S8A5Ln/arfFAfHor5InAdZuIOwZdgQ== + dependencies: + "@babel/helper-define-polyfill-provider" "^0.4.3" + core-js-compat "^3.33.1" + +babel-plugin-polyfill-regenerator@^0.5.3: + version "0.5.3" + resolved "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.5.3.tgz" + integrity sha512-8sHeDOmXC8csczMrYEOf0UTNa4yE2SxV5JGeT/LP1n0OYVDUUFPxG9vdk2AlDlIit4t+Kf0xCtpgXPBwnn/9pw== + dependencies: + "@babel/helper-define-polyfill-provider" "^0.4.3" + +bail@^2.0.0: + version "2.0.2" + resolved "https://registry.npmjs.org/bail/-/bail-2.0.2.tgz" + integrity sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw== + +balanced-match@^1.0.0: + version "1.0.2" + resolved "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz" + integrity sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw== + +base64-js@^1.0.2, base64-js@^1.1.2, base64-js@^1.3.0: + version "1.5.1" + resolved "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz" + integrity sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA== + +bidi-js@^1.0.2: + version "1.0.3" + resolved "https://registry.npmjs.org/bidi-js/-/bidi-js-1.0.3.tgz" + integrity sha512-RKshQI1R3YQ+n9YJz2QQ147P66ELpa1FQEg20Dk8oW9t2KgLbpDLLp9aGZ7y8WHSshDknG0bknqGw5/tyCs5tw== + dependencies: + require-from-string "^2.0.2" + +boolbase@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/boolbase/-/boolbase-1.0.0.tgz" + integrity sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww== + +bowser@^2.11.0: + version "2.11.0" + resolved "https://registry.npmjs.org/bowser/-/bowser-2.11.0.tgz" + integrity sha512-AlcaJBi/pqqJBIQ8U9Mcpc9i8Aqxn88Skv5d+xBX006BY5u8N3mGLHa5Lgppa7L/HfwgwLgZ6NYs+Ag6uUmJRA== + +brace-expansion@^1.1.7: + version "1.1.11" + resolved "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz" + integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA== + dependencies: + balanced-match "^1.0.0" + concat-map "0.0.1" + +brace-expansion@^2.0.1: + version "2.0.1" + resolved "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz" + integrity sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA== + dependencies: + balanced-match "^1.0.0" + +braces@^3.0.2: + version "3.0.3" + resolved "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz" + integrity sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA== + dependencies: + fill-range "^7.1.1" + +brotli@^1.3.2: + version "1.3.3" + resolved "https://registry.npmjs.org/brotli/-/brotli-1.3.3.tgz" + integrity sha512-oTKjJdShmDuGW94SyyaoQvAjf30dZaHnjJ8uAF+u2/vGJkJbJPJAT1gDiOJP5v1Zb6f9KEyW/1HpuaWIXtGHPg== + dependencies: + base64-js "^1.1.2" + +browserify-zlib@^0.2.0: + version "0.2.0" + resolved "https://registry.npmjs.org/browserify-zlib/-/browserify-zlib-0.2.0.tgz" + integrity sha512-Z942RysHXmJrhqk88FmKBVq/v5tqmSkDz7p54G/MGyjMnCFFnC79XWNbg+Vta8W6Wb2qtSZTSxIGkJrRpCFEiA== + dependencies: + pako "~1.0.5" + +browserslist@^4.21.9, browserslist@^4.22.1, "browserslist@>= 4.21.0": + version "4.22.1" + resolved "https://registry.npmjs.org/browserslist/-/browserslist-4.22.1.tgz" + integrity sha512-FEVc202+2iuClEhZhrWy6ZiAcRLvNMyYcxZ8raemul1DYVOVdFsbqckWLdsixQZCpJlwe77Z3UTalE7jsjnKfQ== + dependencies: + caniuse-lite "^1.0.30001541" + electron-to-chromium "^1.4.535" + node-releases "^2.0.13" + update-browserslist-db "^1.0.13" + +buffer@4.9.2: + version "4.9.2" + resolved "https://registry.npmjs.org/buffer/-/buffer-4.9.2.tgz" + integrity sha512-xq+q3SRMOxGivLhBNaUdC64hDTQwejJ+H0T/NB1XMtTVEwNTrfFF3gAxiyW0Bu/xWEGhjVKgUcMhCrUy2+uCWg== + dependencies: + base64-js "^1.0.2" + ieee754 "^1.1.4" + isarray "^1.0.0" + +busboy@1.6.0: + version "1.6.0" + resolved "https://registry.npmjs.org/busboy/-/busboy-1.6.0.tgz" + integrity sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA== + dependencies: + streamsearch "^1.1.0" + +bytewise-core@^1.2.2: + version "1.2.3" + resolved "https://registry.npmjs.org/bytewise-core/-/bytewise-core-1.2.3.tgz" + integrity sha512-nZD//kc78OOxeYtRlVk8/zXqTB4gf/nlguL1ggWA8FuchMyOxcyHR4QPQZMUmA7czC+YnaBrPUCubqAWe50DaA== + dependencies: + typewise-core "^1.2" + +bytewise@^1.1.0: + version "1.1.0" + resolved "https://registry.npmjs.org/bytewise/-/bytewise-1.1.0.tgz" + integrity sha512-rHuuseJ9iQ0na6UDhnrRVDh8YnWVlU6xM3VH6q/+yHDeUH2zIhUzP+2/h3LIrhLDBtTqzWpE3p3tP/boefskKQ== + dependencies: + bytewise-core "^1.2.2" + typewise "^1.0.3" + +call-bind@^1.0.2, call-bind@^1.0.5, call-bind@^1.0.6, call-bind@^1.0.7: + version "1.0.7" + resolved "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz" + integrity sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w== + dependencies: + es-define-property "^1.0.0" + es-errors "^1.3.0" + function-bind "^1.1.2" + get-intrinsic "^1.2.4" + set-function-length "^1.2.1" + +callsites@^3.0.0: + version "3.1.0" + resolved "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz" + integrity sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ== + +camelcase@^6.2.0: + version "6.3.0" + resolved "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz" + integrity sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA== + +can-use-dom@^0.1.0: + version "0.1.0" + resolved "https://registry.npmjs.org/can-use-dom/-/can-use-dom-0.1.0.tgz" + integrity sha512-ceOhN1DL7Y4O6M0j9ICgmTYziV89WMd96SvSl0REd8PMgrY0B/WBOPoed5S1KUmJqXgUXh8gzSe6E3ae27upsQ== + +caniuse-lite@^1.0.30001541, caniuse-lite@^1.0.30001579: + version "1.0.30001634" + resolved "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001634.tgz" + integrity sha512-fbBYXQ9q3+yp1q1gBk86tOFs4pyn/yxFm5ZNP18OXJDfA3txImOY9PhfxVggZ4vRHDqoU8NrKU81eN0OtzOgRA== + +ccount@^2.0.0: + version "2.0.1" + resolved "https://registry.npmjs.org/ccount/-/ccount-2.0.1.tgz" + integrity sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg== + +chalk@^2.4.2: + version "2.4.2" + resolved "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz" + integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ== + dependencies: + ansi-styles "^3.2.1" + escape-string-regexp "^1.0.5" + supports-color "^5.3.0" + +chalk@^4.0.0: + version "4.1.2" + resolved "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz" + integrity sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA== + dependencies: + ansi-styles "^4.1.0" + supports-color "^7.1.0" + +character-entities@^2.0.0: + version "2.0.2" + resolved "https://registry.npmjs.org/character-entities/-/character-entities-2.0.2.tgz" + integrity sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ== + +cheap-ruler@^3.0.1: + version "3.0.2" + resolved "https://registry.npmjs.org/cheap-ruler/-/cheap-ruler-3.0.2.tgz" + integrity sha512-02T332h1/HTN6cDSufLP8x4JzDs2+VC+8qZ/N0kWIVPyc2xUkWwWh3B2fJxR7raXkL4Mq7k554mfuM9ofv/vGg== + +classnames@^2.5.1: + version "2.5.1" + resolved "https://registry.npmjs.org/classnames/-/classnames-2.5.1.tgz" + integrity sha512-saHYOzhIQs6wy2sVxTM6bUDsQO4F50V9RQ22qBpEdCW+I+/Wmke2HOl6lS6dTpdxVhb88/I6+Hs+438c3lfUow== + +client-only@^0.0.1, client-only@0.0.1: + version "0.0.1" + resolved "https://registry.npmjs.org/client-only/-/client-only-0.0.1.tgz" + integrity sha512-IV3Ou0jSMzZrd3pZ48nLkT9DA7Ag1pnPzaiQhpW7c3RbcqqzvzzVu+L8gfqMp/8IM2MQtSiqaCxrrcfu8I8rMA== + +cliui@^8.0.1: + version "8.0.1" + resolved "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz" + integrity sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ== + dependencies: + string-width "^4.2.0" + strip-ansi "^6.0.1" + wrap-ansi "^7.0.0" + +clone@^2.1.2: + version "2.1.2" + resolved "https://registry.npmjs.org/clone/-/clone-2.1.2.tgz" + integrity sha512-3Pe/CF1Nn94hyhIYpjtiLhdCoEoz0DqQ+988E9gmeEdQZlojxnOb74wctFyuwWQHzqyf9X7C7MG8juUpqBJT8w== + +clsx@^2.1.0, clsx@^2.1.1: + version "2.1.1" + resolved "https://registry.npmjs.org/clsx/-/clsx-2.1.1.tgz" + integrity sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA== + +color-convert@^1.9.0: + version "1.9.3" + resolved "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz" + integrity sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg== + dependencies: + color-name "1.1.3" + +color-convert@^2.0.1: + version "2.0.1" + resolved "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz" + integrity sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ== + dependencies: + color-name "~1.1.4" + +color-name@^1.0.0, color-name@1.1.3: + version "1.1.3" + resolved "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz" + integrity sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw== + +color-name@~1.1.4: + version "1.1.4" + resolved "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz" + integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA== + +color-string@^1.9.1: + version "1.9.1" + resolved "https://registry.npmjs.org/color-string/-/color-string-1.9.1.tgz" + integrity sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg== + dependencies: + color-name "^1.0.0" + simple-swizzle "^0.2.2" + +combined-stream@^1.0.8: + version "1.0.8" + resolved "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz" + integrity sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg== + dependencies: + delayed-stream "~1.0.0" + +comma-separated-tokens@^2.0.0: + version "2.0.3" + resolved "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-2.0.3.tgz" + integrity sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg== + +commander@^7.2.0: + version "7.2.0" + resolved "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz" + integrity sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw== + +concat-map@0.0.1: + version "0.0.1" + resolved "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz" + integrity sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg== + +confusing-browser-globals@^1.0.10: + version "1.0.11" + resolved "https://registry.npmjs.org/confusing-browser-globals/-/confusing-browser-globals-1.0.11.tgz" + integrity sha512-JsPKdmh8ZkmnHxDk55FZ1TqVLvEQTvoByJZRN9jzI0UjxK/QgAmsphz7PGtqgPieQZ/CQcHWXCR7ATDNhGe+YA== + +convert-source-map@^1.5.0: + version "1.9.0" + resolved "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz" + integrity sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A== + +convert-source-map@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz" + integrity sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg== + +core-js-compat@^3.31.0, core-js-compat@^3.33.1: + version "3.33.3" + resolved "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.33.3.tgz" + integrity sha512-cNzGqFsh3Ot+529GIXacjTJ7kegdt5fPXxCBVS1G0iaZpuo/tBz399ymceLJveQhFFZ8qThHiP3fzuoQjKN2ow== + dependencies: + browserslist "^4.22.1" + +cosmiconfig@^7.0.0: + version "7.1.0" + resolved "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.1.0.tgz" + integrity sha512-AdmX6xUzdNASswsFtmwSt7Vj8po9IuqXm0UXz7QKPuEUmPB4XyjGfaAr2PSuELMwkRMVH1EpIkX5bTZGRB3eCA== + dependencies: + "@types/parse-json" "^4.0.0" + import-fresh "^3.2.1" + parse-json "^5.0.0" + path-type "^4.0.0" + yaml "^1.10.0" + +cosmiconfig@^8.1.3: + version "8.3.6" + resolved "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-8.3.6.tgz" + integrity sha512-kcZ6+W5QzcJ3P1Mt+83OUv/oHFqZHIx8DuxG6eZ5RGMERoLqp4BuGjhHLYGK+Kf5XVkQvqBSmAy/nGWN3qDgEA== + dependencies: + import-fresh "^3.3.0" + js-yaml "^4.1.0" + parse-json "^5.2.0" + path-type "^4.0.0" + +country-flag-icons@^1.5.11: + version "1.5.11" + resolved "https://registry.npmjs.org/country-flag-icons/-/country-flag-icons-1.5.11.tgz" + integrity sha512-B+mvFywunkRJs270k7kCBjhogvIA0uNn6GAXv6m2cPn3rrwqZzZVr2gBWcz+Cz7OGVWlcbERlYRIX0S6OGr8Bw== + +crelt@^1.0.0: + version "1.0.6" + resolved "https://registry.npmjs.org/crelt/-/crelt-1.0.6.tgz" + integrity sha512-VQ2MBenTq1fWZUH9DJNGti7kKv6EeAuYr3cLwxUWhIu1baTaXh4Ib5W2CqHVqib4/MqbYGJqiL3Zb8GJZr3l4g== + +cross-fetch@^3.1.5: + version "3.1.8" + resolved "https://registry.npmjs.org/cross-fetch/-/cross-fetch-3.1.8.tgz" + integrity sha512-cvA+JwZoU0Xq+h6WkMvAUqPEYy92Obet6UdKLfW60qn99ftItKjB5T+BkyWOFWe2pUyfQ+IJHmpOTznqk1M6Kg== + dependencies: + node-fetch "^2.6.12" + +cross-spawn@^7.0.2: + version "7.0.3" + resolved "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz" + integrity sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w== + dependencies: + path-key "^3.1.0" + shebang-command "^2.0.0" + which "^2.0.1" + +crypto-js@^4.2.0: + version "4.2.0" + resolved "https://registry.npmjs.org/crypto-js/-/crypto-js-4.2.0.tgz" + integrity sha512-KALDyEYgpY+Rlob/iriUtjV6d5Eq+Y191A5g4UqLAi8CyGP9N1+FdVbkc1SxKc2r4YAYqG8JzO2KGL+AizD70Q== + +css-select@^5.1.0: + version "5.1.0" + resolved "https://registry.npmjs.org/css-select/-/css-select-5.1.0.tgz" + integrity sha512-nwoRF1rvRRnnCqqY7updORDsuqKzqYJ28+oSMaJMMgOauh3fvwHqMS7EZpIPqK8GL+g9mKxF1vP/ZjSeNjEVHg== + dependencies: + boolbase "^1.0.0" + css-what "^6.1.0" + domhandler "^5.0.2" + domutils "^3.0.1" + nth-check "^2.0.1" + +css-tree@^2.2.1: + version "2.3.1" + resolved "https://registry.npmjs.org/css-tree/-/css-tree-2.3.1.tgz" + integrity sha512-6Fv1DV/TYw//QF5IzQdqsNDjx/wc8TrMBZsqjL9eW01tWb7R7k/mq+/VXfJCl7SoD5emsJop9cOByJZfs8hYIw== + dependencies: + mdn-data "2.0.30" + source-map-js "^1.0.1" + +css-tree@~2.2.0: + version "2.2.1" + resolved "https://registry.npmjs.org/css-tree/-/css-tree-2.2.1.tgz" + integrity sha512-OA0mILzGc1kCOCSJerOeqDxDQ4HOh+G8NbOJFOTgOCzpw7fCBubk0fEyxp8AgOL/jvLgYA/uV0cMbe43ElF1JA== + dependencies: + mdn-data "2.0.28" + source-map-js "^1.0.1" + +css-what@^6.1.0: + version "6.1.0" + resolved "https://registry.npmjs.org/css-what/-/css-what-6.1.0.tgz" + integrity sha512-HTUrgRJ7r4dsZKU6GjmpfRK1O76h97Z8MfS1G0FozR+oF2kG6Vfe8JE6zwrkbxigziPHinCJ+gCPjA9EaBDtRw== + +csscolorparser@~1.0.3: + version "1.0.3" + resolved "https://registry.npmjs.org/csscolorparser/-/csscolorparser-1.0.3.tgz" + integrity sha512-umPSgYwZkdFoUrH5hIq5kf0wPSXiro51nPw0j2K/c83KflkPSTBGMz6NJvMB+07VlL0y7VPo6QJcDjcgKTTm3w== + +cssjanus@^2.0.1: + version "2.1.0" + resolved "https://registry.npmjs.org/cssjanus/-/cssjanus-2.1.0.tgz" + integrity sha512-kAijbny3GmdOi9k+QT6DGIXqFvL96aksNlGr4Rhk9qXDZYWUojU4bRc3IHWxdaLNOqgEZHuXoe5Wl2l7dxLW5g== + +csso@5.0.5: + version "5.0.5" + resolved "https://registry.npmjs.org/csso/-/csso-5.0.5.tgz" + integrity sha512-0LrrStPOdJj+SPCCrGhzryycLjwcgUSHBtxNA8aIDxf0GLsRh1cKYhB00Gd1lDOS4yGH69+SNn13+TWbVHETFQ== + dependencies: + css-tree "~2.2.0" + +csstype@^3.0.2, csstype@^3.1.3: + version "3.1.3" + resolved "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz" + integrity sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw== + +damerau-levenshtein@^1.0.8: + version "1.0.8" + resolved "https://registry.npmjs.org/damerau-levenshtein/-/damerau-levenshtein-1.0.8.tgz" + integrity sha512-sdQSFB7+llfUcQHUQO3+B8ERRj0Oa4w9POWMI/puGtuf7gFywGmkaLCElnudfTiKZV+NvHqL0ifzdrI8Ro7ESA== + +data-view-buffer@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/data-view-buffer/-/data-view-buffer-1.0.1.tgz" + integrity sha512-0lht7OugA5x3iJLOWFhWK/5ehONdprk0ISXqVFn/NFrDu+cuc8iADFrGQz5BnRK7LLU3JmkbXSxaqX+/mXYtUA== + dependencies: + call-bind "^1.0.6" + es-errors "^1.3.0" + is-data-view "^1.0.1" + +data-view-byte-length@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/data-view-byte-length/-/data-view-byte-length-1.0.1.tgz" + integrity sha512-4J7wRJD3ABAzr8wP+OcIcqq2dlUKp4DVflx++hs5h5ZKydWMI6/D/fAot+yh6g2tHh8fLFTvNOaVN357NvSrOQ== + dependencies: + call-bind "^1.0.7" + es-errors "^1.3.0" + is-data-view "^1.0.1" + +data-view-byte-offset@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/data-view-byte-offset/-/data-view-byte-offset-1.0.0.tgz" + integrity sha512-t/Ygsytq+R995EJ5PZlD4Cu56sWa8InXySaViRzw9apusqsOO2bQP+SbYzAhR0pFKoB+43lYy8rWban9JSuXnA== + dependencies: + call-bind "^1.0.6" + es-errors "^1.3.0" + is-data-view "^1.0.1" + +dayjs@^1.10.7, dayjs@^1.11.11: + version "1.11.11" + resolved "https://registry.npmjs.org/dayjs/-/dayjs-1.11.11.tgz" + integrity sha512-okzr3f11N6WuqYtZSvm+F776mB41wRZMhKP+hc34YdW+KmtYYK9iqvHSwo2k9FEH3fhGXvOPV6yz2IcSrfRUDg== + +debug@^3.2.7: + version "3.2.7" + resolved "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz" + integrity sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ== + dependencies: + ms "^2.1.1" + +debug@^4.0.0, debug@^4.1.0, debug@^4.1.1, debug@^4.3.1, debug@^4.3.2, debug@^4.3.4: + version "4.3.4" + resolved "https://registry.npmjs.org/debug/-/debug-4.3.4.tgz" + integrity sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ== + dependencies: + ms "2.1.2" + +decode-named-character-reference@^1.0.0: + version "1.0.2" + resolved "https://registry.npmjs.org/decode-named-character-reference/-/decode-named-character-reference-1.0.2.tgz" + integrity sha512-O8x12RzrUF8xyVcY0KJowWsmaJxQbmy0/EtnNtHRpsOcT7dFk5W598coHqBVpmWo1oQQfsCqfCmkZN5DJrZVdg== + dependencies: + character-entities "^2.0.0" + +deep-diff@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/deep-diff/-/deep-diff-1.0.2.tgz" + integrity sha512-aWS3UIVH+NPGCD1kki+DCU9Dua032iSsO43LqQpcs4R3+dVv7tX0qBGjiVHJHjplsoUM2XRO/KB92glqc68awg== + +deep-is@^0.1.3: + version "0.1.4" + resolved "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz" + integrity sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ== + +deepmerge@^4.3.1: + version "4.3.1" + resolved "https://registry.npmjs.org/deepmerge/-/deepmerge-4.3.1.tgz" + integrity sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A== + +define-data-property@^1.0.1, define-data-property@^1.1.4: + version "1.1.4" + resolved "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz" + integrity sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A== + dependencies: + es-define-property "^1.0.0" + es-errors "^1.3.0" + gopd "^1.0.1" + +define-properties@^1.1.3, define-properties@^1.2.0, define-properties@^1.2.1: + version "1.2.1" + resolved "https://registry.npmjs.org/define-properties/-/define-properties-1.2.1.tgz" + integrity sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg== + dependencies: + define-data-property "^1.0.1" + has-property-descriptors "^1.0.0" + object-keys "^1.1.1" + +delayed-stream@~1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz" + integrity sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ== + +dequal@^2.0.0, dequal@^2.0.3: + version "2.0.3" + resolved "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz" + integrity sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA== + +devlop@^1.0.0, devlop@^1.1.0: + version "1.1.0" + resolved "https://registry.npmjs.org/devlop/-/devlop-1.1.0.tgz" + integrity sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA== + dependencies: + dequal "^2.0.0" + +dfa@^1.2.0: + version "1.2.0" + resolved "https://registry.npmjs.org/dfa/-/dfa-1.2.0.tgz" + integrity sha512-ED3jP8saaweFTjeGX8HQPjeC1YYyZs98jGNZx6IiBvxW7JG5v492kamAQB3m2wop07CvU/RQmzcKr6bgcC5D/Q== + +dir-glob@^3.0.1: + version "3.0.1" + resolved "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz" + integrity sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA== + dependencies: + path-type "^4.0.0" + +doctrine@^2.1.0: + version "2.1.0" + resolved "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz" + integrity sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw== + dependencies: + esutils "^2.0.2" + +doctrine@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz" + integrity sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w== + dependencies: + esutils "^2.0.2" + +dom-helpers@^5.0.1: + version "5.2.1" + resolved "https://registry.npmjs.org/dom-helpers/-/dom-helpers-5.2.1.tgz" + integrity sha512-nRCa7CK3VTrM2NmGkIy4cbK7IZlgBE/PYMn55rrXefr5xXDP0LdtfPnblFDoVdcAfslJ7or6iqAUnx0CCGIWQA== + dependencies: + "@babel/runtime" "^7.8.7" + csstype "^3.0.2" + +dom-serializer@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/dom-serializer/-/dom-serializer-2.0.0.tgz" + integrity sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg== + dependencies: + domelementtype "^2.3.0" + domhandler "^5.0.2" + entities "^4.2.0" + +domelementtype@^2.3.0: + version "2.3.0" + resolved "https://registry.npmjs.org/domelementtype/-/domelementtype-2.3.0.tgz" + integrity sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw== + +domhandler@^5.0.2, domhandler@^5.0.3: + version "5.0.3" + resolved "https://registry.npmjs.org/domhandler/-/domhandler-5.0.3.tgz" + integrity sha512-cgwlv/1iFQiFnU96XXgROh8xTeetsnJiDsTc7TYCLFd9+/WNkIqPTxiM/8pSd8VIrhXGTf1Ny1q1hquVqDJB5w== + dependencies: + domelementtype "^2.3.0" + +domutils@^3.0.1: + version "3.1.0" + resolved "https://registry.npmjs.org/domutils/-/domutils-3.1.0.tgz" + integrity sha512-H78uMmQtI2AhgDJjWeQmHwJJ2bLPD3GMmO7Zja/ZZh84wkm+4ut+IUnUdRa8uCGX88DiVx1j6FRe1XfxEgjEZA== + dependencies: + dom-serializer "^2.0.0" + domelementtype "^2.3.0" + domhandler "^5.0.3" + +dot-case@^3.0.4: + version "3.0.4" + resolved "https://registry.npmjs.org/dot-case/-/dot-case-3.0.4.tgz" + integrity sha512-Kv5nKlh6yRrdrGvxeJ2e5y2eRUpkUosIW4A2AS38zwSz27zu7ufDwQPi5Jhs3XAlGNetl3bmnGhQsMtkKJnj3w== + dependencies: + no-case "^3.0.4" + tslib "^2.0.3" + +earcut@^2.2.4: + version "2.2.4" + resolved "https://registry.npmjs.org/earcut/-/earcut-2.2.4.tgz" + integrity sha512-/pjZsA1b4RPHbeWZQn66SWS8nZZWLQQ23oE3Eam7aroEFGEvwKAsJfZ9ytiEMycfzXWpca4FA9QIOehf7PocBQ== + +electron-to-chromium@^1.4.535: + version "1.4.594" + resolved "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.594.tgz" + integrity sha512-xT1HVAu5xFn7bDfkjGQi9dNpMqGchUkebwf1GL7cZN32NSwwlHRPMSDJ1KN6HkS0bWUtndbSQZqvpQftKG2uFQ== + +embla-carousel-auto-height@^8.1.5: + version "8.1.5" + resolved "https://registry.npmjs.org/embla-carousel-auto-height/-/embla-carousel-auto-height-8.1.5.tgz" + integrity sha512-nYUQjcsobrgHvvJ1SYY12CHnZ/rEVYhu2Jmg9jVsroULBi7YlXeMcPJDrZOQjXg10VU07LJcP9t5KxzRaDU5rg== + +embla-carousel-auto-scroll@^8.1.5: + version "8.1.5" + resolved "https://registry.npmjs.org/embla-carousel-auto-scroll/-/embla-carousel-auto-scroll-8.1.5.tgz" + integrity sha512-LpU6Slbhrb+YzmsH9qi6J8Hde+vEq+oxIgO2zQkiVRfu2ImvOsenKZyd0ZDYj/YN/Mt+C4VVx5a2kCHXGYoXPA== + +embla-carousel-autoplay@^8.1.5: + version "8.1.5" + resolved "https://registry.npmjs.org/embla-carousel-autoplay/-/embla-carousel-autoplay-8.1.5.tgz" + integrity sha512-9pHIezRqiO9yism7wRFwmM1j/W9c9hBNX4hq3F4aTPbK84M0M57ryG8QUwhbsTGJbDoBBVTm//YEd0T6i/5YgA== + +embla-carousel-react@^8.1.5: + version "8.1.5" + resolved "https://registry.npmjs.org/embla-carousel-react/-/embla-carousel-react-8.1.5.tgz" + integrity sha512-xFmfxgJd7mpWDHQ4iyK1Qs+5BTTwu4bkn+mSROKiUH9nKpPHTeilQ+rpeQDCHRrAPeshD67aBk0/p6FxWxXsng== + dependencies: + embla-carousel "8.1.5" + embla-carousel-reactive-utils "8.1.5" + +embla-carousel-reactive-utils@8.1.5: + version "8.1.5" + resolved "https://registry.npmjs.org/embla-carousel-reactive-utils/-/embla-carousel-reactive-utils-8.1.5.tgz" + integrity sha512-76uZTrSaEGGta+qpiGkMFlLK0I7N04TdjZ2obrBhyggYIFDWlxk1CriIEmt2lisLNsa1IYXM85kr863JoCMSyg== + +embla-carousel@^8.1.5, embla-carousel@8.1.5: + version "8.1.5" + resolved "https://registry.npmjs.org/embla-carousel/-/embla-carousel-8.1.5.tgz" + integrity sha512-R6xTf7cNdR2UTNM6/yUPZlJFRmZSogMiRjJ5vXHO65II5MoUlrVYUAP0fHQei/py82Vf15lj+WI+QdhnzBxA2g== + +emoji-regex@^10.3.0: + version "10.3.0" + resolved "https://registry.npmjs.org/emoji-regex/-/emoji-regex-10.3.0.tgz" + integrity sha512-QpLs9D9v9kArv4lfDEgg1X/gN5XLnf/A6l9cs8SPZLRZR3ZkY9+kwIQTxm+fsSej5UMYGE8fdoaZVIBlqG0XTw== + +emoji-regex@^8.0.0: + version "8.0.0" + resolved "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz" + integrity sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A== + +emoji-regex@^9.2.2: + version "9.2.2" + resolved "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz" + integrity sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg== + +entities@^4.2.0, entities@^4.4.0: + version "4.5.0" + resolved "https://registry.npmjs.org/entities/-/entities-4.5.0.tgz" + integrity sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw== + +error-ex@^1.3.1: + version "1.3.2" + resolved "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz" + integrity sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g== + dependencies: + is-arrayish "^0.2.1" + +es-abstract@^1.22.1, es-abstract@^1.22.3, es-abstract@^1.23.0, es-abstract@^1.23.2, es-abstract@^1.23.3: + version "1.23.3" + resolved "https://registry.npmjs.org/es-abstract/-/es-abstract-1.23.3.tgz" + integrity sha512-e+HfNH61Bj1X9/jLc5v1owaLYuHdeHHSQlkhCBiTK8rBvKaULl/beGMxwrMXjpYrv4pz22BlY570vVePA2ho4A== + dependencies: + array-buffer-byte-length "^1.0.1" + arraybuffer.prototype.slice "^1.0.3" + available-typed-arrays "^1.0.7" + call-bind "^1.0.7" + data-view-buffer "^1.0.1" + data-view-byte-length "^1.0.1" + data-view-byte-offset "^1.0.0" + es-define-property "^1.0.0" + es-errors "^1.3.0" + es-object-atoms "^1.0.0" + es-set-tostringtag "^2.0.3" + es-to-primitive "^1.2.1" + function.prototype.name "^1.1.6" + get-intrinsic "^1.2.4" + get-symbol-description "^1.0.2" + globalthis "^1.0.3" + gopd "^1.0.1" + has-property-descriptors "^1.0.2" + has-proto "^1.0.3" + has-symbols "^1.0.3" + hasown "^2.0.2" + internal-slot "^1.0.7" + is-array-buffer "^3.0.4" + is-callable "^1.2.7" + is-data-view "^1.0.1" + is-negative-zero "^2.0.3" + is-regex "^1.1.4" + is-shared-array-buffer "^1.0.3" + is-string "^1.0.7" + is-typed-array "^1.1.13" + is-weakref "^1.0.2" + object-inspect "^1.13.1" + object-keys "^1.1.1" + object.assign "^4.1.5" + regexp.prototype.flags "^1.5.2" + safe-array-concat "^1.1.2" + safe-regex-test "^1.0.3" + string.prototype.trim "^1.2.9" + string.prototype.trimend "^1.0.8" + string.prototype.trimstart "^1.0.8" + typed-array-buffer "^1.0.2" + typed-array-byte-length "^1.0.1" + typed-array-byte-offset "^1.0.2" + typed-array-length "^1.0.6" + unbox-primitive "^1.0.2" + which-typed-array "^1.1.15" + +es-define-property@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.0.tgz" + integrity sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ== + dependencies: + get-intrinsic "^1.2.4" + +es-errors@^1.1.0, es-errors@^1.2.1, es-errors@^1.3.0: + version "1.3.0" + resolved "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz" + integrity sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw== + +es-iterator-helpers@^1.0.15, es-iterator-helpers@^1.0.19: + version "1.0.19" + resolved "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.0.19.tgz" + integrity sha512-zoMwbCcH5hwUkKJkT8kDIBZSz9I6mVG//+lDCinLCGov4+r7NIy0ld8o03M0cJxl2spVf6ESYVS6/gpIfq1FFw== + dependencies: + call-bind "^1.0.7" + define-properties "^1.2.1" + es-abstract "^1.23.3" + es-errors "^1.3.0" + es-set-tostringtag "^2.0.3" + function-bind "^1.1.2" + get-intrinsic "^1.2.4" + globalthis "^1.0.3" + has-property-descriptors "^1.0.2" + has-proto "^1.0.3" + has-symbols "^1.0.3" + internal-slot "^1.0.7" + iterator.prototype "^1.1.2" + safe-array-concat "^1.1.2" + +es-object-atoms@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.0.0.tgz" + integrity sha512-MZ4iQ6JwHOBQjahnjwaC1ZtIBH+2ohjamzAO3oaHcXYup7qxjF2fixyH+Q71voWHeOkI2q/TnJao/KfXYIZWbw== + dependencies: + es-errors "^1.3.0" + +es-set-tostringtag@^2.0.3: + version "2.0.3" + resolved "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.0.3.tgz" + integrity sha512-3T8uNMC3OQTHkFUsFq8r/BwAXLHvU/9O9mE0fBc/MY5iq/8H7ncvO947LmYA6ldWw9Uh8Yhf25zu6n7nML5QWQ== + dependencies: + get-intrinsic "^1.2.4" + has-tostringtag "^1.0.2" + hasown "^2.0.1" + +es-shim-unscopables@^1.0.0, es-shim-unscopables@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/es-shim-unscopables/-/es-shim-unscopables-1.0.2.tgz" + integrity sha512-J3yBRXCzDu4ULnQwxyToo/OjdMx6akgVC7K6few0a7F/0wLtmKKN7I73AH5T2836UuXRqN7Qg+IIUw/+YJksRw== + dependencies: + hasown "^2.0.0" + +es-to-primitive@^1.2.1: + version "1.2.1" + resolved "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.1.tgz" + integrity sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA== + dependencies: + is-callable "^1.1.4" + is-date-object "^1.0.1" + is-symbol "^1.0.2" + +escalade@^3.1.1: + version "3.1.1" + resolved "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz" + integrity sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw== + +escape-string-regexp@^1.0.5: + version "1.0.5" + resolved "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz" + integrity sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg== + +escape-string-regexp@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz" + integrity sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA== + +escape-string-regexp@^5.0.0: + version "5.0.0" + resolved "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-5.0.0.tgz" + integrity sha512-/veY75JbMK4j1yjvuUxuVsiS/hr/4iHs9FTT6cgTexxdE0Ly/glccBAkloH/DofkjRbZU3bnoj38mOmhkZ0lHw== + +eslint-config-airbnb-base@^15.0.0: + version "15.0.0" + resolved "https://registry.npmjs.org/eslint-config-airbnb-base/-/eslint-config-airbnb-base-15.0.0.tgz" + integrity sha512-xaX3z4ZZIcFLvh2oUNvcX5oEofXda7giYmuplVxoOg5A7EXJMrUyqRgR+mhDhPK8LZ4PttFOBvCYDbX3sUoUig== + dependencies: + confusing-browser-globals "^1.0.10" + object.assign "^4.1.2" + object.entries "^1.1.5" + semver "^6.3.0" + +eslint-config-airbnb@^19.0.4: + version "19.0.4" + resolved "https://registry.npmjs.org/eslint-config-airbnb/-/eslint-config-airbnb-19.0.4.tgz" + integrity sha512-T75QYQVQX57jiNgpF9r1KegMICE94VYwoFQyMGhrvc+lB8YF2E/M/PYDaQe1AJcWaEgqLE+ErXV1Og/+6Vyzew== + dependencies: + eslint-config-airbnb-base "^15.0.0" + object.assign "^4.1.2" + object.entries "^1.1.5" + +eslint-config-prettier@*, eslint-config-prettier@^9.1.0: + version "9.1.0" + resolved "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-9.1.0.tgz" + integrity sha512-NSWl5BFQWEPi1j4TjVNItzYV7dZXZ+wP6I6ZhrBGpChQhZRUaElihE9uRRkcbRnNb76UMKDF3r+WTmNcGPKsqw== + +eslint-import-resolver-alias@^1.1.2: + version "1.1.2" + resolved "https://registry.npmjs.org/eslint-import-resolver-alias/-/eslint-import-resolver-alias-1.1.2.tgz" + integrity sha512-WdviM1Eu834zsfjHtcGHtGfcu+F30Od3V7I9Fi57uhBEwPkjDcii7/yW8jAT+gOhn4P/vOxxNAXbFAKsrrc15w== + +eslint-import-resolver-node@^0.3.9: + version "0.3.9" + resolved "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.9.tgz" + integrity sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g== + dependencies: + debug "^3.2.7" + is-core-module "^2.13.0" + resolve "^1.22.4" + +eslint-module-utils@^2.8.0: + version "2.8.0" + resolved "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.8.0.tgz" + integrity sha512-aWajIYfsqCKRDgUfjEXNN/JlrzauMuSEy5sbd7WXbtW3EH6A6MpwEh42c7qD+MqQo9QMJ6fWLAeIJynx0g6OAw== + dependencies: + debug "^3.2.7" + +eslint-plugin-import@^2.25.2, eslint-plugin-import@^2.25.3, eslint-plugin-import@^2.29.1, eslint-plugin-import@>=1.4.0: + version "2.29.1" + resolved "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.29.1.tgz" + integrity sha512-BbPC0cuExzhiMo4Ff1BTVwHpjjv28C5R+btTOGaCRC7UEz801up0JadwkeSk5Ued6TG34uaczuVuH6qyy5YUxw== + dependencies: + array-includes "^3.1.7" + array.prototype.findlastindex "^1.2.3" + array.prototype.flat "^1.3.2" + array.prototype.flatmap "^1.3.2" + debug "^3.2.7" + doctrine "^2.1.0" + eslint-import-resolver-node "^0.3.9" + eslint-module-utils "^2.8.0" + hasown "^2.0.0" + is-core-module "^2.13.1" + is-glob "^4.0.3" + minimatch "^3.1.2" + object.fromentries "^2.0.7" + object.groupby "^1.0.1" + object.values "^1.1.7" + semver "^6.3.1" + tsconfig-paths "^3.15.0" + +eslint-plugin-jsx-a11y@^6.5.1, eslint-plugin-jsx-a11y@^6.8.0: + version "6.8.0" + resolved "https://registry.npmjs.org/eslint-plugin-jsx-a11y/-/eslint-plugin-jsx-a11y-6.8.0.tgz" + integrity sha512-Hdh937BS3KdwwbBaKd5+PLCOmYY6U4f2h9Z2ktwtNKvIdIEu137rjYbcb9ApSbVJfWxANNuiKTD/9tOKjK9qOA== + dependencies: + "@babel/runtime" "^7.23.2" + aria-query "^5.3.0" + array-includes "^3.1.7" + array.prototype.flatmap "^1.3.2" + ast-types-flow "^0.0.8" + axe-core "=4.7.0" + axobject-query "^3.2.1" + damerau-levenshtein "^1.0.8" + emoji-regex "^9.2.2" + es-iterator-helpers "^1.0.15" + hasown "^2.0.0" + jsx-ast-utils "^3.3.5" + language-tags "^1.0.9" + minimatch "^3.1.2" + object.entries "^1.1.7" + object.fromentries "^2.0.7" + +eslint-plugin-perfectionist@^2.11.0: + version "2.11.0" + resolved "https://registry.npmjs.org/eslint-plugin-perfectionist/-/eslint-plugin-perfectionist-2.11.0.tgz" + integrity sha512-XrtBtiu5rbQv88gl+1e2RQud9te9luYNvKIgM9emttQ2zutHPzY/AQUucwxscDKV4qlTkvLTxjOFvxqeDpPorw== + dependencies: + "@typescript-eslint/utils" "^6.13.0 || ^7.0.0" + minimatch "^9.0.3" + natural-compare-lite "^1.4.0" + +eslint-plugin-prettier@^5.1.3: + version "5.1.3" + resolved "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-5.1.3.tgz" + integrity sha512-C9GCVAs4Eq7ZC/XFQHITLiHJxQngdtraXaM+LoUFoFp/lHNl2Zn8f3WQbe9HvTBBQ9YnKFB0/2Ajdqwo5D1EAw== + dependencies: + prettier-linter-helpers "^1.0.0" + synckit "^0.8.6" + +eslint-plugin-react-hooks@^4.3.0, eslint-plugin-react-hooks@^4.6.2: + version "4.6.2" + resolved "https://registry.npmjs.org/eslint-plugin-react-hooks/-/eslint-plugin-react-hooks-4.6.2.tgz" + integrity sha512-QzliNJq4GinDBcD8gPB5v0wh6g8q3SUi6EFF0x8N/BL9PoVs0atuGc47ozMRyOWAKdwaZ5OnbOEa3WR+dSGKuQ== + +eslint-plugin-react@^7.28.0, eslint-plugin-react@^7.34.2: + version "7.34.2" + resolved "https://registry.npmjs.org/eslint-plugin-react/-/eslint-plugin-react-7.34.2.tgz" + integrity sha512-2HCmrU+/JNigDN6tg55cRDKCQWicYAPB38JGSFDQt95jDm8rrvSUo7YPkOIm5l6ts1j1zCvysNcasvfTMQzUOw== + dependencies: + array-includes "^3.1.8" + array.prototype.findlast "^1.2.5" + array.prototype.flatmap "^1.3.2" + array.prototype.toreversed "^1.1.2" + array.prototype.tosorted "^1.1.3" + doctrine "^2.1.0" + es-iterator-helpers "^1.0.19" + estraverse "^5.3.0" + jsx-ast-utils "^2.4.1 || ^3.0.0" + minimatch "^3.1.2" + object.entries "^1.1.8" + object.fromentries "^2.0.8" + object.hasown "^1.1.4" + object.values "^1.2.0" + prop-types "^15.8.1" + resolve "^2.0.0-next.5" + semver "^6.3.1" + string.prototype.matchall "^4.0.11" + +eslint-plugin-unused-imports@^3.2.0: + version "3.2.0" + resolved "https://registry.npmjs.org/eslint-plugin-unused-imports/-/eslint-plugin-unused-imports-3.2.0.tgz" + integrity sha512-6uXyn6xdINEpxE1MtDjxQsyXB37lfyO2yKGVVgtD7WEWQGORSOZjgrD6hBhvGv4/SO+TOlS+UnC6JppRqbuwGQ== + dependencies: + eslint-rule-composer "^0.3.0" + +eslint-rule-composer@^0.3.0: + version "0.3.0" + resolved "https://registry.npmjs.org/eslint-rule-composer/-/eslint-rule-composer-0.3.0.tgz" + integrity sha512-bt+Sh8CtDmn2OajxvNO+BX7Wn4CIWMpTRm3MaiKPCQcnnlm0CS2mhui6QaoeQugs+3Kj2ESKEEGJUdVafwhiCg== + +eslint-scope@^7.2.2: + version "7.2.2" + resolved "https://registry.npmjs.org/eslint-scope/-/eslint-scope-7.2.2.tgz" + integrity sha512-dOt21O7lTMhDM+X9mB4GX+DZrZtCUJPL/wlcTqxyrx5IvO0IYtILdtrQGQp+8n5S0gwSVmOf9NQrjMOgfQZlIg== + dependencies: + esrecurse "^4.3.0" + estraverse "^5.2.0" + +eslint-visitor-keys@^3.3.0, eslint-visitor-keys@^3.4.1, eslint-visitor-keys@^3.4.3: + version "3.4.3" + resolved "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.4.3.tgz" + integrity sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag== + +"eslint@^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8", "eslint@^3 || ^4 || ^5 || ^6 || ^7 || ^8", "eslint@^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0-0", "eslint@^6.0.0 || ^7.0.0 || >=8.0.0", "eslint@^7.32.0 || ^8.2.0", eslint@^8.56.0, eslint@^8.57.0, eslint@>=7.0.0, eslint@>=8.0.0, eslint@8: + version "8.57.0" + resolved "https://registry.npmjs.org/eslint/-/eslint-8.57.0.tgz" + integrity sha512-dZ6+mexnaTIbSBZWgou51U6OmzIhYM2VcNdtiTtI7qPNZm35Akpr0f6vtw3w1Kmn5PYo+tZVfh13WrhpS6oLqQ== + dependencies: + "@eslint-community/eslint-utils" "^4.2.0" + "@eslint-community/regexpp" "^4.6.1" + "@eslint/eslintrc" "^2.1.4" + "@eslint/js" "8.57.0" + "@humanwhocodes/config-array" "^0.11.14" + "@humanwhocodes/module-importer" "^1.0.1" + "@nodelib/fs.walk" "^1.2.8" + "@ungap/structured-clone" "^1.2.0" + ajv "^6.12.4" + chalk "^4.0.0" + cross-spawn "^7.0.2" + debug "^4.3.2" + doctrine "^3.0.0" + escape-string-regexp "^4.0.0" + eslint-scope "^7.2.2" + eslint-visitor-keys "^3.4.3" + espree "^9.6.1" + esquery "^1.4.2" + esutils "^2.0.2" + fast-deep-equal "^3.1.3" + file-entry-cache "^6.0.1" + find-up "^5.0.0" + glob-parent "^6.0.2" + globals "^13.19.0" + graphemer "^1.4.0" + ignore "^5.2.0" + imurmurhash "^0.1.4" + is-glob "^4.0.0" + is-path-inside "^3.0.3" + js-yaml "^4.1.0" + json-stable-stringify-without-jsonify "^1.0.1" + levn "^0.4.1" + lodash.merge "^4.6.2" + minimatch "^3.1.2" + natural-compare "^1.4.0" + optionator "^0.9.3" + strip-ansi "^6.0.1" + text-table "^0.2.0" + +espree@^9.6.0, espree@^9.6.1: + version "9.6.1" + resolved "https://registry.npmjs.org/espree/-/espree-9.6.1.tgz" + integrity sha512-oruZaFkjorTpF32kDSI5/75ViwGeZginGGy2NoOSg3Q9bnwlnmDm4HLnkl0RE3n+njDXR037aY1+x58Z/zFdwQ== + dependencies: + acorn "^8.9.0" + acorn-jsx "^5.3.2" + eslint-visitor-keys "^3.4.1" + +esquery@^1.4.2: + version "1.5.0" + resolved "https://registry.npmjs.org/esquery/-/esquery-1.5.0.tgz" + integrity sha512-YQLXUplAwJgCydQ78IMJywZCceoqk1oH01OERdSAJc/7U2AylwjhSCLDEtqwg811idIS/9fIU5GjG73IgjKMVg== + dependencies: + estraverse "^5.1.0" + +esrecurse@^4.3.0: + version "4.3.0" + resolved "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz" + integrity sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag== + dependencies: + estraverse "^5.2.0" + +estraverse@^5.1.0, estraverse@^5.2.0, estraverse@^5.3.0: + version "5.3.0" + resolved "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz" + integrity sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA== + +esutils@^2.0.2: + version "2.0.3" + resolved "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz" + integrity sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g== + +events@^3.3.0: + version "3.3.0" + resolved "https://registry.npmjs.org/events/-/events-3.3.0.tgz" + integrity sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q== + +extend-shallow@^2.0.1: + version "2.0.1" + resolved "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz" + integrity sha512-zCnTtlxNoAiDc3gqY2aYAWFx7XWWiasuF2K8Me5WbN8otHKTUKBwjPtNpRs/rbUZm7KxWAaNj7P1a/p52GbVug== + dependencies: + is-extendable "^0.1.0" + +extend-shallow@^3.0.0: + version "3.0.2" + resolved "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz" + integrity sha512-BwY5b5Ql4+qZoefgMj2NUmx+tehVTH/Kf4k1ZEtOHNFcm2wSxMRo992l6X3TIgni2eZVTZ85xMOjF31fwZAj6Q== + dependencies: + assign-symbols "^1.0.0" + is-extendable "^1.0.1" + +extend@^3.0.0: + version "3.0.2" + resolved "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz" + integrity sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g== + +fast-deep-equal@^3.1.1, fast-deep-equal@^3.1.3: + version "3.1.3" + resolved "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz" + integrity sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q== + +fast-diff@^1.1.2: + version "1.3.0" + resolved "https://registry.npmjs.org/fast-diff/-/fast-diff-1.3.0.tgz" + integrity sha512-VxPP4NqbUjj6MaAOafWeUn2cXWLcCtljklUtZf0Ind4XQ+QPtmA0b18zZy0jIQx+ExRVCR/ZQpBmik5lXshNsw== + +fast-glob@^3.2.9: + version "3.3.2" + resolved "https://registry.npmjs.org/fast-glob/-/fast-glob-3.3.2.tgz" + integrity sha512-oX2ruAFQwf/Orj8m737Y5adxDQO0LAB7/S5MnxCdTNDd4p6BsyIVsv9JQsATbTSq8KHRpLwIHbVlUNatxd+1Ow== + dependencies: + "@nodelib/fs.stat" "^2.0.2" + "@nodelib/fs.walk" "^1.2.3" + glob-parent "^5.1.2" + merge2 "^1.3.0" + micromatch "^4.0.4" + +fast-json-stable-stringify@^2.0.0: + version "2.1.0" + resolved "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz" + integrity sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw== + +fast-levenshtein@^2.0.6: + version "2.0.6" + resolved "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz" + integrity sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw== + +fast-xml-parser@^4.2.5: + version "4.4.0" + resolved "https://registry.npmjs.org/fast-xml-parser/-/fast-xml-parser-4.4.0.tgz" + integrity sha512-kLY3jFlwIYwBNDojclKsNAC12sfD6NwW74QB2CoNGPvtVxjliYehVunB3HYyNi+n4Tt1dAcgwYvmKF/Z18flqg== + dependencies: + strnum "^1.0.5" + +fast-xml-parser@4.2.5: + version "4.2.5" + resolved "https://registry.npmjs.org/fast-xml-parser/-/fast-xml-parser-4.2.5.tgz" + integrity sha512-B9/wizE4WngqQftFPmdaMYlXoJlJOYxGQOanC77fq9k8+Z0v5dDSVh+3glErdIROP//s/jgb7ZuxKfB8nVyo0g== + dependencies: + strnum "^1.0.5" + +fastq@^1.6.0: + version "1.15.0" + resolved "https://registry.npmjs.org/fastq/-/fastq-1.15.0.tgz" + integrity sha512-wBrocU2LCXXa+lWBt8RoIRD89Fi8OdABODa/kEnyeyjS5aZO5/GNvI5sEINADqP/h8M29UHTHUb53sUu5Ihqdw== + dependencies: + reusify "^1.0.4" + +faye-websocket@0.11.4: + version "0.11.4" + resolved "https://registry.npmjs.org/faye-websocket/-/faye-websocket-0.11.4.tgz" + integrity sha512-CzbClwlXAuiRQAlUyfqPgvPoNKTckTPGfwZV4ZdAhVcP2lh9KUxJg2b5GkE7XbjKQ3YJnQ9z6D9ntLAlB+tP8g== + dependencies: + websocket-driver ">=0.5.1" + +fflate@^0.8.1: + version "0.8.2" + resolved "https://registry.npmjs.org/fflate/-/fflate-0.8.2.tgz" + integrity sha512-cPJU47OaAoCbg0pBvzsgpTPhmhqI5eJjh/JIu8tPj5q+T7iLvW/JAYUqmE7KOB4R1ZyEhzBaIQpQpardBF5z8A== + +file-entry-cache@^6.0.1: + version "6.0.1" + resolved "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-6.0.1.tgz" + integrity sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg== + dependencies: + flat-cache "^3.0.4" + +file-selector@^0.6.0: + version "0.6.0" + resolved "https://registry.npmjs.org/file-selector/-/file-selector-0.6.0.tgz" + integrity sha512-QlZ5yJC0VxHxQQsQhXvBaC7VRJ2uaxTf+Tfpu4Z/OcVQJVpZO+DGU0rkoVW5ce2SccxugvpBJoMvUs59iILYdw== + dependencies: + tslib "^2.4.0" + +fill-range@^7.1.1: + version "7.1.1" + resolved "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz" + integrity sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg== + dependencies: + to-regex-range "^5.0.1" + +find-root@^1.1.0: + version "1.1.0" + resolved "https://registry.npmjs.org/find-root/-/find-root-1.1.0.tgz" + integrity sha512-NKfW6bec6GfKc0SGx1e07QZY9PE99u0Bft/0rzSD5k3sO/vwkVUpDUKVm5Gpp5Ue3YfShPFTX2070tDs5kB9Ng== + +find-up@^5.0.0: + version "5.0.0" + resolved "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz" + integrity sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng== + dependencies: + locate-path "^6.0.0" + path-exists "^4.0.0" + +firebase@^10.12.2: + version "10.12.2" + resolved "https://registry.npmjs.org/firebase/-/firebase-10.12.2.tgz" + integrity sha512-ZxEdtSvP1I9su1yf32D8TIdgxtPgxwr6z3jYAR1TXS/t+fVfpoPc/N1/N2bxOco9mNjUoc+od34v5Fn4GeKs6Q== + dependencies: + "@firebase/analytics" "0.10.4" + "@firebase/analytics-compat" "0.2.10" + "@firebase/app" "0.10.5" + "@firebase/app-check" "0.8.4" + "@firebase/app-check-compat" "0.3.11" + "@firebase/app-compat" "0.2.35" + "@firebase/app-types" "0.9.2" + "@firebase/auth" "1.7.4" + "@firebase/auth-compat" "0.5.9" + "@firebase/database" "1.0.5" + "@firebase/database-compat" "1.0.5" + "@firebase/firestore" "4.6.3" + "@firebase/firestore-compat" "0.3.32" + "@firebase/functions" "0.11.5" + "@firebase/functions-compat" "0.3.11" + "@firebase/installations" "0.6.7" + "@firebase/installations-compat" "0.2.7" + "@firebase/messaging" "0.12.9" + "@firebase/messaging-compat" "0.2.9" + "@firebase/performance" "0.6.7" + "@firebase/performance-compat" "0.2.7" + "@firebase/remote-config" "0.4.7" + "@firebase/remote-config-compat" "0.2.7" + "@firebase/storage" "0.12.5" + "@firebase/storage-compat" "0.3.8" + "@firebase/util" "1.9.6" + "@firebase/vertexai-preview" "0.0.2" + +flat-cache@^3.0.4: + version "3.2.0" + resolved "https://registry.npmjs.org/flat-cache/-/flat-cache-3.2.0.tgz" + integrity sha512-CYcENa+FtcUKLmhhqyctpclsq7QF38pKjZHsGNiSQF5r4FtoKDWabFDl3hzaEQMvT1LHEysw5twgLvpYYb4vbw== + dependencies: + flatted "^3.2.9" + keyv "^4.5.3" + rimraf "^3.0.2" + +flatted@^3.2.9: + version "3.2.9" + resolved "https://registry.npmjs.org/flatted/-/flatted-3.2.9.tgz" + integrity sha512-36yxDn5H7OFZQla0/jFJmbIKTdZAQHngCedGxiMmpNfEZM0sdEeT+WczLQrjK6D7o2aiyLYDnkw0R3JK0Qv1RQ== + +follow-redirects@^1.15.6: + version "1.15.6" + resolved "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.6.tgz" + integrity sha512-wWN62YITEaOpSK584EZXJafH1AGpO8RVgElfkuXbTOrPX4fIfOyEpW/CsiNd8JdYrAoOvafRTOEnvsO++qCqFA== + +fontkit@^2.0.2: + version "2.0.2" + resolved "https://registry.npmjs.org/fontkit/-/fontkit-2.0.2.tgz" + integrity sha512-jc4k5Yr8iov8QfS6u8w2CnHWVmbOGtdBtOXMze5Y+QD966Rx6PEVWXSEGwXlsDlKtu1G12cJjcsybnqhSk/+LA== + dependencies: + "@swc/helpers" "^0.4.2" + brotli "^1.3.2" + clone "^2.1.2" + dfa "^1.2.0" + fast-deep-equal "^3.1.3" + restructure "^3.0.0" + tiny-inflate "^1.0.3" + unicode-properties "^1.4.0" + unicode-trie "^2.0.0" + +for-each@^0.3.3: + version "0.3.3" + resolved "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz" + integrity sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw== + dependencies: + is-callable "^1.1.3" + +form-data@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz" + integrity sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww== + dependencies: + asynckit "^0.4.0" + combined-stream "^1.0.8" + mime-types "^2.1.12" + +framer-motion@^11.2.10: + version "11.2.10" + resolved "https://registry.npmjs.org/framer-motion/-/framer-motion-11.2.10.tgz" + integrity sha512-/gr3PLZUVFCc86a9MqCUboVrALscrdluzTb3yew+2/qKBU8CX6nzs918/SRBRCqaPbx0TZP10CB6yFgK2C5cYQ== + dependencies: + tslib "^2.4.0" + +fs.realpath@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz" + integrity sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw== + +function-bind@^1.1.2: + version "1.1.2" + resolved "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz" + integrity sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA== + +function.prototype.name@^1.1.5, function.prototype.name@^1.1.6: + version "1.1.6" + resolved "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.1.6.tgz" + integrity sha512-Z5kx79swU5P27WEayXM1tBi5Ze/lbIyiNgU3qyXUOf9b2rgXYyF9Dy9Cx+IQv/Lc8WCG6L82zwUPpSS9hGehIg== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + functions-have-names "^1.2.3" + +functions-have-names@^1.2.3: + version "1.2.3" + resolved "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz" + integrity sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ== + +gensync@^1.0.0-beta.2: + version "1.0.0-beta.2" + resolved "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz" + integrity sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg== + +geojson-vt@^3.2.1: + version "3.2.1" + resolved "https://registry.npmjs.org/geojson-vt/-/geojson-vt-3.2.1.tgz" + integrity sha512-EvGQQi/zPrDA6zr6BnJD/YhwAkBP8nnJ9emh3EnHQKVMfg/MRVtPbMYdgVy/IaEmn4UfagD2a6fafPDL5hbtwg== + +get-caller-file@^2.0.5: + version "2.0.5" + resolved "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz" + integrity sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg== + +get-intrinsic@^1.1.1, get-intrinsic@^1.1.3, get-intrinsic@^1.2.1, get-intrinsic@^1.2.3, get-intrinsic@^1.2.4: + version "1.2.4" + resolved "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.4.tgz" + integrity sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ== + dependencies: + es-errors "^1.3.0" + function-bind "^1.1.2" + has-proto "^1.0.1" + has-symbols "^1.0.3" + hasown "^2.0.0" + +get-symbol-description@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/get-symbol-description/-/get-symbol-description-1.0.2.tgz" + integrity sha512-g0QYk1dZBxGwk+Ngc+ltRH2IBp2f7zBkBMBJZCDerh6EhlhSR6+9irMCuT/09zD6qkarHUSn529sK/yL4S27mg== + dependencies: + call-bind "^1.0.5" + es-errors "^1.3.0" + get-intrinsic "^1.2.4" + +get-value@^2.0.2, get-value@^2.0.6: + version "2.0.6" + resolved "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz" + integrity sha512-Ln0UQDlxH1BapMu3GPtf7CuYNwRZf2gwCuPqbyG6pB8WfmFpzqcy4xtAaAMUhnNqjMKTiCPZG2oMT3YSx8U2NA== + +gl-matrix@^3.4.3: + version "3.4.3" + resolved "https://registry.npmjs.org/gl-matrix/-/gl-matrix-3.4.3.tgz" + integrity sha512-wcCp8vu8FT22BnvKVPjXa/ICBWRq/zjFfdofZy1WSpQZpphblv12/bOQLBC1rMM7SGOFS9ltVmKOHil5+Ml7gA== + +glob-parent@^5.1.2: + version "5.1.2" + resolved "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz" + integrity sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow== + dependencies: + is-glob "^4.0.1" + +glob-parent@^6.0.2: + version "6.0.2" + resolved "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz" + integrity sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A== + dependencies: + is-glob "^4.0.3" + +glob@^7.1.3: + version "7.2.3" + resolved "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz" + integrity sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.1.1" + once "^1.3.0" + path-is-absolute "^1.0.0" + +globals@^11.1.0: + version "11.12.0" + resolved "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz" + integrity sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA== + +globals@^13.19.0: + version "13.23.0" + resolved "https://registry.npmjs.org/globals/-/globals-13.23.0.tgz" + integrity sha512-XAmF0RjlrjY23MA51q3HltdlGxUpXPvg0GioKiD9X6HD28iMjo2dKC8Vqwm7lne4GNr78+RHTfliktR6ZH09wA== + dependencies: + type-fest "^0.20.2" + +globalthis@^1.0.3: + version "1.0.3" + resolved "https://registry.npmjs.org/globalthis/-/globalthis-1.0.3.tgz" + integrity sha512-sFdI5LyBiNTHjRd7cGPWapiHWMOXKyuBNX/cWJ3NfzrZQVa8GI/8cofCl74AOVqq9W5kNmguTIzJ/1s2gyI9wA== + dependencies: + define-properties "^1.1.3" + +globby@^11.1.0: + version "11.1.0" + resolved "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz" + integrity sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g== + dependencies: + array-union "^2.1.0" + dir-glob "^3.0.1" + fast-glob "^3.2.9" + ignore "^5.2.0" + merge2 "^1.4.1" + slash "^3.0.0" + +gopd@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz" + integrity sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA== + dependencies: + get-intrinsic "^1.1.3" + +graceful-fs@^4.2.11: + version "4.2.11" + resolved "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz" + integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ== + +graphemer@^1.4.0: + version "1.4.0" + resolved "https://registry.npmjs.org/graphemer/-/graphemer-1.4.0.tgz" + integrity sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag== + +graphql@15.8.0: + version "15.8.0" + resolved "https://registry.npmjs.org/graphql/-/graphql-15.8.0.tgz" + integrity sha512-5gghUc24tP9HRznNpV2+FIoq3xKkj5dTQqf4v0CpdPbFVwFkWoxOM+o+2OC9ZSvjEMTjfmG9QT+gcvggTwW1zw== + +grid-index@^1.1.0: + version "1.1.0" + resolved "https://registry.npmjs.org/grid-index/-/grid-index-1.1.0.tgz" + integrity sha512-HZRwumpOGUrHyxO5bqKZL0B0GlUpwtCAzZ42sgxUPniu33R1LSFH5yrIcBCHjkctCAh3mtWKcKd9J4vDDdeVHA== + +has-bigints@^1.0.1, has-bigints@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/has-bigints/-/has-bigints-1.0.2.tgz" + integrity sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ== + +has-flag@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz" + integrity sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw== + +has-flag@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz" + integrity sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ== + +has-property-descriptors@^1.0.0, has-property-descriptors@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz" + integrity sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg== + dependencies: + es-define-property "^1.0.0" + +has-proto@^1.0.1, has-proto@^1.0.3: + version "1.0.3" + resolved "https://registry.npmjs.org/has-proto/-/has-proto-1.0.3.tgz" + integrity sha512-SJ1amZAJUiZS+PhsVLf5tGydlaVB8EdFpaSO4gmiUKUOxk8qzn5AIy4ZeJUmh22znIdk/uMAUT2pl3FxzVUH+Q== + +has-symbols@^1.0.2, has-symbols@^1.0.3: + version "1.0.3" + resolved "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz" + integrity sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A== + +has-tostringtag@^1.0.0, has-tostringtag@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz" + integrity sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw== + dependencies: + has-symbols "^1.0.3" + +hasown@^2.0.0, hasown@^2.0.1, hasown@^2.0.2: + version "2.0.2" + resolved "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz" + integrity sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ== + dependencies: + function-bind "^1.1.2" + +hast-util-from-parse5@^8.0.0: + version "8.0.1" + resolved "https://registry.npmjs.org/hast-util-from-parse5/-/hast-util-from-parse5-8.0.1.tgz" + integrity sha512-Er/Iixbc7IEa7r/XLtuG52zoqn/b3Xng/w6aZQ0xGVxzhw5xUFxcRqdPzP6yFi/4HBYRaifaI5fQ1RH8n0ZeOQ== + dependencies: + "@types/hast" "^3.0.0" + "@types/unist" "^3.0.0" + devlop "^1.0.0" + hastscript "^8.0.0" + property-information "^6.0.0" + vfile "^6.0.0" + vfile-location "^5.0.0" + web-namespaces "^2.0.0" + +hast-util-is-element@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/hast-util-is-element/-/hast-util-is-element-3.0.0.tgz" + integrity sha512-Val9mnv2IWpLbNPqc/pUem+a7Ipj2aHacCwgNfTiK0vJKl0LF+4Ba4+v1oPHFpf3bLYmreq0/l3Gud9S5OH42g== + dependencies: + "@types/hast" "^3.0.0" + +hast-util-parse-selector@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/hast-util-parse-selector/-/hast-util-parse-selector-4.0.0.tgz" + integrity sha512-wkQCkSYoOGCRKERFWcxMVMOcYE2K1AaNLU8DXS9arxnLOUEWbOXKXiJUNzEpqZ3JOKpnha3jkFrumEjVliDe7A== + dependencies: + "@types/hast" "^3.0.0" + +hast-util-raw@^9.0.0: + version "9.0.1" + resolved "https://registry.npmjs.org/hast-util-raw/-/hast-util-raw-9.0.1.tgz" + integrity sha512-5m1gmba658Q+lO5uqL5YNGQWeh1MYWZbZmWrM5lncdcuiXuo5E2HT/CIOp0rLF8ksfSwiCVJ3twlgVRyTGThGA== + dependencies: + "@types/hast" "^3.0.0" + "@types/unist" "^3.0.0" + "@ungap/structured-clone" "^1.0.0" + hast-util-from-parse5 "^8.0.0" + hast-util-to-parse5 "^8.0.0" + html-void-elements "^3.0.0" + mdast-util-to-hast "^13.0.0" + parse5 "^7.0.0" + unist-util-position "^5.0.0" + unist-util-visit "^5.0.0" + vfile "^6.0.0" + web-namespaces "^2.0.0" + zwitch "^2.0.0" + +hast-util-to-jsx-runtime@^2.0.0: + version "2.2.0" + resolved "https://registry.npmjs.org/hast-util-to-jsx-runtime/-/hast-util-to-jsx-runtime-2.2.0.tgz" + integrity sha512-wSlp23N45CMjDg/BPW8zvhEi3R+8eRE1qFbjEyAUzMCzu2l1Wzwakq+Tlia9nkCtEl5mDxa7nKHsvYJ6Gfn21A== + dependencies: + "@types/hast" "^3.0.0" + "@types/unist" "^3.0.0" + comma-separated-tokens "^2.0.0" + hast-util-whitespace "^3.0.0" + property-information "^6.0.0" + space-separated-tokens "^2.0.0" + style-to-object "^0.4.0" + unist-util-position "^5.0.0" + vfile-message "^4.0.0" + +hast-util-to-parse5@^8.0.0: + version "8.0.0" + resolved "https://registry.npmjs.org/hast-util-to-parse5/-/hast-util-to-parse5-8.0.0.tgz" + integrity sha512-3KKrV5ZVI8if87DVSi1vDeByYrkGzg4mEfeu4alwgmmIeARiBLKCZS2uw5Gb6nU9x9Yufyj3iudm6i7nl52PFw== + dependencies: + "@types/hast" "^3.0.0" + comma-separated-tokens "^2.0.0" + devlop "^1.0.0" + property-information "^6.0.0" + space-separated-tokens "^2.0.0" + web-namespaces "^2.0.0" + zwitch "^2.0.0" + +hast-util-to-text@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/hast-util-to-text/-/hast-util-to-text-4.0.0.tgz" + integrity sha512-EWiE1FSArNBPUo1cKWtzqgnuRQwEeQbQtnFJRYV1hb1BWDgrAlBU0ExptvZMM/KSA82cDpm2sFGf3Dmc5Mza3w== + dependencies: + "@types/hast" "^3.0.0" + "@types/unist" "^3.0.0" + hast-util-is-element "^3.0.0" + unist-util-find-after "^5.0.0" + +hast-util-whitespace@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/hast-util-whitespace/-/hast-util-whitespace-3.0.0.tgz" + integrity sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw== + dependencies: + "@types/hast" "^3.0.0" + +hastscript@^8.0.0: + version "8.0.0" + resolved "https://registry.npmjs.org/hastscript/-/hastscript-8.0.0.tgz" + integrity sha512-dMOtzCEd3ABUeSIISmrETiKuyydk1w0pa+gE/uormcTpSYuaNJPbX1NU3JLyscSLjwAQM8bWMhhIlnCqnRvDTw== + dependencies: + "@types/hast" "^3.0.0" + comma-separated-tokens "^2.0.0" + hast-util-parse-selector "^4.0.0" + property-information "^6.0.0" + space-separated-tokens "^2.0.0" + +highlight.js@~11.9.0: + version "11.9.0" + resolved "https://registry.npmjs.org/highlight.js/-/highlight.js-11.9.0.tgz" + integrity sha512-fJ7cW7fQGCYAkgv4CPfwFHrfd/cLS4Hau96JuJ+ZTOWhjnhoeN1ub1tFmALm/+lW5z4WCAuAV9bm05AP0mS6Gw== + +hoist-non-react-statics@^3.3.1: + version "3.3.2" + resolved "https://registry.npmjs.org/hoist-non-react-statics/-/hoist-non-react-statics-3.3.2.tgz" + integrity sha512-/gGivxi8JPKWNm/W0jSmzcMPpfpPLc3dY/6GxhX2hQ9iGj3aDfklV4ET7NjKpSinLpJ5vafa9iiGIEZg10SfBw== + dependencies: + react-is "^16.7.0" + +hsl-to-hex@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/hsl-to-hex/-/hsl-to-hex-1.0.0.tgz" + integrity sha512-K6GVpucS5wFf44X0h2bLVRDsycgJmf9FF2elg+CrqD8GcFU8c6vYhgXn8NjUkFCwj+xDFb70qgLbTUm6sxwPmA== + dependencies: + hsl-to-rgb-for-reals "^1.1.0" + +hsl-to-rgb-for-reals@^1.1.0: + version "1.1.1" + resolved "https://registry.npmjs.org/hsl-to-rgb-for-reals/-/hsl-to-rgb-for-reals-1.1.1.tgz" + integrity sha512-LgOWAkrN0rFaQpfdWBQlv/VhkOxb5AsBjk6NQVx4yEzWS923T07X0M1Y0VNko2H52HeSpZrZNNMJ0aFqsdVzQg== + +html-parse-stringify@^3.0.1: + version "3.0.1" + resolved "https://registry.npmjs.org/html-parse-stringify/-/html-parse-stringify-3.0.1.tgz" + integrity sha512-KknJ50kTInJ7qIScF3jeaFRpMpE8/lfiTdzf/twXyPBLAGrLRTmkz3AdTnKeh40X8k9L2fdYwEp/42WGXIRGcg== + dependencies: + void-elements "3.1.0" + +html-url-attributes@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/html-url-attributes/-/html-url-attributes-3.0.0.tgz" + integrity sha512-/sXbVCWayk6GDVg3ctOX6nxaVj7So40FcFAnWlWGNAB1LpYKcV5Cd10APjPjW80O7zYW2MsjBV4zZ7IZO5fVow== + +html-void-elements@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/html-void-elements/-/html-void-elements-3.0.0.tgz" + integrity sha512-bEqo66MRXsUGxWHV5IP0PUiAWwoEjba4VCzg0LjFJBpchPaTfyfCKTG6bc5F8ucKec3q5y6qOdGyYTSBEvhCrg== + +http-parser-js@>=0.5.1: + version "0.5.8" + resolved "https://registry.npmjs.org/http-parser-js/-/http-parser-js-0.5.8.tgz" + integrity sha512-SGeBX54F94Wgu5RH3X5jsDtf4eHyRogWX1XGT3b4HuW3tQPM4AaBzoUji/4AAJNXCEOWZ5O0DgZmJw1947gD5Q== + +hyphen@^1.6.4: + version "1.10.4" + resolved "https://registry.npmjs.org/hyphen/-/hyphen-1.10.4.tgz" + integrity sha512-SejXzIpv9gOVdDWXd4suM1fdF1k2dxZGvuTdkOVLoazYfK7O4DykIQbdrvuyG+EaTNlXAGhMndtKrhykgbt0gg== + +i18next-browser-languagedetector@^8.0.0: + version "8.0.0" + resolved "https://registry.npmjs.org/i18next-browser-languagedetector/-/i18next-browser-languagedetector-8.0.0.tgz" + integrity sha512-zhXdJXTTCoG39QsrOCiOabnWj2jecouOqbchu3EfhtSHxIB5Uugnm9JaizenOy39h7ne3+fLikIjeW88+rgszw== + dependencies: + "@babel/runtime" "^7.23.2" + +i18next-resources-to-backend@^1.2.1: + version "1.2.1" + resolved "https://registry.npmjs.org/i18next-resources-to-backend/-/i18next-resources-to-backend-1.2.1.tgz" + integrity sha512-okHbVA+HZ7n1/76MsfhPqDou0fptl2dAlhRDu2ideXloRRduzHsqDOznJBef+R3DFZnbvWoBW+KxJ7fnFjd6Yw== + dependencies: + "@babel/runtime" "^7.23.2" + +i18next@^23.11.5, "i18next@>= 23.2.3": + version "23.11.5" + resolved "https://registry.npmjs.org/i18next/-/i18next-23.11.5.tgz" + integrity sha512-41pvpVbW9rhZPk5xjCX2TPJi2861LEig/YRhUkY+1FQ2IQPS0bKUDYnEqY8XPPbB48h1uIwLnP9iiEfuSl20CA== + dependencies: + "@babel/runtime" "^7.23.2" + +idb@5.0.6: + version "5.0.6" + resolved "https://registry.npmjs.org/idb/-/idb-5.0.6.tgz" + integrity sha512-/PFvOWPzRcEPmlDt5jEvzVZVs0wyd/EvGvkDIcbBpGuMMLQKrTPG0TxvE2UJtgZtCQCmOtM2QD7yQJBVEjKGOw== + +idb@7.1.1: + version "7.1.1" + resolved "https://registry.npmjs.org/idb/-/idb-7.1.1.tgz" + integrity sha512-gchesWBzyvGHRO9W8tzUWFDycow5gwjvFKfyV9FF32Y7F50yZMp7mP+T2mJIWFx49zicqyC4uefHM17o6xKIVQ== + +ieee754@^1.1.12, ieee754@^1.1.4: + version "1.2.1" + resolved "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz" + integrity sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA== + +ignore@^5.2.0: + version "5.3.1" + resolved "https://registry.npmjs.org/ignore/-/ignore-5.3.1.tgz" + integrity sha512-5Fytz/IraMjqpwfd34ke28PTVMjZjJG2MPn5t7OE4eUCUNf8BAa7b5WUS9/Qvr6mwOQS7Mk6vdsMno5he+T8Xw== + +immer@9.0.6: + version "9.0.6" + resolved "https://registry.npmjs.org/immer/-/immer-9.0.6.tgz" + integrity sha512-G95ivKpy+EvVAnAab4fVa4YGYn24J1SpEktnJX7JJ45Bd7xqME/SCplFzYFmTbrkwZbQ4xJK1xMTUYBkN6pWsQ== + +import-fresh@^3.2.1, import-fresh@^3.3.0: + version "3.3.0" + resolved "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz" + integrity sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw== + dependencies: + parent-module "^1.0.0" + resolve-from "^4.0.0" + +imurmurhash@^0.1.4: + version "0.1.4" + resolved "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz" + integrity sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA== + +inflight@^1.0.4: + version "1.0.6" + resolved "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz" + integrity sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA== + dependencies: + once "^1.3.0" + wrappy "1" + +inherits@^2.0.3, inherits@~2.0.3, inherits@2: + version "2.0.4" + resolved "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz" + integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== + +inline-style-parser@0.1.1: + version "0.1.1" + resolved "https://registry.npmjs.org/inline-style-parser/-/inline-style-parser-0.1.1.tgz" + integrity sha512-7NXolsK4CAS5+xvdj5OMMbI962hU/wvwoxk+LWR9Ek9bVtyuuYScDN6eS0rUm6TxApFpw7CX1o4uJzcd4AyD3Q== + +input-format@^0.3.10: + version "0.3.10" + resolved "https://registry.npmjs.org/input-format/-/input-format-0.3.10.tgz" + integrity sha512-5cFv/kOZD7Ch0viprVkuYPDkAU7HBZYBx8QrIpQ6yXUWbAQ0+RQ8IIojDJOf/RO6FDJLL099HDSK2KoVZ2zevg== + dependencies: + prop-types "^15.8.1" + +internal-slot@^1.0.7: + version "1.0.7" + resolved "https://registry.npmjs.org/internal-slot/-/internal-slot-1.0.7.tgz" + integrity sha512-NGnrKwXzSms2qUUih/ILZ5JBqNTSa1+ZmP6flaIp6KmSElgE9qdndzS3cqjrDovwFdmwsGsLdeFgB6suw+1e9g== + dependencies: + es-errors "^1.3.0" + hasown "^2.0.0" + side-channel "^1.0.4" + +is-array-buffer@^3.0.4: + version "3.0.4" + resolved "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.4.tgz" + integrity sha512-wcjaerHw0ydZwfhiKbXJWLDY8A7yV7KhjQOpb83hGgGfId/aQa4TOvwyzn2PuswW2gPCYEL/nEAiSVpdOj1lXw== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.2.1" + +is-arrayish@^0.2.1: + version "0.2.1" + resolved "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz" + integrity sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg== + +is-arrayish@^0.3.1: + version "0.3.2" + resolved "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.3.2.tgz" + integrity sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ== + +is-async-function@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/is-async-function/-/is-async-function-2.0.0.tgz" + integrity sha512-Y1JXKrfykRJGdlDwdKlLpLyMIiWqWvuSd17TvZk68PLAOGOoF4Xyav1z0Xhoi+gCYjZVeC5SI+hYFOfvXmGRCA== + dependencies: + has-tostringtag "^1.0.0" + +is-bigint@^1.0.1: + version "1.0.4" + resolved "https://registry.npmjs.org/is-bigint/-/is-bigint-1.0.4.tgz" + integrity sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg== + dependencies: + has-bigints "^1.0.1" + +is-boolean-object@^1.1.0: + version "1.1.2" + resolved "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.1.2.tgz" + integrity sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA== + dependencies: + call-bind "^1.0.2" + has-tostringtag "^1.0.0" + +is-callable@^1.1.3, is-callable@^1.1.4, is-callable@^1.2.7: + version "1.2.7" + resolved "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz" + integrity sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA== + +is-core-module@^2.13.0, is-core-module@^2.13.1: + version "2.13.1" + resolved "https://registry.npmjs.org/is-core-module/-/is-core-module-2.13.1.tgz" + integrity sha512-hHrIjvZsftOsvKSn2TRYl63zvxsgE0K+0mYMoH6gD4omR5IWB2KynivBQczo3+wF1cCkjzvptnI9Q0sPU66ilw== + dependencies: + hasown "^2.0.0" + +is-data-view@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/is-data-view/-/is-data-view-1.0.1.tgz" + integrity sha512-AHkaJrsUVW6wq6JS8y3JnM/GJF/9cf+k20+iDzlSaJrinEo5+7vRiteOSwBhHRiAyQATN1AmY4hwzxJKPmYf+w== + dependencies: + is-typed-array "^1.1.13" + +is-date-object@^1.0.1, is-date-object@^1.0.5: + version "1.0.5" + resolved "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.5.tgz" + integrity sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ== + dependencies: + has-tostringtag "^1.0.0" + +is-extendable@^0.1.0, is-extendable@^0.1.1: + version "0.1.1" + resolved "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz" + integrity sha512-5BMULNob1vgFX6EjQw5izWDxrecWK9AM72rugNr0TFldMOi0fj6Jk+zeKIt0xGj4cEfQIJth4w3OKWOJ4f+AFw== + +is-extendable@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz" + integrity sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA== + dependencies: + is-plain-object "^2.0.4" + +is-extglob@^2.1.1: + version "2.1.1" + resolved "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz" + integrity sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ== + +is-finalizationregistry@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/is-finalizationregistry/-/is-finalizationregistry-1.0.2.tgz" + integrity sha512-0by5vtUJs8iFQb5TYUHHPudOR+qXYIMKtiUzvLIZITZUjknFmziyBJuLhVRc+Ds0dREFlskDNJKYIdIzu/9pfw== + dependencies: + call-bind "^1.0.2" + +is-fullwidth-code-point@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz" + integrity sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg== + +is-generator-function@^1.0.10: + version "1.0.10" + resolved "https://registry.npmjs.org/is-generator-function/-/is-generator-function-1.0.10.tgz" + integrity sha512-jsEjy9l3yiXEQ+PsXdmBwEPcOxaXWLspKdplFUVI9vq1iZgIekeC0L167qeu86czQaxed3q/Uzuw0swL0irL8A== + dependencies: + has-tostringtag "^1.0.0" + +is-glob@^4.0.0, is-glob@^4.0.1, is-glob@^4.0.3: + version "4.0.3" + resolved "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz" + integrity sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg== + dependencies: + is-extglob "^2.1.1" + +is-lite@^0.8.2: + version "0.8.2" + resolved "https://registry.npmjs.org/is-lite/-/is-lite-0.8.2.tgz" + integrity sha512-JZfH47qTsslwaAsqbMI3Q6HNNjUuq6Cmzzww50TdP5Esb6e1y2sK2UAaZZuzfAzpoI2AkxoPQapZdlDuP6Vlsw== + +is-lite@^1.2.0, is-lite@^1.2.1: + version "1.2.1" + resolved "https://registry.npmjs.org/is-lite/-/is-lite-1.2.1.tgz" + integrity sha512-pgF+L5bxC+10hLBgf6R2P4ZZUBOQIIacbdo8YvuCP8/JvsWxG7aZ9p10DYuLtifFci4l3VITphhMlMV4Y+urPw== + +is-map@^2.0.1: + version "2.0.2" + resolved "https://registry.npmjs.org/is-map/-/is-map-2.0.2.tgz" + integrity sha512-cOZFQQozTha1f4MxLFzlgKYPTyj26picdZTx82hbc/Xf4K/tZOOXSCkMvU4pKioRXGDLJRn0GM7Upe7kR721yg== + +is-negative-zero@^2.0.3: + version "2.0.3" + resolved "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.3.tgz" + integrity sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw== + +is-number-object@^1.0.4: + version "1.0.7" + resolved "https://registry.npmjs.org/is-number-object/-/is-number-object-1.0.7.tgz" + integrity sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ== + dependencies: + has-tostringtag "^1.0.0" + +is-number@^7.0.0: + version "7.0.0" + resolved "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz" + integrity sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng== + +is-path-inside@^3.0.3: + version "3.0.3" + resolved "https://registry.npmjs.org/is-path-inside/-/is-path-inside-3.0.3.tgz" + integrity sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ== + +is-plain-obj@^4.0.0: + version "4.1.0" + resolved "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-4.1.0.tgz" + integrity sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg== + +is-plain-object@^2.0.3, is-plain-object@^2.0.4: + version "2.0.4" + resolved "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz" + integrity sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og== + dependencies: + isobject "^3.0.1" + +is-regex@^1.1.4: + version "1.1.4" + resolved "https://registry.npmjs.org/is-regex/-/is-regex-1.1.4.tgz" + integrity sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg== + dependencies: + call-bind "^1.0.2" + has-tostringtag "^1.0.0" + +is-set@^2.0.1: + version "2.0.2" + resolved "https://registry.npmjs.org/is-set/-/is-set-2.0.2.tgz" + integrity sha512-+2cnTEZeY5z/iXGbLhPrOAaK/Mau5k5eXq9j14CpRTftq0pAJu2MwVRSZhyZWBzx3o6X795Lz6Bpb6R0GKf37g== + +is-shared-array-buffer@^1.0.2, is-shared-array-buffer@^1.0.3: + version "1.0.3" + resolved "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.3.tgz" + integrity sha512-nA2hv5XIhLR3uVzDDfCIknerhx8XUKnstuOERPNNIinXG7v9u+ohXF67vxm4TPTEPU6lm61ZkwP3c9PCB97rhg== + dependencies: + call-bind "^1.0.7" + +is-string@^1.0.5, is-string@^1.0.7: + version "1.0.7" + resolved "https://registry.npmjs.org/is-string/-/is-string-1.0.7.tgz" + integrity sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg== + dependencies: + has-tostringtag "^1.0.0" + +is-symbol@^1.0.2, is-symbol@^1.0.3: + version "1.0.4" + resolved "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.4.tgz" + integrity sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg== + dependencies: + has-symbols "^1.0.2" + +is-typed-array@^1.1.13: + version "1.1.13" + resolved "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.13.tgz" + integrity sha512-uZ25/bUAlUY5fR4OKT4rZQEBrzQWYV9ZJYGGsUmEJ6thodVJ1HX64ePQ6Z0qPWP+m+Uq6e9UugrE38jeYsDSMw== + dependencies: + which-typed-array "^1.1.14" + +is-url@^1.2.4: + version "1.2.4" + resolved "https://registry.npmjs.org/is-url/-/is-url-1.2.4.tgz" + integrity sha512-ITvGim8FhRiYe4IQ5uHSkj7pVaPDrCTkNd3yq3cV7iZAcJdHTUMPMEHcqSOy9xZ9qFenQCvi+2wjH9a1nXqHww== + +is-weakmap@^2.0.1: + version "2.0.1" + resolved "https://registry.npmjs.org/is-weakmap/-/is-weakmap-2.0.1.tgz" + integrity sha512-NSBR4kH5oVj1Uwvv970ruUkCV7O1mzgVFO4/rev2cLRda9Tm9HrL70ZPut4rOHgY0FNrUu9BCbXA2sdQ+x0chA== + +is-weakref@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/is-weakref/-/is-weakref-1.0.2.tgz" + integrity sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ== + dependencies: + call-bind "^1.0.2" + +is-weakset@^2.0.1: + version "2.0.2" + resolved "https://registry.npmjs.org/is-weakset/-/is-weakset-2.0.2.tgz" + integrity sha512-t2yVvttHkQktwnNNmBQ98AhENLdPUTDTE21uPqAQ0ARwQfGeQKRVS0NNurH7bTf7RrvcVn1OOge45CnBeHCSmg== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.1.1" + +isarray@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz" + integrity sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ== + +isarray@^2.0.5: + version "2.0.5" + resolved "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz" + integrity sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw== + +isexe@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz" + integrity sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw== + +isobject@^3.0.1: + version "3.0.1" + resolved "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz" + integrity sha512-WhB9zCku7EGTj/HQQRz5aUQEUeoQZH2bWcltRErOpymJ4boYE6wL9Tbr23krRPSZ+C5zqNSrSw+Cc7sZZ4b7vg== + +iterator.prototype@^1.1.2: + version "1.1.2" + resolved "https://registry.npmjs.org/iterator.prototype/-/iterator.prototype-1.1.2.tgz" + integrity sha512-DR33HMMr8EzwuRL8Y9D3u2BMj8+RqSE850jfGu59kS7tbmPLzGkZmVSfyCFSDxuZiEY6Rzt3T2NA/qU+NwVj1w== + dependencies: + define-properties "^1.2.1" + get-intrinsic "^1.2.1" + has-symbols "^1.0.3" + reflect.getprototypeof "^1.0.4" + set-function-name "^2.0.1" + +jay-peg@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/jay-peg/-/jay-peg-1.0.2.tgz" + integrity sha512-fyV3NVvv6pTys/3BTapBUGAWAuU9rM2gRcgijZHzptd5KKL+s+S7hESFN+wOsbDH1MzFwdlRAXi0aGxS6uiMKg== + dependencies: + restructure "^3.0.0" + +js-cookie@^3.0.5: + version "3.0.5" + resolved "https://registry.npmjs.org/js-cookie/-/js-cookie-3.0.5.tgz" + integrity sha512-cEiJEAEoIbWfCZYKWhVwFuvPX1gETRYPw6LlaTKoxD3s2AkXzkCjnp6h0V77ozyqj0jakteJ4YqDJT830+lVGw== + +"js-tokens@^3.0.0 || ^4.0.0", js-tokens@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz" + integrity sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ== + +js-yaml@^4.1.0: + version "4.1.0" + resolved "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz" + integrity sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA== + dependencies: + argparse "^2.0.1" + +jsesc@^2.5.1: + version "2.5.2" + resolved "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz" + integrity sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA== + +jsesc@~0.5.0: + version "0.5.0" + resolved "https://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz" + integrity sha512-uZz5UnB7u4T9LvwmFqXii7pZSouaRPorGs5who1Ip7VO0wxanFvBL7GkM6dTHlgX+jhBApRetaWpnDabOeTcnA== + +json-buffer@3.0.1: + version "3.0.1" + resolved "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz" + integrity sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ== + +json-parse-even-better-errors@^2.3.0: + version "2.3.1" + resolved "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz" + integrity sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w== + +json-schema-traverse@^0.4.1: + version "0.4.1" + resolved "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz" + integrity sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg== + +json-stable-stringify-without-jsonify@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz" + integrity sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw== + +json-stringify-pretty-compact@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/json-stringify-pretty-compact/-/json-stringify-pretty-compact-3.0.0.tgz" + integrity sha512-Rc2suX5meI0S3bfdZuA7JMFBGkJ875ApfVyq2WHELjBiiG22My/l7/8zPpH/CfFVQHuVLd8NLR0nv6vi0BYYKA== + +json5@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/json5/-/json5-1.0.2.tgz" + integrity sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA== + dependencies: + minimist "^1.2.0" + +json5@^2.2.3: + version "2.2.3" + resolved "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz" + integrity sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg== + +"jsx-ast-utils@^2.4.1 || ^3.0.0", jsx-ast-utils@^3.3.5: + version "3.3.5" + resolved "https://registry.npmjs.org/jsx-ast-utils/-/jsx-ast-utils-3.3.5.tgz" + integrity sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ== + dependencies: + array-includes "^3.1.6" + array.prototype.flat "^1.3.1" + object.assign "^4.1.4" + object.values "^1.1.6" + +kdbush@^4.0.1, kdbush@^4.0.2: + version "4.0.2" + resolved "https://registry.npmjs.org/kdbush/-/kdbush-4.0.2.tgz" + integrity sha512-WbCVYJ27Sz8zi9Q7Q0xHC+05iwkm3Znipc2XTlrnJbsHMYktW4hPhXUE8Ys1engBrvffoSCqbil1JQAa7clRpA== + +keyv@^4.5.3: + version "4.5.4" + resolved "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz" + integrity sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw== + dependencies: + json-buffer "3.0.1" + +language-subtag-registry@^0.3.20: + version "0.3.22" + resolved "https://registry.npmjs.org/language-subtag-registry/-/language-subtag-registry-0.3.22.tgz" + integrity sha512-tN0MCzyWnoz/4nHS6uxdlFWoUZT7ABptwKPQ52Ea7URk6vll88bWBVhodtnlfEuCcKWNGoc+uGbw1cwa9IKh/w== + +language-tags@^1.0.9: + version "1.0.9" + resolved "https://registry.npmjs.org/language-tags/-/language-tags-1.0.9.tgz" + integrity sha512-MbjN408fEndfiQXbFQ1vnd+1NoLDsnQW41410oQBXiyXDMYH5z505juWa4KUE1LqxRC7DgOgZDbKLxHIwm27hA== + dependencies: + language-subtag-registry "^0.3.20" + +"legacy-swc-helpers@npm:@swc/helpers@=0.4.14": + version "0.4.14" + resolved "https://registry.npmjs.org/@swc/helpers/-/helpers-0.4.14.tgz" + integrity sha512-4C7nX/dvpzB7za4Ql9K81xK3HPxCpHMgwTZVyf+9JQ6VUbn9jjZVN7/Nkdz/Ugzs2CSjqnL/UPXroiVBVHUWUw== + dependencies: + tslib "^2.4.0" + +levn@^0.4.1: + version "0.4.1" + resolved "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz" + integrity sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ== + dependencies: + prelude-ls "^1.2.1" + type-check "~0.4.0" + +libphonenumber-js@^1.11.2: + version "1.11.2" + resolved "https://registry.npmjs.org/libphonenumber-js/-/libphonenumber-js-1.11.2.tgz" + integrity sha512-V9mGLlaXN1WETzqQvSu6qf6XVAr3nFuJvWsHcuzCCCo6xUKawwSxOPTpan5CGOSKTn5w/bQuCZcLPJkyysgC3w== + +lines-and-columns@^1.1.6: + version "1.2.4" + resolved "https://registry.npmjs.org/lines-and-columns/-/lines-and-columns-1.2.4.tgz" + integrity sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg== + +linkify-it@^5.0.0: + version "5.0.0" + resolved "https://registry.npmjs.org/linkify-it/-/linkify-it-5.0.0.tgz" + integrity sha512-5aHCbzQRADcdP+ATqnDuhhJ/MRIqDkZX5pyjFHRRysS8vZ5AbqGEoFIb6pYHPZ+L/OC2Lc+xT8uHVVR5CAK/wQ== + dependencies: + uc.micro "^2.0.0" + +linkifyjs@^4.1.0: + version "4.1.3" + resolved "https://registry.npmjs.org/linkifyjs/-/linkifyjs-4.1.3.tgz" + integrity sha512-auMesunaJ8yfkHvK4gfg1K0SaKX/6Wn9g2Aac/NwX+l5VdmFZzo/hdPGxEOETj+ryRa4/fiOPjeeKURSAJx1sg== + +locate-path@^6.0.0: + version "6.0.0" + resolved "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz" + integrity sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw== + dependencies: + p-locate "^5.0.0" + +lodash-es@^4.17.21: + version "4.17.21" + resolved "https://registry.npmjs.org/lodash-es/-/lodash-es-4.17.21.tgz" + integrity sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw== + +lodash.camelcase@^4.3.0: + version "4.3.0" + resolved "https://registry.npmjs.org/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz" + integrity sha512-TwuEnCnxbc3rAvhf/LbG7tJUDzhqXyFnv3dtzLOPgCG/hODL7WFnsbwktkD7yUV0RrreP/l1PALq/YSg6VvjlA== + +lodash.clonedeep@^4.5.0: + version "4.5.0" + resolved "https://registry.npmjs.org/lodash.clonedeep/-/lodash.clonedeep-4.5.0.tgz" + integrity sha512-H5ZhCF25riFd9uB5UCkVKo61m3S/xZk1x4wA6yp/L3RFP6Z/eHH1ymQcGLo7J3GMPfm0V/7m1tryHuGVxpqEBQ== + +lodash.debounce@^4.0.8: + version "4.0.8" + resolved "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz" + integrity sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow== + +lodash.merge@^4.6.2: + version "4.6.2" + resolved "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz" + integrity sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ== + +lodash.throttle@^4.1.1: + version "4.1.1" + resolved "https://registry.npmjs.org/lodash.throttle/-/lodash.throttle-4.1.1.tgz" + integrity sha512-wIkUCfVKpVsWo3JSZlc+8MB5it+2AN5W8J7YVMST30UrvcQNZ1Okbj+rbVniijTWE6FGYy4XJq/rHkas8qJMLQ== + +lodash@^4.17.21: + version "4.17.21" + resolved "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz" + integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg== + +long@^5.0.0: + version "5.2.3" + resolved "https://registry.npmjs.org/long/-/long-5.2.3.tgz" + integrity sha512-lcHwpNoggQTObv5apGNCTdJrO69eHOZMi4BNC+rTLER8iHAqGrUVeLh/irVIM7zTw2bOXA8T6uNPeujwOLg/2Q== + +longest-streak@^3.0.0: + version "3.1.0" + resolved "https://registry.npmjs.org/longest-streak/-/longest-streak-3.1.0.tgz" + integrity sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g== + +loose-envify@^1.1.0, loose-envify@^1.4.0: + version "1.4.0" + resolved "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz" + integrity sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q== + dependencies: + js-tokens "^3.0.0 || ^4.0.0" + +lower-case@^2.0.2: + version "2.0.2" + resolved "https://registry.npmjs.org/lower-case/-/lower-case-2.0.2.tgz" + integrity sha512-7fm3l3NAF9WfN6W3JOmf5drwpVqX78JtoGJ3A6W0a6ZnldM41w2fV5D490psKFTpMds8TJse/eHLFFsNHHjHgg== + dependencies: + tslib "^2.0.3" + +lowlight@^3.0.0, lowlight@^3.1.0: + version "3.1.0" + resolved "https://registry.npmjs.org/lowlight/-/lowlight-3.1.0.tgz" + integrity sha512-CEbNVoSikAxwDMDPjXlqlFYiZLkDJHwyGu/MfOsJnF3d7f3tds5J3z8s/l9TMXhzfsJCCJEAsD78842mwmg0PQ== + dependencies: + "@types/hast" "^3.0.0" + devlop "^1.0.0" + highlight.js "~11.9.0" + +lru-cache@^5.1.1: + version "5.1.1" + resolved "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz" + integrity sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w== + dependencies: + yallist "^3.0.2" + +mapbox-gl@^3.4.0, mapbox-gl@>=1.13.0: + version "3.4.0" + resolved "https://registry.npmjs.org/mapbox-gl/-/mapbox-gl-3.4.0.tgz" + integrity sha512-QWgL28zg/zuIOHeF8DXPvHy1UHTgO5p4Oy6ifCAHwI9/hoI9/Fruya0yI4HkDtX1OgzTLO6SHO13A781BGJvyw== + dependencies: + "@mapbox/jsonlint-lines-primitives" "^2.0.2" + "@mapbox/mapbox-gl-supported" "^3.0.0" + "@mapbox/point-geometry" "^0.1.0" + "@mapbox/tiny-sdf" "^2.0.6" + "@mapbox/unitbezier" "^0.0.1" + "@mapbox/vector-tile" "^1.3.1" + "@mapbox/whoots-js" "^3.1.0" + cheap-ruler "^3.0.1" + csscolorparser "~1.0.3" + earcut "^2.2.4" + fflate "^0.8.1" + geojson-vt "^3.2.1" + gl-matrix "^3.4.3" + grid-index "^1.1.0" + kdbush "^4.0.1" + lodash.clonedeep "^4.5.0" + murmurhash-js "^1.0.0" + pbf "^3.2.1" + potpack "^2.0.0" + quickselect "^2.0.0" + rw "^1.3.3" + serialize-to-js "^3.1.2" + supercluster "^8.0.0" + tiny-lru "^11.2.6" + tinyqueue "^2.0.3" + tweakpane "^4.0.3" + vt-pbf "^3.1.3" + +markdown-it@^14.0.0: + version "14.1.0" + resolved "https://registry.npmjs.org/markdown-it/-/markdown-it-14.1.0.tgz" + integrity sha512-a54IwgWPaeBCAAsv13YgmALOF1elABB08FxO9i+r4VFk5Vl4pKokRPeX8u5TCgSsPi6ec1otfLjdOpVcgbpshg== + dependencies: + argparse "^2.0.1" + entities "^4.4.0" + linkify-it "^5.0.0" + mdurl "^2.0.0" + punycode.js "^2.3.1" + uc.micro "^2.1.0" + +markdown-table@^3.0.0: + version "3.0.3" + resolved "https://registry.npmjs.org/markdown-table/-/markdown-table-3.0.3.tgz" + integrity sha512-Z1NL3Tb1M9wH4XESsCDEksWoKTdlUafKc4pt0GRwjUyXaCFZ+dc3g2erqB6zm3szA2IUSi7VnPI+o/9jnxh9hw== + +mdast-util-find-and-replace@^3.0.0: + version "3.0.1" + resolved "https://registry.npmjs.org/mdast-util-find-and-replace/-/mdast-util-find-and-replace-3.0.1.tgz" + integrity sha512-SG21kZHGC3XRTSUhtofZkBzZTJNM5ecCi0SK2IMKmSXR8vO3peL+kb1O0z7Zl83jKtutG4k5Wv/W7V3/YHvzPA== + dependencies: + "@types/mdast" "^4.0.0" + escape-string-regexp "^5.0.0" + unist-util-is "^6.0.0" + unist-util-visit-parents "^6.0.0" + +mdast-util-from-markdown@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-2.0.0.tgz" + integrity sha512-n7MTOr/z+8NAX/wmhhDji8O3bRvPTV/U0oTCaZJkjhPSKTPhS3xufVhKGF8s1pJ7Ox4QgoIU7KHseh09S+9rTA== + dependencies: + "@types/mdast" "^4.0.0" + "@types/unist" "^3.0.0" + decode-named-character-reference "^1.0.0" + devlop "^1.0.0" + mdast-util-to-string "^4.0.0" + micromark "^4.0.0" + micromark-util-decode-numeric-character-reference "^2.0.0" + micromark-util-decode-string "^2.0.0" + micromark-util-normalize-identifier "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + unist-util-stringify-position "^4.0.0" + +mdast-util-gfm-autolink-literal@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/mdast-util-gfm-autolink-literal/-/mdast-util-gfm-autolink-literal-2.0.0.tgz" + integrity sha512-FyzMsduZZHSc3i0Px3PQcBT4WJY/X/RCtEJKuybiC6sjPqLv7h1yqAkmILZtuxMSsUyaLUWNp71+vQH2zqp5cg== + dependencies: + "@types/mdast" "^4.0.0" + ccount "^2.0.0" + devlop "^1.0.0" + mdast-util-find-and-replace "^3.0.0" + micromark-util-character "^2.0.0" + +mdast-util-gfm-footnote@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/mdast-util-gfm-footnote/-/mdast-util-gfm-footnote-2.0.0.tgz" + integrity sha512-5jOT2boTSVkMnQ7LTrd6n/18kqwjmuYqo7JUPe+tRCY6O7dAuTFMtTPauYYrMPpox9hlN0uOx/FL8XvEfG9/mQ== + dependencies: + "@types/mdast" "^4.0.0" + devlop "^1.1.0" + mdast-util-from-markdown "^2.0.0" + mdast-util-to-markdown "^2.0.0" + micromark-util-normalize-identifier "^2.0.0" + +mdast-util-gfm-strikethrough@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/mdast-util-gfm-strikethrough/-/mdast-util-gfm-strikethrough-2.0.0.tgz" + integrity sha512-mKKb915TF+OC5ptj5bJ7WFRPdYtuHv0yTRxK2tJvi+BDqbkiG7h7u/9SI89nRAYcmap2xHQL9D+QG/6wSrTtXg== + dependencies: + "@types/mdast" "^4.0.0" + mdast-util-from-markdown "^2.0.0" + mdast-util-to-markdown "^2.0.0" + +mdast-util-gfm-table@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/mdast-util-gfm-table/-/mdast-util-gfm-table-2.0.0.tgz" + integrity sha512-78UEvebzz/rJIxLvE7ZtDd/vIQ0RHv+3Mh5DR96p7cS7HsBhYIICDBCu8csTNWNO6tBWfqXPWekRuj2FNOGOZg== + dependencies: + "@types/mdast" "^4.0.0" + devlop "^1.0.0" + markdown-table "^3.0.0" + mdast-util-from-markdown "^2.0.0" + mdast-util-to-markdown "^2.0.0" + +mdast-util-gfm-task-list-item@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/mdast-util-gfm-task-list-item/-/mdast-util-gfm-task-list-item-2.0.0.tgz" + integrity sha512-IrtvNvjxC1o06taBAVJznEnkiHxLFTzgonUdy8hzFVeDun0uTjxxrRGVaNFqkU1wJR3RBPEfsxmU6jDWPofrTQ== + dependencies: + "@types/mdast" "^4.0.0" + devlop "^1.0.0" + mdast-util-from-markdown "^2.0.0" + mdast-util-to-markdown "^2.0.0" + +mdast-util-gfm@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/mdast-util-gfm/-/mdast-util-gfm-3.0.0.tgz" + integrity sha512-dgQEX5Amaq+DuUqf26jJqSK9qgixgd6rYDHAv4aTBuA92cTknZlKpPfa86Z/s8Dj8xsAQpFfBmPUHWJBWqS4Bw== + dependencies: + mdast-util-from-markdown "^2.0.0" + mdast-util-gfm-autolink-literal "^2.0.0" + mdast-util-gfm-footnote "^2.0.0" + mdast-util-gfm-strikethrough "^2.0.0" + mdast-util-gfm-table "^2.0.0" + mdast-util-gfm-task-list-item "^2.0.0" + mdast-util-to-markdown "^2.0.0" + +mdast-util-phrasing@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/mdast-util-phrasing/-/mdast-util-phrasing-4.0.0.tgz" + integrity sha512-xadSsJayQIucJ9n053dfQwVu1kuXg7jCTdYsMK8rqzKZh52nLfSH/k0sAxE0u+pj/zKZX+o5wB+ML5mRayOxFA== + dependencies: + "@types/mdast" "^4.0.0" + unist-util-is "^6.0.0" + +mdast-util-to-hast@^13.0.0: + version "13.0.2" + resolved "https://registry.npmjs.org/mdast-util-to-hast/-/mdast-util-to-hast-13.0.2.tgz" + integrity sha512-U5I+500EOOw9e3ZrclN3Is3fRpw8c19SMyNZlZ2IS+7vLsNzb2Om11VpIVOR+/0137GhZsFEF6YiKD5+0Hr2Og== + dependencies: + "@types/hast" "^3.0.0" + "@types/mdast" "^4.0.0" + "@ungap/structured-clone" "^1.0.0" + devlop "^1.0.0" + micromark-util-sanitize-uri "^2.0.0" + trim-lines "^3.0.0" + unist-util-position "^5.0.0" + unist-util-visit "^5.0.0" + +mdast-util-to-markdown@^2.0.0: + version "2.1.0" + resolved "https://registry.npmjs.org/mdast-util-to-markdown/-/mdast-util-to-markdown-2.1.0.tgz" + integrity sha512-SR2VnIEdVNCJbP6y7kVTJgPLifdr8WEU440fQec7qHoHOUz/oJ2jmNRqdDQ3rbiStOXb2mCDGTuwsK5OPUgYlQ== + dependencies: + "@types/mdast" "^4.0.0" + "@types/unist" "^3.0.0" + longest-streak "^3.0.0" + mdast-util-phrasing "^4.0.0" + mdast-util-to-string "^4.0.0" + micromark-util-decode-string "^2.0.0" + unist-util-visit "^5.0.0" + zwitch "^2.0.0" + +mdast-util-to-string@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-4.0.0.tgz" + integrity sha512-0H44vDimn51F0YwvxSJSm0eCDOJTRlmN0R1yBh4HLj9wiV1Dn0QoXGbvFAWj2hSItVTlCmBF1hqKlIyUBVFLPg== + dependencies: + "@types/mdast" "^4.0.0" + +mdn-data@2.0.28: + version "2.0.28" + resolved "https://registry.npmjs.org/mdn-data/-/mdn-data-2.0.28.tgz" + integrity sha512-aylIc7Z9y4yzHYAJNuESG3hfhC+0Ibp/MAMiaOZgNv4pmEdFyfZhhhny4MNiAfWdBQ1RQ2mfDWmM1x8SvGyp8g== + +mdn-data@2.0.30: + version "2.0.30" + resolved "https://registry.npmjs.org/mdn-data/-/mdn-data-2.0.30.tgz" + integrity sha512-GaqWWShW4kv/G9IEucWScBx9G1/vsFZZJUO+tD26M8J8z3Kw5RDQjaoZe03YAClgeS/SWPOcb4nkFBTEi5DUEA== + +mdurl@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/mdurl/-/mdurl-2.0.0.tgz" + integrity sha512-Lf+9+2r+Tdp5wXDXC4PcIBjTDtq4UKjCPMQhKIuzpJNW0b96kVqSwW0bT7FhRSfmAiFYgP+SCRvdrDozfh0U5w== + +media-engine@^1.0.3: + version "1.0.3" + resolved "https://registry.npmjs.org/media-engine/-/media-engine-1.0.3.tgz" + integrity sha512-aa5tG6sDoK+k70B9iEX1NeyfT8ObCKhNDs6lJVpwF6r8vhUfuKMslIcirq6HIUYuuUYLefcEQOn9bSBOvawtwg== + +merge2@^1.3.0, merge2@^1.4.1: + version "1.4.1" + resolved "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz" + integrity sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg== + +micromark-core-commonmark@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-core-commonmark/-/micromark-core-commonmark-2.0.0.tgz" + integrity sha512-jThOz/pVmAYUtkroV3D5c1osFXAMv9e0ypGDOIZuCeAe91/sD6BoE2Sjzt30yuXtwOYUmySOhMas/PVyh02itA== + dependencies: + decode-named-character-reference "^1.0.0" + devlop "^1.0.0" + micromark-factory-destination "^2.0.0" + micromark-factory-label "^2.0.0" + micromark-factory-space "^2.0.0" + micromark-factory-title "^2.0.0" + micromark-factory-whitespace "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-chunked "^2.0.0" + micromark-util-classify-character "^2.0.0" + micromark-util-html-tag-name "^2.0.0" + micromark-util-normalize-identifier "^2.0.0" + micromark-util-resolve-all "^2.0.0" + micromark-util-subtokenize "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-extension-gfm-autolink-literal@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-extension-gfm-autolink-literal/-/micromark-extension-gfm-autolink-literal-2.0.0.tgz" + integrity sha512-rTHfnpt/Q7dEAK1Y5ii0W8bhfJlVJFnJMHIPisfPK3gpVNuOP0VnRl96+YJ3RYWV/P4gFeQoGKNlT3RhuvpqAg== + dependencies: + micromark-util-character "^2.0.0" + micromark-util-sanitize-uri "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-extension-gfm-footnote@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-extension-gfm-footnote/-/micromark-extension-gfm-footnote-2.0.0.tgz" + integrity sha512-6Rzu0CYRKDv3BfLAUnZsSlzx3ak6HAoI85KTiijuKIz5UxZxbUI+pD6oHgw+6UtQuiRwnGRhzMmPRv4smcz0fg== + dependencies: + devlop "^1.0.0" + micromark-core-commonmark "^2.0.0" + micromark-factory-space "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-normalize-identifier "^2.0.0" + micromark-util-sanitize-uri "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-extension-gfm-strikethrough@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-extension-gfm-strikethrough/-/micromark-extension-gfm-strikethrough-2.0.0.tgz" + integrity sha512-c3BR1ClMp5fxxmwP6AoOY2fXO9U8uFMKs4ADD66ahLTNcwzSCyRVU4k7LPV5Nxo/VJiR4TdzxRQY2v3qIUceCw== + dependencies: + devlop "^1.0.0" + micromark-util-chunked "^2.0.0" + micromark-util-classify-character "^2.0.0" + micromark-util-resolve-all "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-extension-gfm-table@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-extension-gfm-table/-/micromark-extension-gfm-table-2.0.0.tgz" + integrity sha512-PoHlhypg1ItIucOaHmKE8fbin3vTLpDOUg8KAr8gRCF1MOZI9Nquq2i/44wFvviM4WuxJzc3demT8Y3dkfvYrw== + dependencies: + devlop "^1.0.0" + micromark-factory-space "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-extension-gfm-tagfilter@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-extension-gfm-tagfilter/-/micromark-extension-gfm-tagfilter-2.0.0.tgz" + integrity sha512-xHlTOmuCSotIA8TW1mDIM6X2O1SiX5P9IuDtqGonFhEK0qgRI4yeC6vMxEV2dgyr2TiD+2PQ10o+cOhdVAcwfg== + dependencies: + micromark-util-types "^2.0.0" + +micromark-extension-gfm-task-list-item@^2.0.0: + version "2.0.1" + resolved "https://registry.npmjs.org/micromark-extension-gfm-task-list-item/-/micromark-extension-gfm-task-list-item-2.0.1.tgz" + integrity sha512-cY5PzGcnULaN5O7T+cOzfMoHjBW7j+T9D2sucA5d/KbsBTPcYdebm9zUd9zzdgJGCwahV+/W78Z3nbulBYVbTw== + dependencies: + devlop "^1.0.0" + micromark-factory-space "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-extension-gfm@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/micromark-extension-gfm/-/micromark-extension-gfm-3.0.0.tgz" + integrity sha512-vsKArQsicm7t0z2GugkCKtZehqUm31oeGBV/KVSorWSy8ZlNAv7ytjFhvaryUiCUJYqs+NoE6AFhpQvBTM6Q4w== + dependencies: + micromark-extension-gfm-autolink-literal "^2.0.0" + micromark-extension-gfm-footnote "^2.0.0" + micromark-extension-gfm-strikethrough "^2.0.0" + micromark-extension-gfm-table "^2.0.0" + micromark-extension-gfm-tagfilter "^2.0.0" + micromark-extension-gfm-task-list-item "^2.0.0" + micromark-util-combine-extensions "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-factory-destination@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-factory-destination/-/micromark-factory-destination-2.0.0.tgz" + integrity sha512-j9DGrQLm/Uhl2tCzcbLhy5kXsgkHUrjJHg4fFAeoMRwJmJerT9aw4FEhIbZStWN8A3qMwOp1uzHr4UL8AInxtA== + dependencies: + micromark-util-character "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-factory-label@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-factory-label/-/micromark-factory-label-2.0.0.tgz" + integrity sha512-RR3i96ohZGde//4WSe/dJsxOX6vxIg9TimLAS3i4EhBAFx8Sm5SmqVfR8E87DPSR31nEAjZfbt91OMZWcNgdZw== + dependencies: + devlop "^1.0.0" + micromark-util-character "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-factory-space@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.0.tgz" + integrity sha512-TKr+LIDX2pkBJXFLzpyPyljzYK3MtmllMUMODTQJIUfDGncESaqB90db9IAUcz4AZAJFdd8U9zOp9ty1458rxg== + dependencies: + micromark-util-character "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-factory-title@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-factory-title/-/micromark-factory-title-2.0.0.tgz" + integrity sha512-jY8CSxmpWLOxS+t8W+FG3Xigc0RDQA9bKMY/EwILvsesiRniiVMejYTE4wumNc2f4UbAa4WsHqe3J1QS1sli+A== + dependencies: + micromark-factory-space "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-factory-whitespace@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-factory-whitespace/-/micromark-factory-whitespace-2.0.0.tgz" + integrity sha512-28kbwaBjc5yAI1XadbdPYHX/eDnqaUFVikLwrO7FDnKG7lpgxnvk/XGRhX/PN0mOZ+dBSZ+LgunHS+6tYQAzhA== + dependencies: + micromark-factory-space "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-util-character@^2.0.0: + version "2.0.1" + resolved "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.0.1.tgz" + integrity sha512-3wgnrmEAJ4T+mGXAUfMvMAbxU9RDG43XmGce4j6CwPtVxB3vfwXSZ6KhFwDzZ3mZHhmPimMAXg71veiBGzeAZw== + dependencies: + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-util-chunked@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-chunked/-/micromark-util-chunked-2.0.0.tgz" + integrity sha512-anK8SWmNphkXdaKgz5hJvGa7l00qmcaUQoMYsBwDlSKFKjc6gjGXPDw3FNL3Nbwq5L8gE+RCbGqTw49FK5Qyvg== + dependencies: + micromark-util-symbol "^2.0.0" + +micromark-util-classify-character@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-classify-character/-/micromark-util-classify-character-2.0.0.tgz" + integrity sha512-S0ze2R9GH+fu41FA7pbSqNWObo/kzwf8rN/+IGlW/4tC6oACOs8B++bh+i9bVyNnwCcuksbFwsBme5OCKXCwIw== + dependencies: + micromark-util-character "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-util-combine-extensions@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-combine-extensions/-/micromark-util-combine-extensions-2.0.0.tgz" + integrity sha512-vZZio48k7ON0fVS3CUgFatWHoKbbLTK/rT7pzpJ4Bjp5JjkZeasRfrS9wsBdDJK2cJLHMckXZdzPSSr1B8a4oQ== + dependencies: + micromark-util-chunked "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-util-decode-numeric-character-reference@^2.0.0: + version "2.0.1" + resolved "https://registry.npmjs.org/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-2.0.1.tgz" + integrity sha512-bmkNc7z8Wn6kgjZmVHOX3SowGmVdhYS7yBpMnuMnPzDq/6xwVA604DuOXMZTO1lvq01g+Adfa0pE2UKGlxL1XQ== + dependencies: + micromark-util-symbol "^2.0.0" + +micromark-util-decode-string@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-decode-string/-/micromark-util-decode-string-2.0.0.tgz" + integrity sha512-r4Sc6leeUTn3P6gk20aFMj2ntPwn6qpDZqWvYmAG6NgvFTIlj4WtrAudLi65qYoaGdXYViXYw2pkmn7QnIFasA== + dependencies: + decode-named-character-reference "^1.0.0" + micromark-util-character "^2.0.0" + micromark-util-decode-numeric-character-reference "^2.0.0" + micromark-util-symbol "^2.0.0" + +micromark-util-encode@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-2.0.0.tgz" + integrity sha512-pS+ROfCXAGLWCOc8egcBvT0kf27GoWMqtdarNfDcjb6YLuV5cM3ioG45Ys2qOVqeqSbjaKg72vU+Wby3eddPsA== + +micromark-util-html-tag-name@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-html-tag-name/-/micromark-util-html-tag-name-2.0.0.tgz" + integrity sha512-xNn4Pqkj2puRhKdKTm8t1YHC/BAjx6CEwRFXntTaRf/x16aqka6ouVoutm+QdkISTlT7e2zU7U4ZdlDLJd2Mcw== + +micromark-util-normalize-identifier@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-2.0.0.tgz" + integrity sha512-2xhYT0sfo85FMrUPtHcPo2rrp1lwbDEEzpx7jiH2xXJLqBuy4H0GgXk5ToU8IEwoROtXuL8ND0ttVa4rNqYK3w== + dependencies: + micromark-util-symbol "^2.0.0" + +micromark-util-resolve-all@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-resolve-all/-/micromark-util-resolve-all-2.0.0.tgz" + integrity sha512-6KU6qO7DZ7GJkaCgwBNtplXCvGkJToU86ybBAUdavvgsCiG8lSSvYxr9MhwmQ+udpzywHsl4RpGJsYWG1pDOcA== + dependencies: + micromark-util-types "^2.0.0" + +micromark-util-sanitize-uri@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-2.0.0.tgz" + integrity sha512-WhYv5UEcZrbAtlsnPuChHUAsu/iBPOVaEVsntLBIdpibO0ddy8OzavZz3iL2xVvBZOpolujSliP65Kq0/7KIYw== + dependencies: + micromark-util-character "^2.0.0" + micromark-util-encode "^2.0.0" + micromark-util-symbol "^2.0.0" + +micromark-util-subtokenize@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-subtokenize/-/micromark-util-subtokenize-2.0.0.tgz" + integrity sha512-vc93L1t+gpR3p8jxeVdaYlbV2jTYteDje19rNSS/H5dlhxUYll5Fy6vJ2cDwP8RnsXi818yGty1ayP55y3W6fg== + dependencies: + devlop "^1.0.0" + micromark-util-chunked "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-util-symbol@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz" + integrity sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw== + +micromark-util-types@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-2.0.0.tgz" + integrity sha512-oNh6S2WMHWRZrmutsRmDDfkzKtxF+bc2VxLC9dvtrDIRFln627VsFP6fLMgTryGDljgLPjkrzQSDcPrjPyDJ5w== + +micromark@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/micromark/-/micromark-4.0.0.tgz" + integrity sha512-o/sd0nMof8kYff+TqcDx3VSrgBTcZpSvYcAHIfHhv5VAuNmisCxjhx6YmxS8PFEpb9z5WKWKPdzf0jM23ro3RQ== + dependencies: + "@types/debug" "^4.0.0" + debug "^4.0.0" + decode-named-character-reference "^1.0.0" + devlop "^1.0.0" + micromark-core-commonmark "^2.0.0" + micromark-factory-space "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-chunked "^2.0.0" + micromark-util-combine-extensions "^2.0.0" + micromark-util-decode-numeric-character-reference "^2.0.0" + micromark-util-encode "^2.0.0" + micromark-util-normalize-identifier "^2.0.0" + micromark-util-resolve-all "^2.0.0" + micromark-util-sanitize-uri "^2.0.0" + micromark-util-subtokenize "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromatch@^4.0.4: + version "4.0.5" + resolved "https://registry.npmjs.org/micromatch/-/micromatch-4.0.5.tgz" + integrity sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA== + dependencies: + braces "^3.0.2" + picomatch "^2.3.1" + +mime-db@1.52.0: + version "1.52.0" + resolved "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz" + integrity sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg== + +mime-types@^2.1.12: + version "2.1.35" + resolved "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz" + integrity sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw== + dependencies: + mime-db "1.52.0" + +minimatch@^3.0.5: + version "3.1.2" + resolved "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz" + integrity sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw== + dependencies: + brace-expansion "^1.1.7" + +minimatch@^3.1.1: + version "3.1.2" + resolved "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz" + integrity sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw== + dependencies: + brace-expansion "^1.1.7" + +minimatch@^3.1.2: + version "3.1.2" + resolved "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz" + integrity sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw== + dependencies: + brace-expansion "^1.1.7" + +minimatch@^9.0.3, minimatch@^9.0.4: + version "9.0.4" + resolved "https://registry.npmjs.org/minimatch/-/minimatch-9.0.4.tgz" + integrity sha512-KqWh+VchfxcMNRAJjj2tnsSJdNbHsVgnkBhTNrW7AjVo6OvLtxw8zfT9oLw1JSohlFzJ8jCoTgaoXvJ+kHt6fw== + dependencies: + brace-expansion "^2.0.1" + +minimist@^1.2.0, minimist@^1.2.6, minimist@^1.2.8: + version "1.2.8" + resolved "https://registry.npmjs.org/minimist/-/minimist-1.2.8.tgz" + integrity sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA== + +ms@^2.1.1, ms@2.1.2: + version "2.1.2" + resolved "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz" + integrity sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w== + +mui-one-time-password-input@^2.0.2: + version "2.0.2" + resolved "https://registry.npmjs.org/mui-one-time-password-input/-/mui-one-time-password-input-2.0.2.tgz" + integrity sha512-KALEh0fIxMOioGU5xUYBZ4bCoUE6/apERw0xo62JdHjnd6VM0Dux70LsMDUeQ4aHtvOMZV3o9tH21wIrPjucug== + dependencies: + "@emotion/react" "^11.11.3" + "@emotion/styled" "^11.11.0" + "@mui/material" "^5.15.10" + "@types/react" "^18.2.55" + react "^18.2.0" + react-dom "^18.2.0" + +murmurhash-js@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/murmurhash-js/-/murmurhash-js-1.0.0.tgz" + integrity sha512-TvmkNhkv8yct0SVBSy+o8wYzXjE4Zz3PCesbfs8HiCXXdcTuocApFv11UWlNFWKYsP2okqrhb7JNlSm9InBhIw== + +nanoid@^3.3.6: + version "3.3.7" + resolved "https://registry.npmjs.org/nanoid/-/nanoid-3.3.7.tgz" + integrity sha512-eSRppjcPIatRIMC1U6UngP8XFcz8MQWGQdt1MTBQ7NaAmvXDfvNxbvWV3x2y6CdEUciCSsDHDQZbhYaB8QEo2g== + +natural-compare-lite@^1.4.0: + version "1.4.0" + resolved "https://registry.npmjs.org/natural-compare-lite/-/natural-compare-lite-1.4.0.tgz" + integrity sha512-Tj+HTDSJJKaZnfiuw+iaF9skdPpTo2GtEly5JHnWV/hfv2Qj/9RKsGISQtLh2ox3l5EAGw487hnBee0sIJ6v2g== + +natural-compare@^1.4.0: + version "1.4.0" + resolved "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz" + integrity sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw== + +"next@^13.0.0 || ^14.0.0", next@^14.2.4: + version "14.2.4" + resolved "https://registry.npmjs.org/next/-/next-14.2.4.tgz" + integrity sha512-R8/V7vugY+822rsQGQCjoLhMuC9oFj9SOi4Cl4b2wjDrseD0LRZ10W7R6Czo4w9ZznVSshKjuIomsRjvm9EKJQ== + dependencies: + "@next/env" "14.2.4" + "@swc/helpers" "0.5.5" + busboy "1.6.0" + caniuse-lite "^1.0.30001579" + graceful-fs "^4.2.11" + postcss "8.4.31" + styled-jsx "5.1.1" + optionalDependencies: + "@next/swc-darwin-arm64" "14.2.4" + "@next/swc-darwin-x64" "14.2.4" + "@next/swc-linux-arm64-gnu" "14.2.4" + "@next/swc-linux-arm64-musl" "14.2.4" + "@next/swc-linux-x64-gnu" "14.2.4" + "@next/swc-linux-x64-musl" "14.2.4" + "@next/swc-win32-arm64-msvc" "14.2.4" + "@next/swc-win32-ia32-msvc" "14.2.4" + "@next/swc-win32-x64-msvc" "14.2.4" + +no-case@^3.0.4: + version "3.0.4" + resolved "https://registry.npmjs.org/no-case/-/no-case-3.0.4.tgz" + integrity sha512-fgAN3jGAh+RoxUGZHTSOLJIqUc2wmoBwGR4tbpNAKmmovFoWq0OdRkb0VkldReO2a2iBT/OEulG9XSUc10r3zg== + dependencies: + lower-case "^2.0.2" + tslib "^2.0.3" + +node-fetch@^2.6.12: + version "2.7.0" + resolved "https://registry.npmjs.org/node-fetch/-/node-fetch-2.7.0.tgz" + integrity sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A== + dependencies: + whatwg-url "^5.0.0" + +node-releases@^2.0.13: + version "2.0.13" + resolved "https://registry.npmjs.org/node-releases/-/node-releases-2.0.13.tgz" + integrity sha512-uYr7J37ae/ORWdZeQ1xxMJe3NtdmqMC/JZK+geofDrkLUApKRHPd18/TxtBOJ4A0/+uUIliorNrfYV6s1b02eQ== + +normalize-svg-path@^1.1.0: + version "1.1.0" + resolved "https://registry.npmjs.org/normalize-svg-path/-/normalize-svg-path-1.1.0.tgz" + integrity sha512-r9KHKG2UUeB5LoTouwDzBy2VxXlHsiM6fyLQvnJa0S5hrhzqElH/CH7TUGhT1fVvIYBIKf3OpY4YJ4CK+iaqHg== + dependencies: + svg-arc-to-cubic-bezier "^3.0.0" + +nprogress@^0.2.0: + version "0.2.0" + resolved "https://registry.npmjs.org/nprogress/-/nprogress-0.2.0.tgz" + integrity sha512-I19aIingLgR1fmhftnbWWO3dXc0hSxqHQHQb3H8m+K3TnEn/iSeTZZOyvKXWqQESMwuUVnatlCnZdLBZZt2VSA== + +nth-check@^2.0.1: + version "2.1.1" + resolved "https://registry.npmjs.org/nth-check/-/nth-check-2.1.1.tgz" + integrity sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w== + dependencies: + boolbase "^1.0.0" + +object-assign@^4.1.1: + version "4.1.1" + resolved "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz" + integrity sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg== + +object-inspect@^1.13.1: + version "1.13.1" + resolved "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.1.tgz" + integrity sha512-5qoj1RUiKOMsCCNLV1CBiPYE10sziTsnmNxkAI/rZhiD63CF7IqdFGC/XzjWjpSgLf0LxXX3bDFIh0E18f6UhQ== + +object-keys@^1.1.1: + version "1.1.1" + resolved "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz" + integrity sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA== + +object.assign@^4.1.2, object.assign@^4.1.4, object.assign@^4.1.5: + version "4.1.5" + resolved "https://registry.npmjs.org/object.assign/-/object.assign-4.1.5.tgz" + integrity sha512-byy+U7gp+FVwmyzKPYhW2h5l3crpmGsxl7X2s8y43IgxvG4g3QZ6CffDtsNQy1WsmZpQbO+ybo0AlW7TY6DcBQ== + dependencies: + call-bind "^1.0.5" + define-properties "^1.2.1" + has-symbols "^1.0.3" + object-keys "^1.1.1" + +object.entries@^1.1.5, object.entries@^1.1.7, object.entries@^1.1.8: + version "1.1.8" + resolved "https://registry.npmjs.org/object.entries/-/object.entries-1.1.8.tgz" + integrity sha512-cmopxi8VwRIAw/fkijJohSfpef5PdN0pMQJN6VC/ZKvn0LIknWD8KtgY6KlQdEc4tIjcQ3HxSMmnvtzIscdaYQ== + dependencies: + call-bind "^1.0.7" + define-properties "^1.2.1" + es-object-atoms "^1.0.0" + +object.fromentries@^2.0.7, object.fromentries@^2.0.8: + version "2.0.8" + resolved "https://registry.npmjs.org/object.fromentries/-/object.fromentries-2.0.8.tgz" + integrity sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ== + dependencies: + call-bind "^1.0.7" + define-properties "^1.2.1" + es-abstract "^1.23.2" + es-object-atoms "^1.0.0" + +object.groupby@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/object.groupby/-/object.groupby-1.0.1.tgz" + integrity sha512-HqaQtqLnp/8Bn4GL16cj+CUYbnpe1bh0TtEaWvybszDG4tgxCJuRpV8VGuvNaI1fAnI4lUJzDG55MXcOH4JZcQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + get-intrinsic "^1.2.1" + +object.hasown@^1.1.4: + version "1.1.4" + resolved "https://registry.npmjs.org/object.hasown/-/object.hasown-1.1.4.tgz" + integrity sha512-FZ9LZt9/RHzGySlBARE3VF+gE26TxR38SdmqOqliuTnl9wrKulaQs+4dee1V+Io8VfxqzAfHu6YuRgUy8OHoTg== + dependencies: + define-properties "^1.2.1" + es-abstract "^1.23.2" + es-object-atoms "^1.0.0" + +object.values@^1.1.6, object.values@^1.1.7, object.values@^1.2.0: + version "1.2.0" + resolved "https://registry.npmjs.org/object.values/-/object.values-1.2.0.tgz" + integrity sha512-yBYjY9QX2hnRmZHAjG/f13MzmBzxzYgQhFrke06TTyKY5zSTEqkOeukBzIdVA3j3ulu8Qa3MbVFShV7T2RmGtQ== + dependencies: + call-bind "^1.0.7" + define-properties "^1.2.1" + es-object-atoms "^1.0.0" + +once@^1.3.0: + version "1.4.0" + resolved "https://registry.npmjs.org/once/-/once-1.4.0.tgz" + integrity sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w== + dependencies: + wrappy "1" + +optionator@^0.9.3: + version "0.9.3" + resolved "https://registry.npmjs.org/optionator/-/optionator-0.9.3.tgz" + integrity sha512-JjCoypp+jKn1ttEFExxhetCKeJt9zhAgAve5FXHixTvFDW/5aEktX9bufBKLRRMdU7bNtpLfcGu94B3cdEJgjg== + dependencies: + "@aashutoshrathi/word-wrap" "^1.2.3" + deep-is "^0.1.3" + fast-levenshtein "^2.0.6" + levn "^0.4.1" + prelude-ls "^1.2.1" + type-check "^0.4.0" + +orderedmap@^2.0.0: + version "2.1.1" + resolved "https://registry.npmjs.org/orderedmap/-/orderedmap-2.1.1.tgz" + integrity sha512-TvAWxi0nDe1j/rtMcWcIj94+Ffe6n7zhow33h40SKxmsmozs6dz/e+EajymfoFcHd7sxNn8yHM8839uixMOV6g== + +p-limit@^3.0.2: + version "3.1.0" + resolved "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz" + integrity sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ== + dependencies: + yocto-queue "^0.1.0" + +p-locate@^5.0.0: + version "5.0.0" + resolved "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz" + integrity sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw== + dependencies: + p-limit "^3.0.2" + +pako@^0.2.5: + version "0.2.9" + resolved "https://registry.npmjs.org/pako/-/pako-0.2.9.tgz" + integrity sha512-NUcwaKxUxWrZLpDG+z/xZaCgQITkA/Dv4V/T6bw7VON6l1Xz/VnrBqrYjZQ12TamKHzITTfOEIYUj48y2KXImA== + +pako@~1.0.5: + version "1.0.11" + resolved "https://registry.npmjs.org/pako/-/pako-1.0.11.tgz" + integrity sha512-4hLB8Py4zZce5s4yd9XzopqwVv/yGNhV1Bl8NTmCq1763HeK2+EwVTv+leGeL13Dnh2wfbqowVPXCIO0z4taYw== + +parent-module@^1.0.0: + version "1.0.1" + resolved "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz" + integrity sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g== + dependencies: + callsites "^3.0.0" + +parse-json@^5.0.0, parse-json@^5.2.0: + version "5.2.0" + resolved "https://registry.npmjs.org/parse-json/-/parse-json-5.2.0.tgz" + integrity sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg== + dependencies: + "@babel/code-frame" "^7.0.0" + error-ex "^1.3.1" + json-parse-even-better-errors "^2.3.0" + lines-and-columns "^1.1.6" + +parse-svg-path@^0.1.2: + version "0.1.2" + resolved "https://registry.npmjs.org/parse-svg-path/-/parse-svg-path-0.1.2.tgz" + integrity sha512-JyPSBnkTJ0AI8GGJLfMXvKq42cj5c006fnLz6fXy6zfoVjJizi8BNTpu8on8ziI1cKy9d9DGNuY17Ce7wuejpQ== + +parse5@^7.0.0: + version "7.1.2" + resolved "https://registry.npmjs.org/parse5/-/parse5-7.1.2.tgz" + integrity sha512-Czj1WaSVpaoj0wbhMzLmWD69anp2WH7FXMB9n1Sy8/ZFF9jolSQVMu1Ij5WIyGmcBmhk7EOndpO4mIpihVqAXw== + dependencies: + entities "^4.4.0" + +path-exists@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz" + integrity sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w== + +path-is-absolute@^1.0.0: + version "1.0.1" + resolved "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz" + integrity sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg== + +path-key@^3.1.0: + version "3.1.1" + resolved "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz" + integrity sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q== + +path-parse@^1.0.7: + version "1.0.7" + resolved "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz" + integrity sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw== + +path-type@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz" + integrity sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw== + +pbf@^3.2.1: + version "3.2.1" + resolved "https://registry.npmjs.org/pbf/-/pbf-3.2.1.tgz" + integrity sha512-ClrV7pNOn7rtmoQVF4TS1vyU0WhYRnP92fzbfF75jAIwpnzdJXf8iTd4CMEqO4yUenH6NDqLiwjqlh6QgZzgLQ== + dependencies: + ieee754 "^1.1.12" + resolve-protobuf-schema "^2.1.0" + +picocolors@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/picocolors/-/picocolors-1.0.0.tgz" + integrity sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ== + +picomatch@^2.3.1: + version "2.3.1" + resolved "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz" + integrity sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA== + +popper.js@^1.16.0: + version "1.16.1" + resolved "https://registry.npmjs.org/popper.js/-/popper.js-1.16.1.tgz" + integrity sha512-Wb4p1J4zyFTbM+u6WuO4XstYx4Ky9Cewe4DWrel7B0w6VVICvPwdOpotjzcf6eD8TsckVnIMNONQyPIUFOUbCQ== + +possible-typed-array-names@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/possible-typed-array-names/-/possible-typed-array-names-1.0.0.tgz" + integrity sha512-d7Uw+eZoloe0EHDIYoe+bQ5WXnGMOpmiZFTuMWCwpjzzkL2nTjcKiAk4hh8TjnGye2TwWOk3UXucZ+3rbmBa8Q== + +postcss-value-parser@^4.1.0: + version "4.2.0" + resolved "https://registry.npmjs.org/postcss-value-parser/-/postcss-value-parser-4.2.0.tgz" + integrity sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ== + +postcss@8.4.31: + version "8.4.31" + resolved "https://registry.npmjs.org/postcss/-/postcss-8.4.31.tgz" + integrity sha512-PS08Iboia9mts/2ygV3eLpY5ghnUcfLV/EXTOW1E2qYxJKGGBUtNjN76FYHnMs36RmARn41bC0AZmn+rR0OVpQ== + dependencies: + nanoid "^3.3.6" + picocolors "^1.0.0" + source-map-js "^1.0.2" + +potpack@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/potpack/-/potpack-2.0.0.tgz" + integrity sha512-Q+/tYsFU9r7xoOJ+y/ZTtdVQwTWfzjbiXBDMM/JKUux3+QPP02iUuIoeBQ+Ot6oEDlC+/PGjB/5A3K7KKb7hcw== + +preact@~10.12.1: + version "10.12.1" + resolved "https://registry.npmjs.org/preact/-/preact-10.12.1.tgz" + integrity sha512-l8386ixSsBdbreOAkqtrwqHwdvR35ID8c3rKPa8lCWuO86dBi32QWHV4vfsZK1utLLFMvw+Z5Ad4XLkZzchscg== + +prelude-ls@^1.2.1: + version "1.2.1" + resolved "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz" + integrity sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g== + +prettier-linter-helpers@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/prettier-linter-helpers/-/prettier-linter-helpers-1.0.0.tgz" + integrity sha512-GbK2cP9nraSSUF9N2XwUwqfzlAFlMNYYl+ShE/V+H8a9uNl/oUqB1w2EL54Jh0OlyRSd8RfWYJ3coVS4TROP2w== + dependencies: + fast-diff "^1.1.2" + +prettier@^3.3.2, prettier@>=3.0.0: + version "3.3.2" + resolved "https://registry.npmjs.org/prettier/-/prettier-3.3.2.tgz" + integrity sha512-rAVeHYMcv8ATV5d508CFdn+8/pHPpXeIid1DdrPwXnaAdH7cqjVbpJaT5eq4yRAFU/lsbwYwSF/n5iNrdJHPQA== + +prop-types@^15.6.2, prop-types@^15.8.1: + version "15.8.1" + resolved "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz" + integrity sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg== + dependencies: + loose-envify "^1.4.0" + object-assign "^4.1.1" + react-is "^16.13.1" + +property-information@^6.0.0: + version "6.4.0" + resolved "https://registry.npmjs.org/property-information/-/property-information-6.4.0.tgz" + integrity sha512-9t5qARVofg2xQqKtytzt+lZ4d1Qvj8t5B8fEwXK6qOfgRLgH/b13QlgEyDh033NOS31nXeFbYv7CLUDG1CeifQ== + +prosemirror-changeset@^2.2.1: + version "2.2.1" + resolved "https://registry.npmjs.org/prosemirror-changeset/-/prosemirror-changeset-2.2.1.tgz" + integrity sha512-J7msc6wbxB4ekDFj+n9gTW/jav/p53kdlivvuppHsrZXCaQdVgRghoZbSS3kwrRyAstRVQ4/+u5k7YfLgkkQvQ== + dependencies: + prosemirror-transform "^1.0.0" + +prosemirror-collab@^1.3.1: + version "1.3.1" + resolved "https://registry.npmjs.org/prosemirror-collab/-/prosemirror-collab-1.3.1.tgz" + integrity sha512-4SnynYR9TTYaQVXd/ieUvsVV4PDMBzrq2xPUWutHivDuOshZXqQ5rGbZM84HEaXKbLdItse7weMGOUdDVcLKEQ== + dependencies: + prosemirror-state "^1.0.0" + +prosemirror-commands@^1.0.0, prosemirror-commands@^1.5.2: + version "1.5.2" + resolved "https://registry.npmjs.org/prosemirror-commands/-/prosemirror-commands-1.5.2.tgz" + integrity sha512-hgLcPaakxH8tu6YvVAaILV2tXYsW3rAdDR8WNkeKGcgeMVQg3/TMhPdVoh7iAmfgVjZGtcOSjKiQaoeKjzd2mQ== + dependencies: + prosemirror-model "^1.0.0" + prosemirror-state "^1.0.0" + prosemirror-transform "^1.0.0" + +prosemirror-dropcursor@^1.8.1: + version "1.8.1" + resolved "https://registry.npmjs.org/prosemirror-dropcursor/-/prosemirror-dropcursor-1.8.1.tgz" + integrity sha512-M30WJdJZLyXHi3N8vxN6Zh5O8ZBbQCz0gURTfPmTIBNQ5pxrdU7A58QkNqfa98YEjSAL1HUyyU34f6Pm5xBSGw== + dependencies: + prosemirror-state "^1.0.0" + prosemirror-transform "^1.1.0" + prosemirror-view "^1.1.0" + +prosemirror-gapcursor@^1.3.2: + version "1.3.2" + resolved "https://registry.npmjs.org/prosemirror-gapcursor/-/prosemirror-gapcursor-1.3.2.tgz" + integrity sha512-wtjswVBd2vaQRrnYZaBCbyDqr232Ed4p2QPtRIUK5FuqHYKGWkEwl08oQM4Tw7DOR0FsasARV5uJFvMZWxdNxQ== + dependencies: + prosemirror-keymap "^1.0.0" + prosemirror-model "^1.0.0" + prosemirror-state "^1.0.0" + prosemirror-view "^1.0.0" + +prosemirror-history@^1.0.0, prosemirror-history@^1.3.2: + version "1.4.0" + resolved "https://registry.npmjs.org/prosemirror-history/-/prosemirror-history-1.4.0.tgz" + integrity sha512-UUiGzDVcqo1lovOPdi9YxxUps3oBFWAIYkXLu3Ot+JPv1qzVogRbcizxK3LhHmtaUxclohgiOVesRw5QSlMnbQ== + dependencies: + prosemirror-state "^1.2.2" + prosemirror-transform "^1.0.0" + prosemirror-view "^1.31.0" + rope-sequence "^1.3.0" + +prosemirror-inputrules@^1.3.0: + version "1.4.0" + resolved "https://registry.npmjs.org/prosemirror-inputrules/-/prosemirror-inputrules-1.4.0.tgz" + integrity sha512-6ygpPRuTJ2lcOXs9JkefieMst63wVJBgHZGl5QOytN7oSZs3Co/BYbc3Yx9zm9H37Bxw8kVzCnDsihsVsL4yEg== + dependencies: + prosemirror-state "^1.0.0" + prosemirror-transform "^1.0.0" + +prosemirror-keymap@^1.0.0, prosemirror-keymap@^1.1.2, prosemirror-keymap@^1.2.2: + version "1.2.2" + resolved "https://registry.npmjs.org/prosemirror-keymap/-/prosemirror-keymap-1.2.2.tgz" + integrity sha512-EAlXoksqC6Vbocqc0GtzCruZEzYgrn+iiGnNjsJsH4mrnIGex4qbLdWWNza3AW5W36ZRrlBID0eM6bdKH4OStQ== + dependencies: + prosemirror-state "^1.0.0" + w3c-keyname "^2.2.0" + +prosemirror-markdown@^1.12.0: + version "1.12.0" + resolved "https://registry.npmjs.org/prosemirror-markdown/-/prosemirror-markdown-1.12.0.tgz" + integrity sha512-6F5HS8Z0HDYiS2VQDZzfZP6A0s/I0gbkJy8NCzzDMtcsz3qrfqyroMMeoSjAmOhDITyon11NbXSzztfKi+frSQ== + dependencies: + markdown-it "^14.0.0" + prosemirror-model "^1.0.0" + +prosemirror-menu@^1.2.4: + version "1.2.4" + resolved "https://registry.npmjs.org/prosemirror-menu/-/prosemirror-menu-1.2.4.tgz" + integrity sha512-S/bXlc0ODQup6aiBbWVsX/eM+xJgCTAfMq/nLqaO5ID/am4wS0tTCIkzwytmao7ypEtjj39i7YbJjAgO20mIqA== + dependencies: + crelt "^1.0.0" + prosemirror-commands "^1.0.0" + prosemirror-history "^1.0.0" + prosemirror-state "^1.0.0" + +prosemirror-model@^1.0.0, prosemirror-model@^1.19.0, prosemirror-model@^1.19.4, prosemirror-model@^1.20.0, prosemirror-model@^1.8.1: + version "1.20.0" + resolved "https://registry.npmjs.org/prosemirror-model/-/prosemirror-model-1.20.0.tgz" + integrity sha512-q7AY7vMjKYqDCeoedgUiAgrLabliXxndJuuFmcmc2+YU1SblvnOiG2WEACF2lwAZsMlfLpiAilA3L+TWlDqIsQ== + dependencies: + orderedmap "^2.0.0" + +prosemirror-schema-basic@^1.2.2: + version "1.2.2" + resolved "https://registry.npmjs.org/prosemirror-schema-basic/-/prosemirror-schema-basic-1.2.2.tgz" + integrity sha512-/dT4JFEGyO7QnNTe9UaKUhjDXbTNkiWTq/N4VpKaF79bBjSExVV2NXmJpcM7z/gD7mbqNjxbmWW5nf1iNSSGnw== + dependencies: + prosemirror-model "^1.19.0" + +prosemirror-schema-list@^1.3.0: + version "1.3.0" + resolved "https://registry.npmjs.org/prosemirror-schema-list/-/prosemirror-schema-list-1.3.0.tgz" + integrity sha512-Hz/7gM4skaaYfRPNgr421CU4GSwotmEwBVvJh5ltGiffUJwm7C8GfN/Bc6DR1EKEp5pDKhODmdXXyi9uIsZl5A== + dependencies: + prosemirror-model "^1.0.0" + prosemirror-state "^1.0.0" + prosemirror-transform "^1.7.3" + +prosemirror-state@^1.0.0, prosemirror-state@^1.2.2, prosemirror-state@^1.3.1, prosemirror-state@^1.4.2, prosemirror-state@^1.4.3: + version "1.4.3" + resolved "https://registry.npmjs.org/prosemirror-state/-/prosemirror-state-1.4.3.tgz" + integrity sha512-goFKORVbvPuAQaXhpbemJFRKJ2aixr+AZMGiquiqKxaucC6hlpHNZHWgz5R7dS4roHiwq9vDctE//CZ++o0W1Q== + dependencies: + prosemirror-model "^1.0.0" + prosemirror-transform "^1.0.0" + prosemirror-view "^1.27.0" + +prosemirror-tables@^1.3.5: + version "1.3.7" + resolved "https://registry.npmjs.org/prosemirror-tables/-/prosemirror-tables-1.3.7.tgz" + integrity sha512-oEwX1wrziuxMtwFvdDWSFHVUWrFJWt929kVVfHvtTi8yvw+5ppxjXZkMG/fuTdFo+3DXyIPSKfid+Be1npKXDA== + dependencies: + prosemirror-keymap "^1.1.2" + prosemirror-model "^1.8.1" + prosemirror-state "^1.3.1" + prosemirror-transform "^1.2.1" + prosemirror-view "^1.13.3" + +prosemirror-trailing-node@^2.0.7: + version "2.0.8" + resolved "https://registry.npmjs.org/prosemirror-trailing-node/-/prosemirror-trailing-node-2.0.8.tgz" + integrity sha512-ujRYhSuhQb1Jsarh1IHqb2KoSnRiD7wAMDGucP35DN7j5af6X7B18PfdPIrbwsPTqIAj0fyOvxbuPsWhNvylmA== + dependencies: + "@remirror/core-constants" "^2.0.2" + escape-string-regexp "^4.0.0" + +prosemirror-transform@^1.0.0, prosemirror-transform@^1.1.0, prosemirror-transform@^1.2.1, prosemirror-transform@^1.7.3, prosemirror-transform@^1.8.0: + version "1.8.0" + resolved "https://registry.npmjs.org/prosemirror-transform/-/prosemirror-transform-1.8.0.tgz" + integrity sha512-BaSBsIMv52F1BVVMvOmp1yzD3u65uC3HTzCBQV1WDPqJRQ2LuHKcyfn0jwqodo8sR9vVzMzZyI+Dal5W9E6a9A== + dependencies: + prosemirror-model "^1.0.0" + +prosemirror-view@^1.0.0, prosemirror-view@^1.1.0, prosemirror-view@^1.13.3, prosemirror-view@^1.27.0, prosemirror-view@^1.31.0, prosemirror-view@^1.31.2, prosemirror-view@^1.32.7: + version "1.33.4" + resolved "https://registry.npmjs.org/prosemirror-view/-/prosemirror-view-1.33.4.tgz" + integrity sha512-xQqAhH8/HGleVpKDhQsrd+oqdyeKMxFtdCWDxWMmP+n0k27fBpyUqa8pA+RB5cFY8rqDDc1hll69aRZQa7UaAw== + dependencies: + prosemirror-model "^1.20.0" + prosemirror-state "^1.0.0" + prosemirror-transform "^1.1.0" + +protobufjs@^7.2.5: + version "7.3.0" + resolved "https://registry.npmjs.org/protobufjs/-/protobufjs-7.3.0.tgz" + integrity sha512-YWD03n3shzV9ImZRX3ccbjqLxj7NokGN0V/ESiBV5xWqrommYHYiihuIyavq03pWSGqlyvYUFmfoMKd+1rPA/g== + dependencies: + "@protobufjs/aspromise" "^1.1.2" + "@protobufjs/base64" "^1.1.2" + "@protobufjs/codegen" "^2.0.4" + "@protobufjs/eventemitter" "^1.1.0" + "@protobufjs/fetch" "^1.1.0" + "@protobufjs/float" "^1.0.2" + "@protobufjs/inquire" "^1.1.0" + "@protobufjs/path" "^1.1.2" + "@protobufjs/pool" "^1.1.0" + "@protobufjs/utf8" "^1.1.0" + "@types/node" ">=13.7.0" + long "^5.0.0" + +protocol-buffers-schema@^3.3.1: + version "3.6.0" + resolved "https://registry.npmjs.org/protocol-buffers-schema/-/protocol-buffers-schema-3.6.0.tgz" + integrity sha512-TdDRD+/QNdrCGCE7v8340QyuXd4kIWIgapsE2+n/SaGiSSbomYl4TjHlvIoCWRpE7wFt02EpB35VVA2ImcBVqw== + +proxy-from-env@^1.1.0: + version "1.1.0" + resolved "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz" + integrity sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg== + +punycode.js@^2.3.1: + version "2.3.1" + resolved "https://registry.npmjs.org/punycode.js/-/punycode.js-2.3.1.tgz" + integrity sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA== + +punycode@^2.1.0: + version "2.3.1" + resolved "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz" + integrity sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg== + +queue-microtask@^1.2.2: + version "1.2.3" + resolved "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz" + integrity sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A== + +queue@^6.0.1: + version "6.0.2" + resolved "https://registry.npmjs.org/queue/-/queue-6.0.2.tgz" + integrity sha512-iHZWu+q3IdFZFX36ro/lKBkSvfkztY5Y7HMiPlOUjhupPcG2JMfst2KKEpu5XndviX/3UhFbRngUPNKtgvtZiA== + dependencies: + inherits "~2.0.3" + +quickselect@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/quickselect/-/quickselect-2.0.0.tgz" + integrity sha512-RKJ22hX8mHe3Y6wH/N3wCM6BWtjaxIyyUIkpHOvfFnxdI4yD4tBXEBKSbriGujF6jnSVkJrffuo6vxACiSSxIw== + +react-apexcharts@^1.4.1: + version "1.4.1" + resolved "https://registry.npmjs.org/react-apexcharts/-/react-apexcharts-1.4.1.tgz" + integrity sha512-G14nVaD64Bnbgy8tYxkjuXEUp/7h30Q0U33xc3AwtGFijJB9nHqOt1a6eG0WBn055RgRg+NwqbKGtqPxy15d0Q== + dependencies: + prop-types "^15.8.1" + +"react-dom@^15.x.x || ^16.x.x || ^17.x.x || ^18.x.x", "react-dom@^16.11.0 || ^17 || ^18", "react-dom@^16.7.0 || ^17 || ^18 || ^19", "react-dom@^17.0.0 || ^18.0.0", react-dom@^18.0.0, react-dom@^18.2.0, react-dom@^18.3.1, "react-dom@>= 16.12.0", react-dom@>=16.3.0, react-dom@>=16.6.0, react-dom@>=16.8, react-dom@>=16.8.0, "react-dom@15 - 18": + version "18.3.1" + resolved "https://registry.npmjs.org/react-dom/-/react-dom-18.3.1.tgz" + integrity sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw== + dependencies: + loose-envify "^1.1.0" + scheduler "^0.23.2" + +react-dropzone@^14.2.3: + version "14.2.3" + resolved "https://registry.npmjs.org/react-dropzone/-/react-dropzone-14.2.3.tgz" + integrity sha512-O3om8I+PkFKbxCukfIR3QAGftYXDZfOE2N1mr/7qebQJHs7U+/RSL/9xomJNpRg9kM5h9soQSdf0Gc7OHF5Fug== + dependencies: + attr-accept "^2.2.2" + file-selector "^0.6.0" + prop-types "^15.8.1" + +react-floater@^0.7.9: + version "0.7.9" + resolved "https://registry.npmjs.org/react-floater/-/react-floater-0.7.9.tgz" + integrity sha512-NXqyp9o8FAXOATOEo0ZpyaQ2KPb4cmPMXGWkx377QtJkIXHlHRAGer7ai0r0C1kG5gf+KJ6Gy+gdNIiosvSicg== + dependencies: + deepmerge "^4.3.1" + is-lite "^0.8.2" + popper.js "^1.16.0" + prop-types "^15.8.1" + tree-changes "^0.9.1" + +react-hook-form@^7.0.0, react-hook-form@^7.51.5: + version "7.51.5" + resolved "https://registry.npmjs.org/react-hook-form/-/react-hook-form-7.51.5.tgz" + integrity sha512-J2ILT5gWx1XUIJRETiA7M19iXHlG74+6O3KApzvqB/w8S5NQR7AbU8HVZrMALdmDgWpRPYiZJl0zx8Z4L2mP6Q== + +react-i18next@^14.1.2: + version "14.1.2" + resolved "https://registry.npmjs.org/react-i18next/-/react-i18next-14.1.2.tgz" + integrity sha512-FSIcJy6oauJbGEXfhUgVeLzvWBhIBIS+/9c6Lj4niwKZyGaGb4V4vUbATXSlsHJDXXB+ociNxqFNiFuV1gmoqg== + dependencies: + "@babel/runtime" "^7.23.9" + html-parse-stringify "^3.0.1" + +react-innertext@^1.1.5: + version "1.1.5" + resolved "https://registry.npmjs.org/react-innertext/-/react-innertext-1.1.5.tgz" + integrity sha512-PWAqdqhxhHIv80dT9znP2KvS+hfkbRovFp4zFYHFFlOoQLRiawIic81gKb3U1wEyJZgMwgs3JoLtwryASRWP3Q== + +react-is@^16.13.1: + version "16.13.1" + resolved "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz" + integrity sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ== + +react-is@^16.7.0: + version "16.13.1" + resolved "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz" + integrity sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ== + +react-is@^18.2.0: + version "18.2.0" + resolved "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz" + integrity sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w== + +react-joyride@^2.8.2: + version "2.8.2" + resolved "https://registry.npmjs.org/react-joyride/-/react-joyride-2.8.2.tgz" + integrity sha512-2QY8HB1G0I2OT0PKMUz7gg2HAjdkG2Bqi13r0Bb1V16PAwfb9khn4wWBTOJsGsjulbAWiQ3/0YrgNUHGFmuifw== + dependencies: + "@gilbarbara/deep-equal" "^0.3.1" + deep-diff "^1.0.2" + deepmerge "^4.3.1" + is-lite "^1.2.1" + react-floater "^0.7.9" + react-innertext "^1.1.5" + react-is "^16.13.1" + scroll "^3.0.1" + scrollparent "^2.1.0" + tree-changes "^0.11.2" + type-fest "^4.18.2" + +react-lazy-load-image-component@^1.6.0: + version "1.6.0" + resolved "https://registry.npmjs.org/react-lazy-load-image-component/-/react-lazy-load-image-component-1.6.0.tgz" + integrity sha512-8KFkDTgjh+0+PVbH+cx0AgxLGbdTsxWMnxXzU5HEUztqewk9ufQAu8cstjZhyvtMIPsdMcPZfA0WAa7HtjQbBQ== + dependencies: + lodash.debounce "^4.0.8" + lodash.throttle "^4.1.1" + +react-map-gl@^7.1.7: + version "7.1.7" + resolved "https://registry.npmjs.org/react-map-gl/-/react-map-gl-7.1.7.tgz" + integrity sha512-mwjc0obkBJOXCcoXQr3VoLqmqwo9vS4bXfbGsdxXzEgVCv/PM0v+1QggL7W0d/ccIy+VCjbXNlGij+PENz6VNg== + dependencies: + "@maplibre/maplibre-gl-style-spec" "^19.2.1" + "@types/mapbox-gl" ">=1.0.0" + +react-markdown@^9.0.1: + version "9.0.1" + resolved "https://registry.npmjs.org/react-markdown/-/react-markdown-9.0.1.tgz" + integrity sha512-186Gw/vF1uRkydbsOIkcGXw7aHq0sZOCRFFjGrr7b9+nVZg4UfA4enXCaxm4fUzecU38sWfrNDitGhshuU7rdg== + dependencies: + "@types/hast" "^3.0.0" + devlop "^1.0.0" + hast-util-to-jsx-runtime "^2.0.0" + html-url-attributes "^3.0.0" + mdast-util-to-hast "^13.0.0" + remark-parse "^11.0.0" + remark-rehype "^11.0.0" + unified "^11.0.0" + unist-util-visit "^5.0.0" + vfile "^6.0.0" + +react-organizational-chart@^2.2.1: + version "2.2.1" + resolved "https://registry.npmjs.org/react-organizational-chart/-/react-organizational-chart-2.2.1.tgz" + integrity sha512-JORmpLeYzCVtztdqCHsnKL8H3WiLRPHjohgh/PxQoszLuaQ+l3F8YefKSfpcBPZJhHwy3SlqjFjPC28a3Hh3QQ== + dependencies: + "@emotion/css" "^11.7.1" + +react-phone-number-input@^3.4.3: + version "3.4.3" + resolved "https://registry.npmjs.org/react-phone-number-input/-/react-phone-number-input-3.4.3.tgz" + integrity sha512-n0dD9V1T8EWeRoGwVMcNK6bwOdEbIk0U3EQ87K0WTADgyJZUJd9NIQMmpcl9mtWSL+LwPaEMzre0yGkhwZYTzg== + dependencies: + classnames "^2.5.1" + country-flag-icons "^1.5.11" + input-format "^0.3.10" + libphonenumber-js "^1.11.2" + prop-types "^15.8.1" + +react-transition-group@^4.4.5: + version "4.4.5" + resolved "https://registry.npmjs.org/react-transition-group/-/react-transition-group-4.4.5.tgz" + integrity sha512-pZcd1MCJoiKiBR2NRxeCRg13uCXbydPnmB4EOeRrY7480qNWO8IIgQG6zlDkm6uRMsURXPuKq0GWtiM59a5Q6g== + dependencies: + "@babel/runtime" "^7.5.5" + dom-helpers "^5.0.1" + loose-envify "^1.4.0" + prop-types "^15.6.2" + +"react@^15.x.x || ^16.x.x || ^17.x.x || ^18.x.x", "react@^16.11.0 || ^17 || ^18", "react@^16.11.0 || ^17.0.0 || ^18.0.0", "react@^16.7.0 || ^17 || ^18 || ^19", "react@^16.8.0 || ^17 || ^18", "react@^16.8.0 || ^17.0.0 || ^18.0.0", "react@^16.8.0 || ^17.0.1 || ^18.0.0", "react@^17.0.0 || ^18.0.0", react@^18.0.0, react@^18.2.0, react@^18.3.1, "react@>= 16.12.0", "react@>= 16.8 || 18.0.0", "react@>= 16.8.0", "react@>= 16.8.0 || 17.x.x || ^18.0.0-0", "react@>=0.0.0 <=99", react@>=0.13, react@>=16, react@>=16.3.0, react@>=16.6.0, react@>=16.8, react@>=16.8.0, react@>=18, "react@15 - 18": + version "18.3.1" + resolved "https://registry.npmjs.org/react/-/react-18.3.1.tgz" + integrity sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ== + dependencies: + loose-envify "^1.1.0" + +reflect.getprototypeof@^1.0.4: + version "1.0.4" + resolved "https://registry.npmjs.org/reflect.getprototypeof/-/reflect.getprototypeof-1.0.4.tgz" + integrity sha512-ECkTw8TmJwW60lOTR+ZkODISW6RQ8+2CL3COqtiJKLd6MmB45hN51HprHFziKLGkAuTGQhBb91V8cy+KHlaCjw== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + get-intrinsic "^1.2.1" + globalthis "^1.0.3" + which-builtin-type "^1.1.3" + +regenerate-unicode-properties@^10.1.0: + version "10.1.1" + resolved "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-10.1.1.tgz" + integrity sha512-X007RyZLsCJVVrjgEFVpLUTZwyOZk3oiL75ZcuYjlIWd6rNJtOjkBwQc5AsRrpbKVkxN6sklw/k/9m2jJYOf8Q== + dependencies: + regenerate "^1.4.2" + +regenerate@^1.4.2: + version "1.4.2" + resolved "https://registry.npmjs.org/regenerate/-/regenerate-1.4.2.tgz" + integrity sha512-zrceR/XhGYU/d/opr2EKO7aRHUeiBI8qjtfHqADTwZd6Szfy16la6kqD0MIUs5z5hx6AaKa+PixpPrR289+I0A== + +regenerator-runtime@^0.14.0: + version "0.14.0" + resolved "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.0.tgz" + integrity sha512-srw17NI0TUWHuGa5CFGGmhfNIeja30WMBfbslPNhf6JrqQlLN5gcrvig1oqPxiVaXb0oW0XRKtH6Nngs5lKCIA== + +regenerator-transform@^0.15.2: + version "0.15.2" + resolved "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.15.2.tgz" + integrity sha512-hfMp2BoF0qOk3uc5V20ALGDS2ddjQaLrdl7xrGXvAIow7qeWRM2VA2HuCHkUKk9slq3VwEwLNK3DFBqDfPGYtg== + dependencies: + "@babel/runtime" "^7.8.4" + +regexp.prototype.flags@^1.5.2: + version "1.5.2" + resolved "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.5.2.tgz" + integrity sha512-NcDiDkTLuPR+++OCKB0nWafEmhg/Da8aUPLPMQbK+bxKKCm1/S5he+AqYa4PlMCVBalb4/yxIRub6qkEx5yJbw== + dependencies: + call-bind "^1.0.6" + define-properties "^1.2.1" + es-errors "^1.3.0" + set-function-name "^2.0.1" + +regexpu-core@^5.3.1: + version "5.3.2" + resolved "https://registry.npmjs.org/regexpu-core/-/regexpu-core-5.3.2.tgz" + integrity sha512-RAM5FlZz+Lhmo7db9L298p2vHP5ZywrVXmVXpmAD9GuL5MPH6t9ROw1iA/wfHkQ76Qe7AaPF0nGuim96/IrQMQ== + dependencies: + "@babel/regjsgen" "^0.8.0" + regenerate "^1.4.2" + regenerate-unicode-properties "^10.1.0" + regjsparser "^0.9.1" + unicode-match-property-ecmascript "^2.0.0" + unicode-match-property-value-ecmascript "^2.1.0" + +regjsparser@^0.9.1: + version "0.9.1" + resolved "https://registry.npmjs.org/regjsparser/-/regjsparser-0.9.1.tgz" + integrity sha512-dQUtn90WanSNl+7mQKcXAgZxvUe7Z0SqXlgzv0za4LwiUhyzBC58yQO3liFoUgu8GiJVInAhJjkj1N0EtQ5nkQ== + dependencies: + jsesc "~0.5.0" + +rehype-highlight@^7.0.0: + version "7.0.0" + resolved "https://registry.npmjs.org/rehype-highlight/-/rehype-highlight-7.0.0.tgz" + integrity sha512-QtobgRgYoQaK6p1eSr2SD1i61f7bjF2kZHAQHxeCHAuJf7ZUDMvQ7owDq9YTkmar5m5TSUol+2D3bp3KfJf/oA== + dependencies: + "@types/hast" "^3.0.0" + hast-util-to-text "^4.0.0" + lowlight "^3.0.0" + unist-util-visit "^5.0.0" + vfile "^6.0.0" + +rehype-raw@^7.0.0: + version "7.0.0" + resolved "https://registry.npmjs.org/rehype-raw/-/rehype-raw-7.0.0.tgz" + integrity sha512-/aE8hCfKlQeA8LmyeyQvQF3eBiLRGNlfBJEvWH7ivp9sBqs7TNqBL5X3v157rM4IFETqDnIOO+z5M/biZbo9Ww== + dependencies: + "@types/hast" "^3.0.0" + hast-util-raw "^9.0.0" + vfile "^6.0.0" + +remark-gfm@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/remark-gfm/-/remark-gfm-4.0.0.tgz" + integrity sha512-U92vJgBPkbw4Zfu/IiW2oTZLSL3Zpv+uI7My2eq8JxKgqraFdU8YUGicEJCEgSbeaG+QDFqIcwwfMTOEelPxuA== + dependencies: + "@types/mdast" "^4.0.0" + mdast-util-gfm "^3.0.0" + micromark-extension-gfm "^3.0.0" + remark-parse "^11.0.0" + remark-stringify "^11.0.0" + unified "^11.0.0" + +remark-parse@^11.0.0: + version "11.0.0" + resolved "https://registry.npmjs.org/remark-parse/-/remark-parse-11.0.0.tgz" + integrity sha512-FCxlKLNGknS5ba/1lmpYijMUzX2esxW5xQqjWxw2eHFfS2MSdaHVINFmhjo+qN1WhZhNimq0dZATN9pH0IDrpA== + dependencies: + "@types/mdast" "^4.0.0" + mdast-util-from-markdown "^2.0.0" + micromark-util-types "^2.0.0" + unified "^11.0.0" + +remark-rehype@^11.0.0: + version "11.0.0" + resolved "https://registry.npmjs.org/remark-rehype/-/remark-rehype-11.0.0.tgz" + integrity sha512-vx8x2MDMcxuE4lBmQ46zYUDfcFMmvg80WYX+UNLeG6ixjdCCLcw1lrgAukwBTuOFsS78eoAedHGn9sNM0w7TPw== + dependencies: + "@types/hast" "^3.0.0" + "@types/mdast" "^4.0.0" + mdast-util-to-hast "^13.0.0" + unified "^11.0.0" + vfile "^6.0.0" + +remark-stringify@^11.0.0: + version "11.0.0" + resolved "https://registry.npmjs.org/remark-stringify/-/remark-stringify-11.0.0.tgz" + integrity sha512-1OSmLd3awB/t8qdoEOMazZkNsfVTeY4fTsgzcQFdXNq8ToTN4ZGwrMnlda4K6smTFKD+GRV6O48i6Z4iKgPPpw== + dependencies: + "@types/mdast" "^4.0.0" + mdast-util-to-markdown "^2.0.0" + unified "^11.0.0" + +remove-accents@^0.4.2: + version "0.4.4" + resolved "https://registry.npmjs.org/remove-accents/-/remove-accents-0.4.4.tgz" + integrity sha512-EpFcOa/ISetVHEXqu+VwI96KZBmq+a8LJnGkaeFw45epGlxIZz5dhEEnNZMsQXgORu3qaMoLX4qJCzOik6ytAg== + +require-directory@^2.1.1: + version "2.1.1" + resolved "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz" + integrity sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q== + +require-from-string@^2.0.2: + version "2.0.2" + resolved "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz" + integrity sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw== + +reselect@^4.1.8: + version "4.1.8" + resolved "https://registry.npmjs.org/reselect/-/reselect-4.1.8.tgz" + integrity sha512-ab9EmR80F/zQTMNeneUr4cv+jSwPJgIlvEmVwLerwrWVbpLlBuls9XHzIeTFy4cegU2NHBp3va0LKOzU5qFEYQ== + +resolve-from@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz" + integrity sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g== + +resolve-protobuf-schema@^2.1.0: + version "2.1.0" + resolved "https://registry.npmjs.org/resolve-protobuf-schema/-/resolve-protobuf-schema-2.1.0.tgz" + integrity sha512-kI5ffTiZWmJaS/huM8wZfEMer1eRd7oJQhDuxeCLe3t7N7mX3z94CN0xPxBQxFYQTSNz9T0i+v6inKqSdK8xrQ== + dependencies: + protocol-buffers-schema "^3.3.1" + +resolve@^1.14.2, resolve@^1.19.0, resolve@^1.22.4: + version "1.22.8" + resolved "https://registry.npmjs.org/resolve/-/resolve-1.22.8.tgz" + integrity sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw== + dependencies: + is-core-module "^2.13.0" + path-parse "^1.0.7" + supports-preserve-symlinks-flag "^1.0.0" + +resolve@^2.0.0-next.5: + version "2.0.0-next.5" + resolved "https://registry.npmjs.org/resolve/-/resolve-2.0.0-next.5.tgz" + integrity sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA== + dependencies: + is-core-module "^2.13.0" + path-parse "^1.0.7" + supports-preserve-symlinks-flag "^1.0.0" + +restructure@^3.0.0: + version "3.0.1" + resolved "https://registry.npmjs.org/restructure/-/restructure-3.0.1.tgz" + integrity sha512-6neDpI/yE9eogQo22qmWwKIA9wFPRyYjQleDEh6zaNAf2ZPqLJYUvNBJBWEWNoBlCeQMQkvIOe2YI/K2GOag+g== + +reusify@^1.0.4: + version "1.0.4" + resolved "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz" + integrity sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw== + +rimraf@^3.0.2: + version "3.0.2" + resolved "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz" + integrity sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA== + dependencies: + glob "^7.1.3" + +rope-sequence@^1.3.0: + version "1.3.4" + resolved "https://registry.npmjs.org/rope-sequence/-/rope-sequence-1.3.4.tgz" + integrity sha512-UT5EDe2cu2E/6O4igUr5PSFs23nvvukicWHx6GnOPlHAiiYbzNuCRQCuiUdHJQcqKalLKlrYJnjY0ySGsXNQXQ== + +run-parallel@^1.1.9: + version "1.2.0" + resolved "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz" + integrity sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA== + dependencies: + queue-microtask "^1.2.2" + +rw@^1.3.3: + version "1.3.3" + resolved "https://registry.npmjs.org/rw/-/rw-1.3.3.tgz" + integrity sha512-PdhdWy89SiZogBLaw42zdeqtRJ//zFd2PgQavcICDUgJT5oW10QCRKbJ6bg4r0/UY2M6BWd5tkxuGFRvCkgfHQ== + +rxjs@^7.8.1: + version "7.8.1" + resolved "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz" + integrity sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg== + dependencies: + tslib "^2.1.0" + +safe-array-concat@^1.1.2: + version "1.1.2" + resolved "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.1.2.tgz" + integrity sha512-vj6RsCsWBCf19jIeHEfkRMw8DPiBb+DMXklQ/1SGDHOMlHdPUkZXFQ2YdplS23zESTijAcurb1aSgJA3AgMu1Q== + dependencies: + call-bind "^1.0.7" + get-intrinsic "^1.2.4" + has-symbols "^1.0.3" + isarray "^2.0.5" + +safe-buffer@>=5.1.0, safe-buffer@~5.2.0: + version "5.2.1" + resolved "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz" + integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ== + +safe-regex-test@^1.0.3: + version "1.0.3" + resolved "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.0.3.tgz" + integrity sha512-CdASjNJPvRa7roO6Ra/gLYBTzYzzPyyBXxIMdGW3USQLyjWEls2RgW5UBTXaQVp+OrpeCK3bLem8smtmheoRuw== + dependencies: + call-bind "^1.0.6" + es-errors "^1.3.0" + is-regex "^1.1.4" + +scheduler@^0.17.0: + version "0.17.0" + resolved "https://registry.npmjs.org/scheduler/-/scheduler-0.17.0.tgz" + integrity sha512-7rro8Io3tnCPuY4la/NuI5F2yfESpnfZyT6TtkXnSWVkcu0BCDJ+8gk5ozUaFaxpIyNuWAPXrH0yFcSi28fnDA== + dependencies: + loose-envify "^1.1.0" + object-assign "^4.1.1" + +scheduler@^0.23.2: + version "0.23.2" + resolved "https://registry.npmjs.org/scheduler/-/scheduler-0.23.2.tgz" + integrity sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ== + dependencies: + loose-envify "^1.1.0" + +scroll@^3.0.1: + version "3.0.1" + resolved "https://registry.npmjs.org/scroll/-/scroll-3.0.1.tgz" + integrity sha512-pz7y517OVls1maEzlirKO5nPYle9AXsFzTMNJrRGmT951mzpIBy7sNHOg5o/0MQd/NqliCiWnAi0kZneMPFLcg== + +scrollparent@^2.1.0: + version "2.1.0" + resolved "https://registry.npmjs.org/scrollparent/-/scrollparent-2.1.0.tgz" + integrity sha512-bnnvJL28/Rtz/kz2+4wpBjHzWoEzXhVg/TE8BeVGJHUqE8THNIRnDxDWMktwM+qahvlRdvlLdsQfYe+cuqfZeA== + +semver@^6.3.0, semver@^6.3.1: + version "6.3.1" + resolved "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz" + integrity sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA== + +semver@^7.6.0: + version "7.6.2" + resolved "https://registry.npmjs.org/semver/-/semver-7.6.2.tgz" + integrity sha512-FNAIBWCx9qcRhoHcgcJ0gvU7SN1lYU2ZXuSfl04bSC5OpvDHFyJCjdNHomPXxjQlCBU67YW64PzY7/VIEH7F2w== + +serialize-to-js@^3.1.2: + version "3.1.2" + resolved "https://registry.npmjs.org/serialize-to-js/-/serialize-to-js-3.1.2.tgz" + integrity sha512-owllqNuDDEimQat7EPG0tH7JjO090xKNzUtYz6X+Sk2BXDnOCilDdNLwjWeFywG9xkJul1ULvtUQa9O4pUaY0w== + +set-function-length@^1.2.1: + version "1.2.2" + resolved "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz" + integrity sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg== + dependencies: + define-data-property "^1.1.4" + es-errors "^1.3.0" + function-bind "^1.1.2" + get-intrinsic "^1.2.4" + gopd "^1.0.1" + has-property-descriptors "^1.0.2" + +set-function-name@^2.0.1, set-function-name@^2.0.2: + version "2.0.2" + resolved "https://registry.npmjs.org/set-function-name/-/set-function-name-2.0.2.tgz" + integrity sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ== + dependencies: + define-data-property "^1.1.4" + es-errors "^1.3.0" + functions-have-names "^1.2.3" + has-property-descriptors "^1.0.2" + +set-value@^2.0.1: + version "2.0.1" + resolved "https://registry.npmjs.org/set-value/-/set-value-2.0.1.tgz" + integrity sha512-JxHc1weCN68wRY0fhCoXpyK55m/XPHafOmK4UWD7m2CI14GMcFypt4w/0+NV5f/ZMby2F6S2wwA7fgynh9gWSw== + dependencies: + extend-shallow "^2.0.1" + is-extendable "^0.1.1" + is-plain-object "^2.0.3" + split-string "^3.0.1" + +shebang-command@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz" + integrity sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA== + dependencies: + shebang-regex "^3.0.0" + +shebang-regex@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz" + integrity sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A== + +side-channel@^1.0.4, side-channel@^1.0.6: + version "1.0.6" + resolved "https://registry.npmjs.org/side-channel/-/side-channel-1.0.6.tgz" + integrity sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA== + dependencies: + call-bind "^1.0.7" + es-errors "^1.3.0" + get-intrinsic "^1.2.4" + object-inspect "^1.13.1" + +simple-swizzle@^0.2.2: + version "0.2.2" + resolved "https://registry.npmjs.org/simple-swizzle/-/simple-swizzle-0.2.2.tgz" + integrity sha512-JA//kQgZtbuY83m+xT+tXJkmJncGMTFT+C+g2h2R9uxkYIrE2yy9sgmcLhCnw57/WSD+Eh3J97FPEDFnbXnDUg== + dependencies: + is-arrayish "^0.3.1" + +simplebar-core@^1.2.5: + version "1.2.5" + resolved "https://registry.npmjs.org/simplebar-core/-/simplebar-core-1.2.5.tgz" + integrity sha512-33AVCYXS8yavWId0GbE4TG1cYELsYybpCKWHJYuWEY/j6nccgz6zQdJ7nCqOpIGo7HgPPbkSSSIlJhi43fHP6A== + dependencies: + "@types/lodash-es" "^4.17.6" + can-use-dom "^0.1.0" + lodash "^4.17.21" + lodash-es "^4.17.21" + +simplebar-react@^3.2.5: + version "3.2.5" + resolved "https://registry.npmjs.org/simplebar-react/-/simplebar-react-3.2.5.tgz" + integrity sha512-ZstHCBF1Is2Lj+Un8NUYSHVCmn8ufi25ylP9UH2bDnASa+V+M+6/thGhUZOZ7YNpFFHTNgVIID3FHdwRqNuqZA== + dependencies: + simplebar-core "^1.2.5" + +slash@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz" + integrity sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q== + +snake-case@^3.0.4: + version "3.0.4" + resolved "https://registry.npmjs.org/snake-case/-/snake-case-3.0.4.tgz" + integrity sha512-LAOh4z89bGQvl9pFfNF8V146i7o7/CqFPbqzYgP+yYzDIDeS9HaNFtXABamRW+AQzEVODcvE79ljJ+8a9YSdMg== + dependencies: + dot-case "^3.0.4" + tslib "^2.0.3" + +sonner@^1.5.0: + version "1.5.0" + resolved "https://registry.npmjs.org/sonner/-/sonner-1.5.0.tgz" + integrity sha512-FBjhG/gnnbN6FY0jaNnqZOMmB73R+5IiyYAw8yBj7L54ER7HB3fOSE5OFiQiE2iXWxeXKvg6fIP4LtVppHEdJA== + +sort-asc@^0.2.0: + version "0.2.0" + resolved "https://registry.npmjs.org/sort-asc/-/sort-asc-0.2.0.tgz" + integrity sha512-umMGhjPeHAI6YjABoSTrFp2zaBtXBej1a0yKkuMUyjjqu6FJsTF+JYwCswWDg+zJfk/5npWUUbd33HH/WLzpaA== + +sort-desc@^0.2.0: + version "0.2.0" + resolved "https://registry.npmjs.org/sort-desc/-/sort-desc-0.2.0.tgz" + integrity sha512-NqZqyvL4VPW+RAxxXnB8gvE1kyikh8+pR+T+CXLksVRN9eiQqkQlPwqWYU0mF9Jm7UnctShlxLyAt1CaBOTL1w== + +sort-object@^3.0.3: + version "3.0.3" + resolved "https://registry.npmjs.org/sort-object/-/sort-object-3.0.3.tgz" + integrity sha512-nK7WOY8jik6zaG9CRwZTaD5O7ETWDLZYMM12pqY8htll+7dYeqGfEUPcUBHOpSJg2vJOrvFIY2Dl5cX2ih1hAQ== + dependencies: + bytewise "^1.1.0" + get-value "^2.0.2" + is-extendable "^0.1.1" + sort-asc "^0.2.0" + sort-desc "^0.2.0" + union-value "^1.0.1" + +source-map-js@^1.0.1, source-map-js@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/source-map-js/-/source-map-js-1.0.2.tgz" + integrity sha512-R0XvVJ9WusLiqTCEiGCmICCMplcCkIwwR11mOSD9CR5u+IXYdiseeEuXCVAjS54zqwkLcPNnmU4OeJ6tUrWhDw== + +source-map@^0.5.7: + version "0.5.7" + resolved "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz" + integrity sha512-LbrmJOMUSdEVxIKvdcJzQC+nQhe8FUZQTXQy6+I75skNgn3OoQ0DZA8YnFa7gp8tqtL3KPf1kmo0R5DoApeSGQ== + +space-separated-tokens@^2.0.0: + version "2.0.2" + resolved "https://registry.npmjs.org/space-separated-tokens/-/space-separated-tokens-2.0.2.tgz" + integrity sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q== + +split-string@^3.0.1: + version "3.1.0" + resolved "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz" + integrity sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw== + dependencies: + extend-shallow "^3.0.0" + +streamsearch@^1.1.0: + version "1.1.0" + resolved "https://registry.npmjs.org/streamsearch/-/streamsearch-1.1.0.tgz" + integrity sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg== + +string_decoder@^1.1.1: + version "1.3.0" + resolved "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz" + integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA== + dependencies: + safe-buffer "~5.2.0" + +string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.3: + version "4.2.3" + resolved "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz" + integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g== + dependencies: + emoji-regex "^8.0.0" + is-fullwidth-code-point "^3.0.0" + strip-ansi "^6.0.1" + +string.prototype.matchall@^4.0.11: + version "4.0.11" + resolved "https://registry.npmjs.org/string.prototype.matchall/-/string.prototype.matchall-4.0.11.tgz" + integrity sha512-NUdh0aDavY2og7IbBPenWqR9exH+E26Sv8e0/eTe1tltDGZL+GtBkDAnnyBtmekfK6/Dq3MkcGtzXFEd1LQrtg== + dependencies: + call-bind "^1.0.7" + define-properties "^1.2.1" + es-abstract "^1.23.2" + es-errors "^1.3.0" + es-object-atoms "^1.0.0" + get-intrinsic "^1.2.4" + gopd "^1.0.1" + has-symbols "^1.0.3" + internal-slot "^1.0.7" + regexp.prototype.flags "^1.5.2" + set-function-name "^2.0.2" + side-channel "^1.0.6" + +string.prototype.trim@^1.2.9: + version "1.2.9" + resolved "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.2.9.tgz" + integrity sha512-klHuCNxiMZ8MlsOihJhJEBJAiMVqU3Z2nEXWfWnIqjN0gEFS9J9+IxKozWWtQGcgoa1WUZzLjKPTr4ZHNFTFxw== + dependencies: + call-bind "^1.0.7" + define-properties "^1.2.1" + es-abstract "^1.23.0" + es-object-atoms "^1.0.0" + +string.prototype.trimend@^1.0.8: + version "1.0.8" + resolved "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.8.tgz" + integrity sha512-p73uL5VCHCO2BZZ6krwwQE3kCzM7NKmis8S//xEC6fQonchbum4eP6kR4DLEjQFO3Wnj3Fuo8NM0kOSjVdHjZQ== + dependencies: + call-bind "^1.0.7" + define-properties "^1.2.1" + es-object-atoms "^1.0.0" + +string.prototype.trimstart@^1.0.8: + version "1.0.8" + resolved "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.8.tgz" + integrity sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg== + dependencies: + call-bind "^1.0.7" + define-properties "^1.2.1" + es-object-atoms "^1.0.0" + +strip-ansi@^6.0.0, strip-ansi@^6.0.1: + version "6.0.1" + resolved "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz" + integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A== + dependencies: + ansi-regex "^5.0.1" + +strip-bom@^3.0.0: + version "3.0.0" + resolved "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz" + integrity sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA== + +strip-json-comments@^3.1.1: + version "3.1.1" + resolved "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz" + integrity sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig== + +strnum@^1.0.5: + version "1.0.5" + resolved "https://registry.npmjs.org/strnum/-/strnum-1.0.5.tgz" + integrity sha512-J8bbNyKKXl5qYcR36TIO8W3mVGVHrmmxsd5PAItGkmyzwJvybiw2IVq5nqd0i4LSNSkB/sx9VHllbfFdr9k1JA== + +style-to-object@^0.4.0: + version "0.4.4" + resolved "https://registry.npmjs.org/style-to-object/-/style-to-object-0.4.4.tgz" + integrity sha512-HYNoHZa2GorYNyqiCaBgsxvcJIn7OHq6inEga+E6Ke3m5JkoqpQbnFssk4jwe+K7AhGa2fcha4wSOf1Kn01dMg== + dependencies: + inline-style-parser "0.1.1" + +styled-jsx@5.1.1: + version "5.1.1" + resolved "https://registry.npmjs.org/styled-jsx/-/styled-jsx-5.1.1.tgz" + integrity sha512-pW7uC1l4mBZ8ugbiZrcIsiIvVx1UmTfw7UkC3Um2tmfUq9Bhk8IiyEIPl6F8agHgjzku6j0xQEZbfA5uSgSaCw== + dependencies: + client-only "0.0.1" + +stylis-plugin-rtl@^2.1.1: + version "2.1.1" + resolved "https://registry.npmjs.org/stylis-plugin-rtl/-/stylis-plugin-rtl-2.1.1.tgz" + integrity sha512-q6xIkri6fBufIO/sV55md2CbgS5c6gg9EhSVATtHHCdOnbN/jcI0u3lYhNVeuI65c4lQPo67g8xmq5jrREvzlg== + dependencies: + cssjanus "^2.0.1" + +stylis@^4.3.2, stylis@4.x: + version "4.3.2" + resolved "https://registry.npmjs.org/stylis/-/stylis-4.3.2.tgz" + integrity sha512-bhtUjWd/z6ltJiQwg0dUfxEJ+W+jdqQd8TbWLWyeIJHlnsqmGLRFFd8e5mA0AZi/zx90smXRlN66YMTcaSFifg== + +stylis@4.2.0: + version "4.2.0" + resolved "https://registry.npmjs.org/stylis/-/stylis-4.2.0.tgz" + integrity sha512-Orov6g6BB1sDfYgzWfTHDOxamtX1bE/zo104Dh9e6fqJ3PooipYyfJ0pUmrZO2wAvO8YbEyeFrkV91XTsGMSrw== + +supercluster@^8.0.0: + version "8.0.1" + resolved "https://registry.npmjs.org/supercluster/-/supercluster-8.0.1.tgz" + integrity sha512-IiOea5kJ9iqzD2t7QJq/cREyLHTtSmUT6gQsweojg9WH2sYJqZK9SswTu6jrscO6D1G5v5vYZ9ru/eq85lXeZQ== + dependencies: + kdbush "^4.0.2" + +supports-color@^5.3.0: + version "5.5.0" + resolved "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz" + integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow== + dependencies: + has-flag "^3.0.0" + +supports-color@^7.1.0: + version "7.2.0" + resolved "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz" + integrity sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw== + dependencies: + has-flag "^4.0.0" + +supports-preserve-symlinks-flag@^1.0.0: + version "1.0.0" + resolved "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz" + integrity sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w== + +svg-arc-to-cubic-bezier@^3.0.0, svg-arc-to-cubic-bezier@^3.2.0: + version "3.2.0" + resolved "https://registry.npmjs.org/svg-arc-to-cubic-bezier/-/svg-arc-to-cubic-bezier-3.2.0.tgz" + integrity sha512-djbJ/vZKZO+gPoSDThGNpKDO+o+bAeA4XQKovvkNCqnIS2t+S4qnLAGQhyyrulhCFRl1WWzAp0wUDV8PpTVU3g== + +svg-parser@^2.0.4: + version "2.0.4" + resolved "https://registry.npmjs.org/svg-parser/-/svg-parser-2.0.4.tgz" + integrity sha512-e4hG1hRwoOdRb37cIMSgzNsxyzKfayW6VOflrwvR+/bzrkyxY/31WkbgnQpgtrNp1SdpJvpUAGTa/ZoiPNDuRQ== + +svg.draggable.js@^2.2.2: + version "2.2.2" + resolved "https://registry.npmjs.org/svg.draggable.js/-/svg.draggable.js-2.2.2.tgz" + integrity sha512-JzNHBc2fLQMzYCZ90KZHN2ohXL0BQJGQimK1kGk6AvSeibuKcIdDX9Kr0dT9+UJ5O8nYA0RB839Lhvk4CY4MZw== + dependencies: + svg.js "^2.0.1" + +svg.easing.js@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/svg.easing.js/-/svg.easing.js-2.0.0.tgz" + integrity sha512-//ctPdJMGy22YoYGV+3HEfHbm6/69LJUTAqI2/5qBvaNHZ9uUFVC82B0Pl299HzgH13rKrBgi4+XyXXyVWWthA== + dependencies: + svg.js ">=2.3.x" + +svg.filter.js@^2.0.2: + version "2.0.2" + resolved "https://registry.npmjs.org/svg.filter.js/-/svg.filter.js-2.0.2.tgz" + integrity sha512-xkGBwU+dKBzqg5PtilaTb0EYPqPfJ9Q6saVldX+5vCRy31P6TlRCP3U9NxH3HEufkKkpNgdTLBJnmhDHeTqAkw== + dependencies: + svg.js "^2.2.5" + +svg.js@^2.0.1, svg.js@^2.2.5, svg.js@^2.4.0, svg.js@^2.6.5, svg.js@>=2.3.x: + version "2.7.1" + resolved "https://registry.npmjs.org/svg.js/-/svg.js-2.7.1.tgz" + integrity sha512-ycbxpizEQktk3FYvn/8BH+6/EuWXg7ZpQREJvgacqn46gIddG24tNNe4Son6omdXCnSOaApnpZw6MPCBA1dODA== + +svg.pathmorphing.js@^0.1.3: + version "0.1.3" + resolved "https://registry.npmjs.org/svg.pathmorphing.js/-/svg.pathmorphing.js-0.1.3.tgz" + integrity sha512-49HWI9X4XQR/JG1qXkSDV8xViuTLIWm/B/7YuQELV5KMOPtXjiwH4XPJvr/ghEDibmLQ9Oc22dpWpG0vUDDNww== + dependencies: + svg.js "^2.4.0" + +svg.resize.js@^1.4.3: + version "1.4.3" + resolved "https://registry.npmjs.org/svg.resize.js/-/svg.resize.js-1.4.3.tgz" + integrity sha512-9k5sXJuPKp+mVzXNvxz7U0uC9oVMQrrf7cFsETznzUDDm0x8+77dtZkWdMfRlmbkEEYvUn9btKuZ3n41oNA+uw== + dependencies: + svg.js "^2.6.5" + svg.select.js "^2.1.2" + +svg.select.js@^2.1.2: + version "2.1.2" + resolved "https://registry.npmjs.org/svg.select.js/-/svg.select.js-2.1.2.tgz" + integrity sha512-tH6ABEyJsAOVAhwcCjF8mw4crjXSI1aa7j2VQR8ZuJ37H2MBUbyeqYr5nEO7sSN3cy9AR9DUwNg0t/962HlDbQ== + dependencies: + svg.js "^2.2.5" + +svg.select.js@^3.0.1: + version "3.0.1" + resolved "https://registry.npmjs.org/svg.select.js/-/svg.select.js-3.0.1.tgz" + integrity sha512-h5IS/hKkuVCbKSieR9uQCj9w+zLHoPh+ce19bBYyqF53g6mnPB8sAtIbe1s9dh2S2fCmYX2xel1Ln3PJBbK4kw== + dependencies: + svg.js "^2.6.5" + +svgo@^3.0.2: + version "3.0.4" + resolved "https://registry.npmjs.org/svgo/-/svgo-3.0.4.tgz" + integrity sha512-T+Xul3JwuJ6VGXKo/p2ndqx1ibxNKnLTvRc1ZTWKCfyKS/GgNjRZcYsK84fxTsy/izr91g/Rwx6fGnVgaFSI5g== + dependencies: + "@trysound/sax" "0.2.0" + commander "^7.2.0" + css-select "^5.1.0" + css-tree "^2.2.1" + css-what "^6.1.0" + csso "5.0.5" + picocolors "^1.0.0" + +swr@^2.2.5: + version "2.2.5" + resolved "https://registry.npmjs.org/swr/-/swr-2.2.5.tgz" + integrity sha512-QtxqyclFeAsxEUeZIYmsaQ0UjimSq1RZ9Un7I68/0ClKK/U3LoyQunwkQfJZr2fc22DfIXLNDc2wFyTEikCUpg== + dependencies: + client-only "^0.0.1" + use-sync-external-store "^1.2.0" + +synckit@^0.8.6: + version "0.8.8" + resolved "https://registry.npmjs.org/synckit/-/synckit-0.8.8.tgz" + integrity sha512-HwOKAP7Wc5aRGYdKH+dw0PRRpbO841v2DENBtjnR5HFWoiNByAl7vrx3p0G/rCyYXQsrxqtX48TImFtPcIHSpQ== + dependencies: + "@pkgr/core" "^0.1.0" + tslib "^2.6.2" + +text-table@^0.2.0: + version "0.2.0" + resolved "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz" + integrity sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw== + +tiny-inflate@^1.0.0, tiny-inflate@^1.0.3: + version "1.0.3" + resolved "https://registry.npmjs.org/tiny-inflate/-/tiny-inflate-1.0.3.tgz" + integrity sha512-pkY1fj1cKHb2seWDy0B16HeWyczlJA9/WW3u3c4z/NiWDsO3DOU5D7nhTLE9CF0yXv/QZFY7sEJmj24dK+Rrqw== + +tiny-lru@^11.2.6: + version "11.2.6" + resolved "https://registry.npmjs.org/tiny-lru/-/tiny-lru-11.2.6.tgz" + integrity sha512-0PU3c9PjMnltZaFo2sGYv/nnJsMjG0Cxx8X6FXHPPGjFyoo1SJDxvUXW1207rdiSxYizf31roo+GrkIByQeZoA== + +tinyqueue@^2.0.3: + version "2.0.3" + resolved "https://registry.npmjs.org/tinyqueue/-/tinyqueue-2.0.3.tgz" + integrity sha512-ppJZNDuKGgxzkHihX8v9v9G5f+18gzaTfrukGrq6ueg0lmH4nqVnA2IPG0AEH3jKEk2GRJCUhDoqpoiw3PHLBA== + +tippy.js@^6.3.7: + version "6.3.7" + resolved "https://registry.npmjs.org/tippy.js/-/tippy.js-6.3.7.tgz" + integrity sha512-E1d3oP2emgJ9dRQZdf3Kkn0qJgI6ZLpyS5z6ZkY1DF3kaQaBsGZsndEpHwx+eC+tYM41HaSNvNtLx8tU57FzTQ== + dependencies: + "@popperjs/core" "^2.9.0" + +to-fast-properties@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-2.0.0.tgz" + integrity sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog== + +to-regex-range@^5.0.1: + version "5.0.1" + resolved "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz" + integrity sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ== + dependencies: + is-number "^7.0.0" + +tr46@~0.0.3: + version "0.0.3" + resolved "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz" + integrity sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw== + +tree-changes@^0.11.2: + version "0.11.2" + resolved "https://registry.npmjs.org/tree-changes/-/tree-changes-0.11.2.tgz" + integrity sha512-4gXlUthrl+RabZw6lLvcCDl6KfJOCmrC16BC5CRdut1EAH509Omgg0BfKLY+ViRlzrvYOTWR0FMS2SQTwzumrw== + dependencies: + "@gilbarbara/deep-equal" "^0.3.1" + is-lite "^1.2.0" + +tree-changes@^0.9.1: + version "0.9.3" + resolved "https://registry.npmjs.org/tree-changes/-/tree-changes-0.9.3.tgz" + integrity sha512-vvvS+O6kEeGRzMglTKbc19ltLWNtmNt1cpBoSYLj/iEcPVvpJasemKOlxBrmZaCtDJoF+4bwv3m01UKYi8mukQ== + dependencies: + "@gilbarbara/deep-equal" "^0.1.1" + is-lite "^0.8.2" + +trim-lines@^3.0.0: + version "3.0.1" + resolved "https://registry.npmjs.org/trim-lines/-/trim-lines-3.0.1.tgz" + integrity sha512-kRj8B+YHZCc9kQYdWfJB2/oUl9rA99qbowYYBtr4ui4mZyAQ2JpvVBd/6U2YloATfqBhBTSMhTpgBHtU0Mf3Rg== + +trough@^2.0.0: + version "2.1.0" + resolved "https://registry.npmjs.org/trough/-/trough-2.1.0.tgz" + integrity sha512-AqTiAOLcj85xS7vQ8QkAV41hPDIJ71XJB4RCUrzo/1GM2CQwhkJGaf9Hgr7BOugMRpgGUrqRg/DrBDl4H40+8g== + +ts-api-utils@^1.3.0: + version "1.3.0" + resolved "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-1.3.0.tgz" + integrity sha512-UQMIo7pb8WRomKR1/+MFVLTroIvDVtMX3K6OUir8ynLyzB8Jeriont2bTAtmNPa1ekAgN7YPDyf6V+ygrdU+eQ== + +tsconfig-paths@^3.15.0: + version "3.15.0" + resolved "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.15.0.tgz" + integrity sha512-2Ac2RgzDe/cn48GvOe3M+o82pEFewD3UPbyoUHHdKasHwJKjds4fLXWf/Ux5kATBKN20oaFGu+jbElp1pos0mg== + dependencies: + "@types/json5" "^0.0.29" + json5 "^1.0.2" + minimist "^1.2.6" + strip-bom "^3.0.0" + +tslib@^1.11.1: + version "1.14.1" + resolved "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz" + integrity sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg== + +tslib@^2.0.0, tslib@^2.0.3, tslib@^2.1.0, tslib@^2.3.1, tslib@^2.4.0, tslib@^2.5.0, tslib@^2.6.2: + version "2.6.2" + resolved "https://registry.npmjs.org/tslib/-/tslib-2.6.2.tgz" + integrity sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q== + +turndown@^7.2.0: + version "7.2.0" + resolved "https://registry.npmjs.org/turndown/-/turndown-7.2.0.tgz" + integrity sha512-eCZGBN4nNNqM9Owkv9HAtWRYfLA4h909E/WGAWWBpmB275ehNhZyk87/Tpvjbp0jjNl9XwCsbe6bm6CqFsgD+A== + dependencies: + "@mixmark-io/domino" "^2.2.0" + +tweakpane@^4.0.3: + version "4.0.3" + resolved "https://registry.npmjs.org/tweakpane/-/tweakpane-4.0.3.tgz" + integrity sha512-BlcWOAe8oe4c+k9pmLBARGdWB6MVZMszayekkixQXTgkxTaYoTUpHpwVEp+3HkoamZkomodpbBf0CkguIHTgLg== + +type-check@^0.4.0, type-check@~0.4.0: + version "0.4.0" + resolved "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz" + integrity sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew== + dependencies: + prelude-ls "^1.2.1" + +type-fest@^0.20.2: + version "0.20.2" + resolved "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz" + integrity sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ== + +type-fest@^4.18.2: + version "4.18.2" + resolved "https://registry.npmjs.org/type-fest/-/type-fest-4.18.2.tgz" + integrity sha512-+suCYpfJLAe4OXS6+PPXjW3urOS4IoP9waSiLuXfLgqZODKw/aWwASvzqE886wA0kQgGy0mIWyhd87VpqIy6Xg== + +typed-array-buffer@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/typed-array-buffer/-/typed-array-buffer-1.0.2.tgz" + integrity sha512-gEymJYKZtKXzzBzM4jqa9w6Q1Jjm7x2d+sh19AdsD4wqnMPDYyvwpsIc2Q/835kHuo3BEQ7CjelGhfTsoBb2MQ== + dependencies: + call-bind "^1.0.7" + es-errors "^1.3.0" + is-typed-array "^1.1.13" + +typed-array-byte-length@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/typed-array-byte-length/-/typed-array-byte-length-1.0.1.tgz" + integrity sha512-3iMJ9q0ao7WE9tWcaYKIptkNBuOIcZCCT0d4MRvuuH88fEoEH62IuQe0OtraD3ebQEoTRk8XCBoknUNc1Y67pw== + dependencies: + call-bind "^1.0.7" + for-each "^0.3.3" + gopd "^1.0.1" + has-proto "^1.0.3" + is-typed-array "^1.1.13" + +typed-array-byte-offset@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/typed-array-byte-offset/-/typed-array-byte-offset-1.0.2.tgz" + integrity sha512-Ous0vodHa56FviZucS2E63zkgtgrACj7omjwd/8lTEMEPFFyjfixMZ1ZXenpgCFBBt4EC1J2XsyVS2gkG0eTFA== + dependencies: + available-typed-arrays "^1.0.7" + call-bind "^1.0.7" + for-each "^0.3.3" + gopd "^1.0.1" + has-proto "^1.0.3" + is-typed-array "^1.1.13" + +typed-array-length@^1.0.6: + version "1.0.6" + resolved "https://registry.npmjs.org/typed-array-length/-/typed-array-length-1.0.6.tgz" + integrity sha512-/OxDN6OtAk5KBpGb28T+HZc2M+ADtvRxXrKKbUwtsLgdoxgX13hyy7ek6bFRl5+aBs2yZzB0c4CnQfAtVypW/g== + dependencies: + call-bind "^1.0.7" + for-each "^0.3.3" + gopd "^1.0.1" + has-proto "^1.0.3" + is-typed-array "^1.1.13" + possible-typed-array-names "^1.0.0" + +typescript@^5.4.5, typescript@>=4.2.0, typescript@>=4.9.5: + version "5.4.5" + resolved "https://registry.npmjs.org/typescript/-/typescript-5.4.5.tgz" + integrity sha512-vcI4UpRgg81oIRUFwR0WSIHKt11nJ7SAVlYNIu+QpqeyXP+gpQJy/Z4+F0aGxSE4MqwjyXvW/TzgkLAx2AGHwQ== + +typewise-core@^1.2, typewise-core@^1.2.0: + version "1.2.0" + resolved "https://registry.npmjs.org/typewise-core/-/typewise-core-1.2.0.tgz" + integrity sha512-2SCC/WLzj2SbUwzFOzqMCkz5amXLlxtJqDKTICqg30x+2DZxcfZN2MvQZmGfXWKNWaKK9pBPsvkcwv8bF/gxKg== + +typewise@^1.0.3: + version "1.0.3" + resolved "https://registry.npmjs.org/typewise/-/typewise-1.0.3.tgz" + integrity sha512-aXofE06xGhaQSPzt8hlTY+/YWQhm9P0jYUp1f2XtmW/3Bk0qzXcyFWAtPoo2uTGQj1ZwbDuSyuxicq+aDo8lCQ== + dependencies: + typewise-core "^1.2.0" + +uc.micro@^2.0.0, uc.micro@^2.1.0: + version "2.1.0" + resolved "https://registry.npmjs.org/uc.micro/-/uc.micro-2.1.0.tgz" + integrity sha512-ARDJmphmdvUk6Glw7y9DQ2bFkKBHwQHLi2lsaH6PPmz/Ka9sFOBsBluozhDltWmnv9u/cF6Rt87znRTPV+yp/A== + +ulid@^2.3.0: + version "2.3.0" + resolved "https://registry.npmjs.org/ulid/-/ulid-2.3.0.tgz" + integrity sha512-keqHubrlpvT6G2wH0OEfSW4mquYRcbe/J8NMmveoQOjUqmo+hXtO+ORCpWhdbZ7k72UtY61BL7haGxW6enBnjw== + +unbox-primitive@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.0.2.tgz" + integrity sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw== + dependencies: + call-bind "^1.0.2" + has-bigints "^1.0.2" + has-symbols "^1.0.3" + which-boxed-primitive "^1.0.2" + +undici-types@~5.26.4: + version "5.26.5" + resolved "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz" + integrity sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA== + +undici@5.28.4: + version "5.28.4" + resolved "https://registry.npmjs.org/undici/-/undici-5.28.4.tgz" + integrity sha512-72RFADWFqKmUb2hmmvNODKL3p9hcB6Gt2DOQMis1SEBaV6a4MH8soBvzg+95CYhCKPFedut2JY9bMfrDl9D23g== + dependencies: + "@fastify/busboy" "^2.0.0" + +unicode-canonical-property-names-ecmascript@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/unicode-canonical-property-names-ecmascript/-/unicode-canonical-property-names-ecmascript-2.0.0.tgz" + integrity sha512-yY5PpDlfVIU5+y/BSCxAJRBIS1Zc2dDG3Ujq+sR0U+JjUevW2JhocOF+soROYDSaAezOzOKuyyixhD6mBknSmQ== + +unicode-match-property-ecmascript@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/unicode-match-property-ecmascript/-/unicode-match-property-ecmascript-2.0.0.tgz" + integrity sha512-5kaZCrbp5mmbz5ulBkDkbY0SsPOjKqVS35VpL9ulMPfSl0J0Xsm+9Evphv9CoIZFwre7aJoa94AY6seMKGVN5Q== + dependencies: + unicode-canonical-property-names-ecmascript "^2.0.0" + unicode-property-aliases-ecmascript "^2.0.0" + +unicode-match-property-value-ecmascript@^2.1.0: + version "2.1.0" + resolved "https://registry.npmjs.org/unicode-match-property-value-ecmascript/-/unicode-match-property-value-ecmascript-2.1.0.tgz" + integrity sha512-qxkjQt6qjg/mYscYMC0XKRn3Rh0wFPlfxB0xkt9CfyTvpX1Ra0+rAmdX2QyAobptSEvuy4RtpPRui6XkV+8wjA== + +unicode-properties@^1.4.0, unicode-properties@^1.4.1: + version "1.4.1" + resolved "https://registry.npmjs.org/unicode-properties/-/unicode-properties-1.4.1.tgz" + integrity sha512-CLjCCLQ6UuMxWnbIylkisbRj31qxHPAurvena/0iwSVbQ2G1VY5/HjV0IRabOEbDHlzZlRdCrD4NhB0JtU40Pg== + dependencies: + base64-js "^1.3.0" + unicode-trie "^2.0.0" + +unicode-property-aliases-ecmascript@^2.0.0: + version "2.1.0" + resolved "https://registry.npmjs.org/unicode-property-aliases-ecmascript/-/unicode-property-aliases-ecmascript-2.1.0.tgz" + integrity sha512-6t3foTQI9qne+OZoVQB/8x8rk2k1eVy1gRXhV3oFQ5T6R1dqQ1xtin3XqSlx3+ATBkliTaR/hHyJBm+LVPNM8w== + +unicode-trie@^2.0.0: + version "2.0.0" + resolved "https://registry.npmjs.org/unicode-trie/-/unicode-trie-2.0.0.tgz" + integrity sha512-x7bc76x0bm4prf1VLg79uhAzKw8DVboClSN5VxJuQ+LKDOVEW9CdH+VY7SP+vX7xCYQqzzgQpFqz15zeLvAtZQ== + dependencies: + pako "^0.2.5" + tiny-inflate "^1.0.0" + +unified@^11.0.0: + version "11.0.4" + resolved "https://registry.npmjs.org/unified/-/unified-11.0.4.tgz" + integrity sha512-apMPnyLjAX+ty4OrNap7yumyVAMlKx5IWU2wlzzUdYJO9A8f1p9m/gywF/GM2ZDFcjQPrx59Mc90KwmxsoklxQ== + dependencies: + "@types/unist" "^3.0.0" + bail "^2.0.0" + devlop "^1.0.0" + extend "^3.0.0" + is-plain-obj "^4.0.0" + trough "^2.0.0" + vfile "^6.0.0" + +union-value@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/union-value/-/union-value-1.0.1.tgz" + integrity sha512-tJfXmxMeWYnczCVs7XAEvIV7ieppALdyepWMkHkwciRpZraG/xwT+s2JN8+pr1+8jCRf80FFzvr+MpQeeoF4Xg== + dependencies: + arr-union "^3.1.0" + get-value "^2.0.6" + is-extendable "^0.1.1" + set-value "^2.0.1" + +unist-util-find-after@^5.0.0: + version "5.0.0" + resolved "https://registry.npmjs.org/unist-util-find-after/-/unist-util-find-after-5.0.0.tgz" + integrity sha512-amQa0Ep2m6hE2g72AugUItjbuM8X8cGQnFoHk0pGfrFeT9GZhzN5SW8nRsiGKK7Aif4CrACPENkA6P/Lw6fHGQ== + dependencies: + "@types/unist" "^3.0.0" + unist-util-is "^6.0.0" + +unist-util-is@^6.0.0: + version "6.0.0" + resolved "https://registry.npmjs.org/unist-util-is/-/unist-util-is-6.0.0.tgz" + integrity sha512-2qCTHimwdxLfz+YzdGfkqNlH0tLi9xjTnHddPmJwtIG9MGsdbutfTc4P+haPD7l7Cjxf/WZj+we5qfVPvvxfYw== + dependencies: + "@types/unist" "^3.0.0" + +unist-util-position@^5.0.0: + version "5.0.0" + resolved "https://registry.npmjs.org/unist-util-position/-/unist-util-position-5.0.0.tgz" + integrity sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA== + dependencies: + "@types/unist" "^3.0.0" + +unist-util-stringify-position@^4.0.0: + version "4.0.0" + resolved "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-4.0.0.tgz" + integrity sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ== + dependencies: + "@types/unist" "^3.0.0" + +unist-util-visit-parents@^6.0.0: + version "6.0.1" + resolved "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-6.0.1.tgz" + integrity sha512-L/PqWzfTP9lzzEa6CKs0k2nARxTdZduw3zyh8d2NVBnsyvHjSX4TWse388YrrQKbvI8w20fGjGlhgT96WwKykw== + dependencies: + "@types/unist" "^3.0.0" + unist-util-is "^6.0.0" + +unist-util-visit@^5.0.0: + version "5.0.0" + resolved "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-5.0.0.tgz" + integrity sha512-MR04uvD+07cwl/yhVuVWAtw+3GOR/knlL55Nd/wAdblk27GCVt3lqpTivy/tkJcZoNPzTwS1Y+KMojlLDhoTzg== + dependencies: + "@types/unist" "^3.0.0" + unist-util-is "^6.0.0" + unist-util-visit-parents "^6.0.0" + +update-browserslist-db@^1.0.13: + version "1.0.13" + resolved "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.0.13.tgz" + integrity sha512-xebP81SNcPuNpPP3uzeW1NYXxI3rxyJzF3pD6sH4jE7o/IX+WtSpwnVU+qIsDPyk0d3hmFQ7mjqc6AtV604hbg== + dependencies: + escalade "^3.1.1" + picocolors "^1.0.0" + +uri-js@^4.2.2: + version "4.4.1" + resolved "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz" + integrity sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg== + dependencies: + punycode "^2.1.0" + +use-sync-external-store@^1.2.0: + version "1.2.0" + resolved "https://registry.npmjs.org/use-sync-external-store/-/use-sync-external-store-1.2.0.tgz" + integrity sha512-eEgnFxGQ1Ife9bzYs6VLi8/4X6CObHMw9Qr9tPY43iKwsPw8xE8+EFsf/2cFZ5S3esXgpWgtSCtLNS41F+sKPA== + +util-deprecate@^1.0.1: + version "1.0.2" + resolved "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz" + integrity sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw== + +uuid@^9.0.0, uuid@^9.0.1: + version "9.0.1" + resolved "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz" + integrity sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA== + +vfile-location@^5.0.0: + version "5.0.2" + resolved "https://registry.npmjs.org/vfile-location/-/vfile-location-5.0.2.tgz" + integrity sha512-NXPYyxyBSH7zB5U6+3uDdd6Nybz6o6/od9rk8bp9H8GR3L+cm/fC0uUTbqBmUTnMCUDslAGBOIKNfvvb+gGlDg== + dependencies: + "@types/unist" "^3.0.0" + vfile "^6.0.0" + +vfile-message@^4.0.0: + version "4.0.2" + resolved "https://registry.npmjs.org/vfile-message/-/vfile-message-4.0.2.tgz" + integrity sha512-jRDZ1IMLttGj41KcZvlrYAaI3CfqpLpfpf+Mfig13viT6NKvRzWZ+lXz0Y5D60w6uJIBAOGq9mSHf0gktF0duw== + dependencies: + "@types/unist" "^3.0.0" + unist-util-stringify-position "^4.0.0" + +vfile@^6.0.0: + version "6.0.1" + resolved "https://registry.npmjs.org/vfile/-/vfile-6.0.1.tgz" + integrity sha512-1bYqc7pt6NIADBJ98UiG0Bn/CHIVOoZ/IyEkqIruLg0mE1BKzkOXY2D6CSqQIcKqgadppE5lrxgWXJmXd7zZJw== + dependencies: + "@types/unist" "^3.0.0" + unist-util-stringify-position "^4.0.0" + vfile-message "^4.0.0" + +vite-compatible-readable-stream@^3.6.1: + version "3.6.1" + resolved "https://registry.npmjs.org/vite-compatible-readable-stream/-/vite-compatible-readable-stream-3.6.1.tgz" + integrity sha512-t20zYkrSf868+j/p31cRIGN28Phrjm3nRSLR2fyc2tiWi4cZGVdv68yNlwnIINTkMTmPoMiSlc0OadaO7DXZaQ== + dependencies: + inherits "^2.0.3" + string_decoder "^1.1.1" + util-deprecate "^1.0.1" + +void-elements@3.1.0: + version "3.1.0" + resolved "https://registry.npmjs.org/void-elements/-/void-elements-3.1.0.tgz" + integrity sha512-Dhxzh5HZuiHQhbvTW9AMetFfBHDMYpo23Uo9btPXgdYP+3T5S+p+jgNy7spra+veYhBP2dCSgxR/i2Y02h5/6w== + +vt-pbf@^3.1.3: + version "3.1.3" + resolved "https://registry.npmjs.org/vt-pbf/-/vt-pbf-3.1.3.tgz" + integrity sha512-2LzDFzt0mZKZ9IpVF2r69G9bXaP2Q2sArJCmcCgvfTdCCZzSyz4aCLoQyUilu37Ll56tCblIZrXFIjNUpGIlmA== + dependencies: + "@mapbox/point-geometry" "0.1.0" + "@mapbox/vector-tile" "^1.3.1" + pbf "^3.2.1" + +w3c-keyname@^2.2.0: + version "2.2.8" + resolved "https://registry.npmjs.org/w3c-keyname/-/w3c-keyname-2.2.8.tgz" + integrity sha512-dpojBhNsCNN7T82Tm7k26A6G9ML3NkhDsnw9n/eoxSRlVBB4CEtIQ/KTCLI2Fwf3ataSXRhYFkQi3SlnFwPvPQ== + +web-namespaces@^2.0.0: + version "2.0.1" + resolved "https://registry.npmjs.org/web-namespaces/-/web-namespaces-2.0.1.tgz" + integrity sha512-bKr1DkiNa2krS7qxNtdrtHAmzuYGFQLiQ13TsorsdT6ULTkPLKuu5+GsFpDlg6JFjUTwX2DyhMPG2be8uPrqsQ== + +webidl-conversions@^3.0.0: + version "3.0.1" + resolved "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz" + integrity sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ== + +websocket-driver@>=0.5.1: + version "0.7.4" + resolved "https://registry.npmjs.org/websocket-driver/-/websocket-driver-0.7.4.tgz" + integrity sha512-b17KeDIQVjvb0ssuSDF2cYXSg2iztliJ4B9WdsuB6J952qCPKmnVq4DyW5motImXHDC1cBT/1UezrJVsKw5zjg== + dependencies: + http-parser-js ">=0.5.1" + safe-buffer ">=5.1.0" + websocket-extensions ">=0.1.1" + +websocket-extensions@>=0.1.1: + version "0.1.4" + resolved "https://registry.npmjs.org/websocket-extensions/-/websocket-extensions-0.1.4.tgz" + integrity sha512-OqedPIGOfsDlo31UNwYbCFMSaO9m9G/0faIHj5/dZFDMFqPTcx6UwqyOy3COEaEOg/9VsGIpdqn62W5KhoKSpg== + +whatwg-url@^5.0.0: + version "5.0.0" + resolved "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz" + integrity sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw== + dependencies: + tr46 "~0.0.3" + webidl-conversions "^3.0.0" + +which-boxed-primitive@^1.0.2: + version "1.0.2" + resolved "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.0.2.tgz" + integrity sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg== + dependencies: + is-bigint "^1.0.1" + is-boolean-object "^1.1.0" + is-number-object "^1.0.4" + is-string "^1.0.5" + is-symbol "^1.0.3" + +which-builtin-type@^1.1.3: + version "1.1.3" + resolved "https://registry.npmjs.org/which-builtin-type/-/which-builtin-type-1.1.3.tgz" + integrity sha512-YmjsSMDBYsM1CaFiayOVT06+KJeXf0o5M/CAd4o1lTadFAtacTUM49zoYxr/oroopFDfhvN6iEcBxUyc3gvKmw== + dependencies: + function.prototype.name "^1.1.5" + has-tostringtag "^1.0.0" + is-async-function "^2.0.0" + is-date-object "^1.0.5" + is-finalizationregistry "^1.0.2" + is-generator-function "^1.0.10" + is-regex "^1.1.4" + is-weakref "^1.0.2" + isarray "^2.0.5" + which-boxed-primitive "^1.0.2" + which-collection "^1.0.1" + which-typed-array "^1.1.9" + +which-collection@^1.0.1: + version "1.0.1" + resolved "https://registry.npmjs.org/which-collection/-/which-collection-1.0.1.tgz" + integrity sha512-W8xeTUwaln8i3K/cY1nGXzdnVZlidBcagyNFtBdD5kxnb4TvGKR7FfSIS3mYpwWS1QUCutfKz8IY8RjftB0+1A== + dependencies: + is-map "^2.0.1" + is-set "^2.0.1" + is-weakmap "^2.0.1" + is-weakset "^2.0.1" + +which-typed-array@^1.1.14, which-typed-array@^1.1.15, which-typed-array@^1.1.9: + version "1.1.15" + resolved "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.15.tgz" + integrity sha512-oV0jmFtUky6CXfkqehVvBP/LSWJ2sy4vWMioiENyJLePrBO/yKyV9OyJySfAKosh+RYkIl5zJCNZ8/4JncrpdA== + dependencies: + available-typed-arrays "^1.0.7" + call-bind "^1.0.7" + for-each "^0.3.3" + gopd "^1.0.1" + has-tostringtag "^1.0.2" + +which@^2.0.1: + version "2.0.2" + resolved "https://registry.npmjs.org/which/-/which-2.0.2.tgz" + integrity sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA== + dependencies: + isexe "^2.0.0" + +wrap-ansi@^7.0.0: + version "7.0.0" + resolved "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz" + integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q== + dependencies: + ansi-styles "^4.0.0" + string-width "^4.1.0" + strip-ansi "^6.0.0" + +wrappy@1: + version "1.0.2" + resolved "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz" + integrity sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ== + +ws@^8.14.2: + version "8.17.0" + resolved "https://registry.npmjs.org/ws/-/ws-8.17.0.tgz" + integrity sha512-uJq6108EgZMAl20KagGkzCKfMEjxmKvZHG7Tlq0Z6nOky7YF7aq4mOx6xK8TJ/i1LeK4Qus7INktacctDgY8Ow== + +y18n@^5.0.5: + version "5.0.8" + resolved "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz" + integrity sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA== + +yallist@^3.0.2: + version "3.1.1" + resolved "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz" + integrity sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g== + +yaml@^1.10.0: + version "1.10.2" + resolved "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz" + integrity sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg== + +yargs-parser@^21.1.1: + version "21.1.1" + resolved "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz" + integrity sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw== + +yargs@^17.7.2: + version "17.7.2" + resolved "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz" + integrity sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w== + dependencies: + cliui "^8.0.1" + escalade "^3.1.1" + get-caller-file "^2.0.5" + require-directory "^2.1.1" + string-width "^4.2.3" + y18n "^5.0.5" + yargs-parser "^21.1.1" + +yet-another-react-lightbox@^3.20.0: + version "3.20.0" + resolved "https://registry.npmjs.org/yet-another-react-lightbox/-/yet-another-react-lightbox-3.20.0.tgz" + integrity sha512-Ty0yrqfVJ5XVq0gr1EmN31Ng5gkjC79RePrtzqGi/Xn+erwiuzEDTmKqbO9pDqrfb05xfow2NwWcp3auk4RVuQ== + +yocto-queue@^0.1.0: + version "0.1.0" + resolved "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz" + integrity sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q== + +yoga-layout@^2.0.1: + version "2.0.1" + resolved "https://registry.npmjs.org/yoga-layout/-/yoga-layout-2.0.1.tgz" + integrity sha512-tT/oChyDXelLo2A+UVnlW9GU7CsvFMaEnd9kVFsaiCQonFAXd3xrHhkLYu+suwwosrAEQ746xBU+HvYtm1Zs2Q== + +zod@^3.23.8: + version "3.23.8" + resolved "https://registry.npmjs.org/zod/-/zod-3.23.8.tgz" + integrity sha512-XBx9AXhXktjUqnepgTiE5flcKIYWi/rme0Eaj+5Y0lftuGBq+jyRu/md4WnuxqgP1ubdpNCsYEYPxrzVHD8d6g== + +zwitch@^2.0.0: + version "2.0.4" + resolved "https://registry.npmjs.org/zwitch/-/zwitch-2.0.4.tgz" + integrity sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==