From 202a9f3160f14dc282ca430494714db63304d2a3 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 09:21:59 +0800
Subject: [PATCH 01/92] imported browser router and wrapped App within it
---
src/index.js | 5 ++++-
1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/src/index.js b/src/index.js
index 31508db1..cbc4561e 100644
--- a/src/index.js
+++ b/src/index.js
@@ -2,10 +2,13 @@ import React from "react";
import ReactDOM from "react-dom/client";
import "./index.css";
import App from "./App";
+import { BrowserRouter } from "react-router-dom";
const root = ReactDOM.createRoot(document.getElementById("root"));
root.render(
-
+
+
+
);
From 3bfbd8c7b60400cff30e9657225d451dc800712f Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 09:34:00 +0800
Subject: [PATCH 02/92] added route paths for Home and Dasdboard
---
src/App.js | 27 ++++++++++++++-------------
1 file changed, 14 insertions(+), 13 deletions(-)
diff --git a/src/App.js b/src/App.js
index 4a6f800f..bc9f2814 100644
--- a/src/App.js
+++ b/src/App.js
@@ -1,20 +1,21 @@
import React from "react";
-import logo from "./logo.png";
+import { Routes, Route } from "react-router-dom";
+import Home from "./components/Home";
+import Dashboard from "./components/Dashboard";
+
import "./App.css";
-class App extends React.Component {
- render() {
- return (
+const App = () => {
+ return (
+ <>
- );
- }
-}
+ >
+ );
+};
export default App;
From f086e34bc0eeab82159a1c63349bdc83e2836e80 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 09:35:49 +0800
Subject: [PATCH 03/92] installed mui and react router v6
---
package.json | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/package.json b/package.json
index a100866d..681597c3 100644
--- a/package.json
+++ b/package.json
@@ -3,8 +3,12 @@
"version": "0.1.0",
"private": true,
"dependencies": {
+ "@emotion/react": "^11.11.1",
+ "@emotion/styled": "^11.11.0",
+ "@mui/material": "^5.14.16",
"react": "^18.1.0",
"react-dom": "^18.1.0",
+ "react-router-dom": "^6.18.0",
"react-scripts": "5.0.1"
},
"scripts": {
From 8b8f7c6f20bf9ec7c4b1c9384bc41fb12de72f21 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 09:36:24 +0800
Subject: [PATCH 04/92] installed mui and react router v6
---
package-lock.json | 954 +++++++++++++++++++++++++++++++++++++++++++++-
1 file changed, 946 insertions(+), 8 deletions(-)
diff --git a/package-lock.json b/package-lock.json
index c205fc57..9bd5de8d 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -8,8 +8,12 @@
"name": "project1-bootcamp",
"version": "0.1.0",
"dependencies": {
+ "@emotion/react": "^11.11.1",
+ "@emotion/styled": "^11.11.0",
+ "@mui/material": "^5.14.16",
"react": "^18.1.0",
"react-dom": "^18.1.0",
+ "react-router-dom": "^6.18.0",
"react-scripts": "5.0.1"
}
},
@@ -1764,11 +1768,11 @@
}
},
"node_modules/@babel/runtime": {
- "version": "7.17.9",
- "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.17.9.tgz",
- "integrity": "sha512-lSiBBvodq29uShpWGNbgFdKYNiFDo5/HIYsaCEY9ff4sb10x9jizo2+pRrSyF4jKZCXqgzuqBOQKbUm90gQwJg==",
+ "version": "7.23.2",
+ "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.23.2.tgz",
+ "integrity": "sha512-mM8eg4yl5D6i3lu2QKPuPH4FArvJ8KhTofbE7jwMUv9KX5mBvwPAqnV3MlyBNqdp9RyRKP6Yck8TrfYrPvX3bg==",
"dependencies": {
- "regenerator-runtime": "^0.13.4"
+ "regenerator-runtime": "^0.14.0"
},
"engines": {
"node": ">=6.9.0"
@@ -1786,6 +1790,11 @@
"node": ">=6.9.0"
}
},
+ "node_modules/@babel/runtime/node_modules/regenerator-runtime": {
+ "version": "0.14.0",
+ "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.0.tgz",
+ "integrity": "sha512-srw17NI0TUWHuGa5CFGGmhfNIeja30WMBfbslPNhf6JrqQlLN5gcrvig1oqPxiVaXb0oW0XRKtH6Nngs5lKCIA=="
+ },
"node_modules/@babel/template": {
"version": "7.16.7",
"resolved": "https://registry.npmjs.org/@babel/template/-/template-7.16.7.tgz",
@@ -1997,6 +2006,158 @@
"postcss": "^8.3"
}
},
+ "node_modules/@emotion/babel-plugin": {
+ "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"
+ }
+ },
+ "node_modules/@emotion/babel-plugin/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/@emotion/babel-plugin/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==",
+ "engines": {
+ "node": ">=0.10.0"
+ }
+ },
+ "node_modules/@emotion/cache": {
+ "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"
+ }
+ },
+ "node_modules/@emotion/hash": {
+ "version": "0.9.1",
+ "resolved": "https://registry.npmjs.org/@emotion/hash/-/hash-0.9.1.tgz",
+ "integrity": "sha512-gJB6HLm5rYwSLI6PQa+X1t5CFGrv1J1TWG+sOyMCeKz2ojaj6Fnl/rZEspogG+cvqbt4AE/2eIyD2QfLKTBNlQ=="
+ },
+ "node_modules/@emotion/is-prop-valid": {
+ "version": "1.2.1",
+ "resolved": "https://registry.npmjs.org/@emotion/is-prop-valid/-/is-prop-valid-1.2.1.tgz",
+ "integrity": "sha512-61Mf7Ufx4aDxx1xlDeOm8aFFigGHE4z+0sKCa+IHCeZKiyP9RLD0Mmx7m8b9/Cf37f7NAvQOOJAbQQGVr5uERw==",
+ "dependencies": {
+ "@emotion/memoize": "^0.8.1"
+ }
+ },
+ "node_modules/@emotion/memoize": {
+ "version": "0.8.1",
+ "resolved": "https://registry.npmjs.org/@emotion/memoize/-/memoize-0.8.1.tgz",
+ "integrity": "sha512-W2P2c/VRW1/1tLox0mVUalvnWXxavmv/Oum2aPsRcoDJuob75FC3Y8FbpfLwUegRcxINtGUMPq0tFCvYNTBXNA=="
+ },
+ "node_modules/@emotion/react": {
+ "version": "11.11.1",
+ "resolved": "https://registry.npmjs.org/@emotion/react/-/react-11.11.1.tgz",
+ "integrity": "sha512-5mlW1DquU5HaxjLkfkGN1GA/fvVGdyHURRiX/0FHl2cfIfRxSOfmxEH5YS43edp0OldZrZ+dkBKbngxcNCdZvA==",
+ "dependencies": {
+ "@babel/runtime": "^7.18.3",
+ "@emotion/babel-plugin": "^11.11.0",
+ "@emotion/cache": "^11.11.0",
+ "@emotion/serialize": "^1.1.2",
+ "@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"
+ },
+ "peerDependencies": {
+ "react": ">=16.8.0"
+ },
+ "peerDependenciesMeta": {
+ "@types/react": {
+ "optional": true
+ }
+ }
+ },
+ "node_modules/@emotion/serialize": {
+ "version": "1.1.2",
+ "resolved": "https://registry.npmjs.org/@emotion/serialize/-/serialize-1.1.2.tgz",
+ "integrity": "sha512-zR6a/fkFP4EAcCMQtLOhIgpprZOwNmCldtpaISpvz348+DP4Mz8ZoKaGGCQpbzepNIUWbq4w6hNZkwDyKoS+HA==",
+ "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"
+ }
+ },
+ "node_modules/@emotion/sheet": {
+ "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=="
+ },
+ "node_modules/@emotion/styled": {
+ "version": "11.11.0",
+ "resolved": "https://registry.npmjs.org/@emotion/styled/-/styled-11.11.0.tgz",
+ "integrity": "sha512-hM5Nnvu9P3midq5aaXj4I+lnSfNi7Pmd4EWk1fOZ3pxookaQTNew6bp4JaCBYM4HVFZF9g7UjJmsUmC2JlxOng==",
+ "dependencies": {
+ "@babel/runtime": "^7.18.3",
+ "@emotion/babel-plugin": "^11.11.0",
+ "@emotion/is-prop-valid": "^1.2.1",
+ "@emotion/serialize": "^1.1.2",
+ "@emotion/use-insertion-effect-with-fallbacks": "^1.0.1",
+ "@emotion/utils": "^1.2.1"
+ },
+ "peerDependencies": {
+ "@emotion/react": "^11.0.0-rc.0",
+ "react": ">=16.8.0"
+ },
+ "peerDependenciesMeta": {
+ "@types/react": {
+ "optional": true
+ }
+ }
+ },
+ "node_modules/@emotion/unitless": {
+ "version": "0.8.1",
+ "resolved": "https://registry.npmjs.org/@emotion/unitless/-/unitless-0.8.1.tgz",
+ "integrity": "sha512-KOEGMu6dmJZtpadb476IsZBclKvILjopjUii3V+7MnXIQCYh8W3NgNcgwo21n9LXZX6EDIKvqfjYxXebDwxKmQ=="
+ },
+ "node_modules/@emotion/use-insertion-effect-with-fallbacks": {
+ "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==",
+ "peerDependencies": {
+ "react": ">=16.8.0"
+ }
+ },
+ "node_modules/@emotion/utils": {
+ "version": "1.2.1",
+ "resolved": "https://registry.npmjs.org/@emotion/utils/-/utils-1.2.1.tgz",
+ "integrity": "sha512-Y2tGf3I+XVnajdItskUCn6LX+VUDmP6lTL4fcqsXAv43dnlbZiuW4MWQW38rW/BVWSE7Q/7+XQocmpnRYILUmg=="
+ },
+ "node_modules/@emotion/weak-memoize": {
+ "version": "0.3.1",
+ "resolved": "https://registry.npmjs.org/@emotion/weak-memoize/-/weak-memoize-0.3.1.tgz",
+ "integrity": "sha512-EsBwpc7hBUJWAsNPBmJy4hxWx12v6bshQsldrVmjxJoc3isbxhOrF2IcCpaXxfvq03NwkI7sbsOLXbYuqF/8Ww=="
+ },
"node_modules/@eslint/eslintrc": {
"version": "1.2.2",
"resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.2.2.tgz",
@@ -2057,6 +2218,40 @@
"url": "https://github.com/sponsors/sindresorhus"
}
},
+ "node_modules/@floating-ui/core": {
+ "version": "1.5.0",
+ "resolved": "https://registry.npmjs.org/@floating-ui/core/-/core-1.5.0.tgz",
+ "integrity": "sha512-kK1h4m36DQ0UHGj5Ah4db7R0rHemTqqO0QLvUqi1/mUUp3LuAWbWxdxSIf/XsnH9VS6rRVPLJCncjRzUvyCLXg==",
+ "dependencies": {
+ "@floating-ui/utils": "^0.1.3"
+ }
+ },
+ "node_modules/@floating-ui/dom": {
+ "version": "1.5.3",
+ "resolved": "https://registry.npmjs.org/@floating-ui/dom/-/dom-1.5.3.tgz",
+ "integrity": "sha512-ClAbQnEqJAKCJOEbbLo5IUlZHkNszqhuxS4fHAVxRPXPya6Ysf2G8KypnYcOTpx6I8xcgF9bbHb6g/2KpbV8qA==",
+ "dependencies": {
+ "@floating-ui/core": "^1.4.2",
+ "@floating-ui/utils": "^0.1.3"
+ }
+ },
+ "node_modules/@floating-ui/react-dom": {
+ "version": "2.0.2",
+ "resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.0.2.tgz",
+ "integrity": "sha512-5qhlDvjaLmAst/rKb3VdlCinwTF4EYMiVxuuc/HVUjs46W0zgtbMmAZ1UTsDrRTxRmUEzl92mOtWbeeXL26lSQ==",
+ "dependencies": {
+ "@floating-ui/dom": "^1.5.1"
+ },
+ "peerDependencies": {
+ "react": ">=16.8.0",
+ "react-dom": ">=16.8.0"
+ }
+ },
+ "node_modules/@floating-ui/utils": {
+ "version": "0.1.6",
+ "resolved": "https://registry.npmjs.org/@floating-ui/utils/-/utils-0.1.6.tgz",
+ "integrity": "sha512-OfX7E2oUDYxtBvsuS4e/jSn4Q9Qb6DzgeYtsAdkPZ47znpoNsMgZw0+tVijiv3uGNR6dgNlty6r9rzIzHjtd/A=="
+ },
"node_modules/@humanwhocodes/config-array": {
"version": "0.9.5",
"resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.9.5.tgz",
@@ -2785,6 +2980,236 @@
"resolved": "https://registry.npmjs.org/@leichtgewicht/ip-codec/-/ip-codec-2.0.3.tgz",
"integrity": "sha512-nkalE/f1RvRGChwBnEIoBfSEYOXnCRdleKuv6+lePbMDrMZXeDQnqak5XDOeBgrPPyPfAdcCu/B5z+v3VhplGg=="
},
+ "node_modules/@mui/base": {
+ "version": "5.0.0-beta.22",
+ "resolved": "https://registry.npmjs.org/@mui/base/-/base-5.0.0-beta.22.tgz",
+ "integrity": "sha512-l4asGID5tmyerx9emJfXOKLyXzaBtdXNIFE3M+IrSZaFtGFvaQKHhc3+nxxSxPf1+G44psjczM0ekRQCdXx9HA==",
+ "dependencies": {
+ "@babel/runtime": "^7.23.2",
+ "@floating-ui/react-dom": "^2.0.2",
+ "@mui/types": "^7.2.8",
+ "@mui/utils": "^5.14.16",
+ "@popperjs/core": "^2.11.8",
+ "clsx": "^2.0.0",
+ "prop-types": "^15.8.1"
+ },
+ "engines": {
+ "node": ">=12.0.0"
+ },
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/mui"
+ },
+ "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/core-downloads-tracker": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/core-downloads-tracker/-/core-downloads-tracker-5.14.16.tgz",
+ "integrity": "sha512-97isBjzH2v1K7oB4UH2f4NOkBShOynY6dhnoR2XlUk/g6bb7ZBv2I3D1hvvqPtpEigKu93e7f/jAYr5d9LOc5w==",
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/mui"
+ }
+ },
+ "node_modules/@mui/material": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/material/-/material-5.14.16.tgz",
+ "integrity": "sha512-W4zZ4vnxgGk6/HqBwgsDHKU7x2l2NhX+r8gAwfg58Rhu3ikfY7NkIS6y8Gl3NkATc4GG1FNaGjjpQKfJx3U6Jw==",
+ "dependencies": {
+ "@babel/runtime": "^7.23.2",
+ "@mui/base": "5.0.0-beta.22",
+ "@mui/core-downloads-tracker": "^5.14.16",
+ "@mui/system": "^5.14.16",
+ "@mui/types": "^7.2.8",
+ "@mui/utils": "^5.14.16",
+ "@types/react-transition-group": "^4.4.8",
+ "clsx": "^2.0.0",
+ "csstype": "^3.1.2",
+ "prop-types": "^15.8.1",
+ "react-is": "^18.2.0",
+ "react-transition-group": "^4.4.5"
+ },
+ "engines": {
+ "node": ">=12.0.0"
+ },
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/mui"
+ },
+ "peerDependencies": {
+ "@emotion/react": "^11.5.0",
+ "@emotion/styled": "^11.3.0",
+ "@types/react": "^17.0.0 || ^18.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
+ },
+ "@types/react": {
+ "optional": true
+ }
+ }
+ },
+ "node_modules/@mui/material/node_modules/react-is": {
+ "version": "18.2.0",
+ "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz",
+ "integrity": "sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w=="
+ },
+ "node_modules/@mui/private-theming": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/private-theming/-/private-theming-5.14.16.tgz",
+ "integrity": "sha512-FNlL0pTSEBh8nXsVWreCHDSHk+jG8cBx1sxRbT8JVtL+PYbYPi802zfV4B00Kkf0LNRVRvAVQwojMWSR/MYGng==",
+ "dependencies": {
+ "@babel/runtime": "^7.23.2",
+ "@mui/utils": "^5.14.16",
+ "prop-types": "^15.8.1"
+ },
+ "engines": {
+ "node": ">=12.0.0"
+ },
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/mui"
+ },
+ "peerDependencies": {
+ "@types/react": "^17.0.0 || ^18.0.0",
+ "react": "^17.0.0 || ^18.0.0"
+ },
+ "peerDependenciesMeta": {
+ "@types/react": {
+ "optional": true
+ }
+ }
+ },
+ "node_modules/@mui/styled-engine": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/styled-engine/-/styled-engine-5.14.16.tgz",
+ "integrity": "sha512-FfvYvTG/Zd+KXMMImbcMYEeQAbONGuX5Vx3gBmmtB6KyA7Mvm9Pma1ly3R0gc44yeoFd+2wBjn1feS8h42HW5w==",
+ "dependencies": {
+ "@babel/runtime": "^7.23.2",
+ "@emotion/cache": "^11.11.0",
+ "csstype": "^3.1.2",
+ "prop-types": "^15.8.1"
+ },
+ "engines": {
+ "node": ">=12.0.0"
+ },
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/mui"
+ },
+ "peerDependencies": {
+ "@emotion/react": "^11.4.1",
+ "@emotion/styled": "^11.3.0",
+ "react": "^17.0.0 || ^18.0.0"
+ },
+ "peerDependenciesMeta": {
+ "@emotion/react": {
+ "optional": true
+ },
+ "@emotion/styled": {
+ "optional": true
+ }
+ }
+ },
+ "node_modules/@mui/system": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/system/-/system-5.14.16.tgz",
+ "integrity": "sha512-uKnPfsDqDs8bbN54TviAuoGWOmFiQLwNZ3Wvj+OBkJCzwA6QnLb/sSeCB7Pk3ilH4h4jQ0BHtbR+Xpjy9wlOuA==",
+ "dependencies": {
+ "@babel/runtime": "^7.23.2",
+ "@mui/private-theming": "^5.14.16",
+ "@mui/styled-engine": "^5.14.16",
+ "@mui/types": "^7.2.8",
+ "@mui/utils": "^5.14.16",
+ "clsx": "^2.0.0",
+ "csstype": "^3.1.2",
+ "prop-types": "^15.8.1"
+ },
+ "engines": {
+ "node": ">=12.0.0"
+ },
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/mui"
+ },
+ "peerDependencies": {
+ "@emotion/react": "^11.5.0",
+ "@emotion/styled": "^11.3.0",
+ "@types/react": "^17.0.0 || ^18.0.0",
+ "react": "^17.0.0 || ^18.0.0"
+ },
+ "peerDependenciesMeta": {
+ "@emotion/react": {
+ "optional": true
+ },
+ "@emotion/styled": {
+ "optional": true
+ },
+ "@types/react": {
+ "optional": true
+ }
+ }
+ },
+ "node_modules/@mui/types": {
+ "version": "7.2.8",
+ "resolved": "https://registry.npmjs.org/@mui/types/-/types-7.2.8.tgz",
+ "integrity": "sha512-9u0ji+xspl96WPqvrYJF/iO+1tQ1L5GTaDOeG3vCR893yy7VcWwRNiVMmPdPNpMDqx0WV1wtEW9OMwK9acWJzQ==",
+ "peerDependencies": {
+ "@types/react": "^17.0.0 || ^18.0.0"
+ },
+ "peerDependenciesMeta": {
+ "@types/react": {
+ "optional": true
+ }
+ }
+ },
+ "node_modules/@mui/utils": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/utils/-/utils-5.14.16.tgz",
+ "integrity": "sha512-3xV31GposHkwRbQzwJJuooWpK2ybWdEdeUPtRjv/6vjomyi97F3+68l+QVj9tPTvmfSbr2sx5c/NuvDulrdRmA==",
+ "dependencies": {
+ "@babel/runtime": "^7.23.2",
+ "@types/prop-types": "^15.7.9",
+ "prop-types": "^15.8.1",
+ "react-is": "^18.2.0"
+ },
+ "engines": {
+ "node": ">=12.0.0"
+ },
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/mui"
+ },
+ "peerDependencies": {
+ "@types/react": "^17.0.0 || ^18.0.0",
+ "react": "^17.0.0 || ^18.0.0"
+ },
+ "peerDependenciesMeta": {
+ "@types/react": {
+ "optional": true
+ }
+ }
+ },
+ "node_modules/@mui/utils/node_modules/react-is": {
+ "version": "18.2.0",
+ "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz",
+ "integrity": "sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w=="
+ },
"node_modules/@nodelib/fs.scandir": {
"version": "2.1.5",
"resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz",
@@ -2866,6 +3291,23 @@
}
}
},
+ "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/@remix-run/router": {
+ "version": "1.11.0",
+ "resolved": "https://registry.npmjs.org/@remix-run/router/-/router-1.11.0.tgz",
+ "integrity": "sha512-BHdhcWgeiudl91HvVa2wxqZjSHbheSgIiDvxrF1VjFzBzpTtuDPkOdOi3Iqvc08kXtFkLjhbS+ML9aM8mJS+wQ==",
+ "engines": {
+ "node": ">=14.0.0"
+ }
+ },
"node_modules/@rollup/plugin-babel": {
"version": "5.3.1",
"resolved": "https://registry.npmjs.org/@rollup/plugin-babel/-/plugin-babel-5.3.1.tgz",
@@ -3387,6 +3829,11 @@
"resolved": "https://registry.npmjs.org/@types/prettier/-/prettier-2.6.0.tgz",
"integrity": "sha512-G/AdOadiZhnJp0jXCaBQU449W2h716OW/EoXeYkCytxKL06X1WCXB4DZpp8TpZ8eyIJVS1cw4lrlkkSYU21cDw=="
},
+ "node_modules/@types/prop-types": {
+ "version": "15.7.9",
+ "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.9.tgz",
+ "integrity": "sha512-n1yyPsugYNSmHgxDFjicaI2+gCNjsBck8UX9kuofAKlc0h1bL+20oSF72KeNaW2DUlesbEVCFgyV2dPGTiY42g=="
+ },
"node_modules/@types/q": {
"version": "1.5.5",
"resolved": "https://registry.npmjs.org/@types/q/-/q-1.5.5.tgz",
@@ -3402,6 +3849,24 @@
"resolved": "https://registry.npmjs.org/@types/range-parser/-/range-parser-1.2.4.tgz",
"integrity": "sha512-EEhsLsD6UsDM1yFhAvy0Cjr6VwmpMWqFBCb9w07wVugF7w9nfajxLuVmngTIpgS6svCnm6Vaw+MZhoDCKnOfsw=="
},
+ "node_modules/@types/react": {
+ "version": "18.2.34",
+ "resolved": "https://registry.npmjs.org/@types/react/-/react-18.2.34.tgz",
+ "integrity": "sha512-U6eW/alrRk37FU/MS2RYMjx0Va2JGIVXELTODaTIYgvWGCV4Y4TfTUzG8DdmpDNIT0Xpj/R7GfyHOJJrDttcvg==",
+ "dependencies": {
+ "@types/prop-types": "*",
+ "@types/scheduler": "*",
+ "csstype": "^3.0.2"
+ }
+ },
+ "node_modules/@types/react-transition-group": {
+ "version": "4.4.8",
+ "resolved": "https://registry.npmjs.org/@types/react-transition-group/-/react-transition-group-4.4.8.tgz",
+ "integrity": "sha512-QmQ22q+Pb+HQSn04NL3HtrqHwYMf4h3QKArOy5F8U5nEVMaihBs3SR10WiOM1iwPz5jIo8x/u11al+iEGZZrvg==",
+ "dependencies": {
+ "@types/react": "*"
+ }
+ },
"node_modules/@types/resolve": {
"version": "1.17.1",
"resolved": "https://registry.npmjs.org/@types/resolve/-/resolve-1.17.1.tgz",
@@ -3415,6 +3880,11 @@
"resolved": "https://registry.npmjs.org/@types/retry/-/retry-0.12.0.tgz",
"integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA=="
},
+ "node_modules/@types/scheduler": {
+ "version": "0.16.5",
+ "resolved": "https://registry.npmjs.org/@types/scheduler/-/scheduler-0.16.5.tgz",
+ "integrity": "sha512-s/FPdYRmZR8SjLWGMCuax7r3qCWQw9QKHzXVukAuuIJkXkDRwp+Pu5LMIVFi0Fxbav35WURicYr8u1QsoybnQw=="
+ },
"node_modules/@types/serve-index": {
"version": "1.9.1",
"resolved": "https://registry.npmjs.org/@types/serve-index/-/serve-index-1.9.1.tgz",
@@ -4920,6 +5390,14 @@
"wrap-ansi": "^7.0.0"
}
},
+ "node_modules/clsx": {
+ "version": "2.0.0",
+ "resolved": "https://registry.npmjs.org/clsx/-/clsx-2.0.0.tgz",
+ "integrity": "sha512-rQ1+kcj+ttHG0MKVGBUXwayCCF1oh39BF5COIpRzuCEv8Mwjv0XucrI2ExNTOn9IlLifGClWQcU9BrZORvtw6Q==",
+ "engines": {
+ "node": ">=6"
+ }
+ },
"node_modules/co": {
"version": "4.6.0",
"resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz",
@@ -5586,6 +6064,11 @@
"resolved": "https://registry.npmjs.org/cssom/-/cssom-0.3.8.tgz",
"integrity": "sha512-b0tGHbfegbhPJpxpiBPU2sCkigAqtM9O121le6bbOlgyV+NyGyCmVfJ6QW9eRjz8CpNfWEOYBIMIGRYkLwsIYg=="
},
+ "node_modules/csstype": {
+ "version": "3.1.2",
+ "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.2.tgz",
+ "integrity": "sha512-I7K1Uu0MBPzaFKg4nI5Q7Vs2t+3gWWW648spaF+Rg7pI9ds18Ugn+lvg4SHczUdKlHI5LWBXyqfS8+DufyBsgQ=="
+ },
"node_modules/damerau-levenshtein": {
"version": "1.0.8",
"resolved": "https://registry.npmjs.org/damerau-levenshtein/-/damerau-levenshtein-1.0.8.tgz",
@@ -5829,6 +6312,15 @@
"utila": "~0.4"
}
},
+ "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": "1.4.1",
"resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-1.4.1.tgz",
@@ -7138,6 +7630,11 @@
"url": "https://github.com/avajs/find-cache-dir?sponsor=1"
}
},
+ "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=="
+ },
"node_modules/find-up": {
"version": "5.0.0",
"resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz",
@@ -7705,6 +8202,19 @@
"he": "bin/he"
}
},
+ "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/hoopy": {
"version": "0.1.4",
"resolved": "https://registry.npmjs.org/hoopy/-/hoopy-0.1.4.tgz",
@@ -13112,6 +13622,36 @@
"node": ">=0.10.0"
}
},
+ "node_modules/react-router": {
+ "version": "6.18.0",
+ "resolved": "https://registry.npmjs.org/react-router/-/react-router-6.18.0.tgz",
+ "integrity": "sha512-vk2y7Dsy8wI02eRRaRmOs9g2o+aE72YCx5q9VasT1N9v+lrdB79tIqrjMfByHiY5+6aYkH2rUa5X839nwWGPDg==",
+ "dependencies": {
+ "@remix-run/router": "1.11.0"
+ },
+ "engines": {
+ "node": ">=14.0.0"
+ },
+ "peerDependencies": {
+ "react": ">=16.8"
+ }
+ },
+ "node_modules/react-router-dom": {
+ "version": "6.18.0",
+ "resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-6.18.0.tgz",
+ "integrity": "sha512-Ubrue4+Ercc/BoDkFQfc6og5zRQ4A8YxSO3Knsne+eRbZ+IepAsK249XBH/XaFuOYOYr3L3r13CXTLvYt5JDjw==",
+ "dependencies": {
+ "@remix-run/router": "1.11.0",
+ "react-router": "6.18.0"
+ },
+ "engines": {
+ "node": ">=14.0.0"
+ },
+ "peerDependencies": {
+ "react": ">=16.8",
+ "react-dom": ">=16.8"
+ }
+ },
"node_modules/react-scripts": {
"version": "5.0.1",
"resolved": "https://registry.npmjs.org/react-scripts/-/react-scripts-5.0.1.tgz",
@@ -13184,6 +13724,21 @@
}
}
},
+ "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": "3.6.0",
"resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz",
@@ -14246,6 +14801,11 @@
"postcss": "^8.2.15"
}
},
+ "node_modules/stylis": {
+ "version": "4.2.0",
+ "resolved": "https://registry.npmjs.org/stylis/-/stylis-4.2.0.tgz",
+ "integrity": "sha512-Orov6g6BB1sDfYgzWfTHDOxamtX1bE/zo104Dh9e6fqJ3PooipYyfJ0pUmrZO2wAvO8YbEyeFrkV91XTsGMSrw=="
+ },
"node_modules/supports-color": {
"version": "5.5.0",
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
@@ -17044,11 +17604,18 @@
}
},
"@babel/runtime": {
- "version": "7.17.9",
- "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.17.9.tgz",
- "integrity": "sha512-lSiBBvodq29uShpWGNbgFdKYNiFDo5/HIYsaCEY9ff4sb10x9jizo2+pRrSyF4jKZCXqgzuqBOQKbUm90gQwJg==",
+ "version": "7.23.2",
+ "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.23.2.tgz",
+ "integrity": "sha512-mM8eg4yl5D6i3lu2QKPuPH4FArvJ8KhTofbE7jwMUv9KX5mBvwPAqnV3MlyBNqdp9RyRKP6Yck8TrfYrPvX3bg==",
"requires": {
- "regenerator-runtime": "^0.13.4"
+ "regenerator-runtime": "^0.14.0"
+ },
+ "dependencies": {
+ "regenerator-runtime": {
+ "version": "0.14.0",
+ "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.0.tgz",
+ "integrity": "sha512-srw17NI0TUWHuGa5CFGGmhfNIeja30WMBfbslPNhf6JrqQlLN5gcrvig1oqPxiVaXb0oW0XRKtH6Nngs5lKCIA=="
+ }
}
},
"@babel/runtime-corejs3": {
@@ -17187,6 +17754,132 @@
"integrity": "sha512-T5ZyNSw9G0x0UDFiXV40a7VjKw2b+l4G+S0sctKqxhx8cg9QtMUAGwJBVU9mHPDPoZEmwm0tEoukjl4zb9MU7Q==",
"requires": {}
},
+ "@emotion/babel-plugin": {
+ "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==",
+ "requires": {
+ "@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"
+ },
+ "dependencies": {
+ "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=="
+ },
+ "source-map": {
+ "version": "0.5.7",
+ "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz",
+ "integrity": "sha512-LbrmJOMUSdEVxIKvdcJzQC+nQhe8FUZQTXQy6+I75skNgn3OoQ0DZA8YnFa7gp8tqtL3KPf1kmo0R5DoApeSGQ=="
+ }
+ }
+ },
+ "@emotion/cache": {
+ "version": "11.11.0",
+ "resolved": "https://registry.npmjs.org/@emotion/cache/-/cache-11.11.0.tgz",
+ "integrity": "sha512-P34z9ssTCBi3e9EI1ZsWpNHcfY1r09ZO0rZbRO2ob3ZQMnFI35jB536qoXbkdesr5EUhYi22anuEJuyxifaqAQ==",
+ "requires": {
+ "@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/hash": {
+ "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": {
+ "version": "1.2.1",
+ "resolved": "https://registry.npmjs.org/@emotion/is-prop-valid/-/is-prop-valid-1.2.1.tgz",
+ "integrity": "sha512-61Mf7Ufx4aDxx1xlDeOm8aFFigGHE4z+0sKCa+IHCeZKiyP9RLD0Mmx7m8b9/Cf37f7NAvQOOJAbQQGVr5uERw==",
+ "requires": {
+ "@emotion/memoize": "^0.8.1"
+ }
+ },
+ "@emotion/memoize": {
+ "version": "0.8.1",
+ "resolved": "https://registry.npmjs.org/@emotion/memoize/-/memoize-0.8.1.tgz",
+ "integrity": "sha512-W2P2c/VRW1/1tLox0mVUalvnWXxavmv/Oum2aPsRcoDJuob75FC3Y8FbpfLwUegRcxINtGUMPq0tFCvYNTBXNA=="
+ },
+ "@emotion/react": {
+ "version": "11.11.1",
+ "resolved": "https://registry.npmjs.org/@emotion/react/-/react-11.11.1.tgz",
+ "integrity": "sha512-5mlW1DquU5HaxjLkfkGN1GA/fvVGdyHURRiX/0FHl2cfIfRxSOfmxEH5YS43edp0OldZrZ+dkBKbngxcNCdZvA==",
+ "requires": {
+ "@babel/runtime": "^7.18.3",
+ "@emotion/babel-plugin": "^11.11.0",
+ "@emotion/cache": "^11.11.0",
+ "@emotion/serialize": "^1.1.2",
+ "@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": {
+ "version": "1.1.2",
+ "resolved": "https://registry.npmjs.org/@emotion/serialize/-/serialize-1.1.2.tgz",
+ "integrity": "sha512-zR6a/fkFP4EAcCMQtLOhIgpprZOwNmCldtpaISpvz348+DP4Mz8ZoKaGGCQpbzepNIUWbq4w6hNZkwDyKoS+HA==",
+ "requires": {
+ "@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": {
+ "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": {
+ "version": "11.11.0",
+ "resolved": "https://registry.npmjs.org/@emotion/styled/-/styled-11.11.0.tgz",
+ "integrity": "sha512-hM5Nnvu9P3midq5aaXj4I+lnSfNi7Pmd4EWk1fOZ3pxookaQTNew6bp4JaCBYM4HVFZF9g7UjJmsUmC2JlxOng==",
+ "requires": {
+ "@babel/runtime": "^7.18.3",
+ "@emotion/babel-plugin": "^11.11.0",
+ "@emotion/is-prop-valid": "^1.2.1",
+ "@emotion/serialize": "^1.1.2",
+ "@emotion/use-insertion-effect-with-fallbacks": "^1.0.1",
+ "@emotion/utils": "^1.2.1"
+ }
+ },
+ "@emotion/unitless": {
+ "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": {
+ "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==",
+ "requires": {}
+ },
+ "@emotion/utils": {
+ "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": {
+ "version": "0.3.1",
+ "resolved": "https://registry.npmjs.org/@emotion/weak-memoize/-/weak-memoize-0.3.1.tgz",
+ "integrity": "sha512-EsBwpc7hBUJWAsNPBmJy4hxWx12v6bshQsldrVmjxJoc3isbxhOrF2IcCpaXxfvq03NwkI7sbsOLXbYuqF/8Ww=="
+ },
"@eslint/eslintrc": {
"version": "1.2.2",
"resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.2.2.tgz",
@@ -17231,6 +17924,36 @@
}
}
},
+ "@floating-ui/core": {
+ "version": "1.5.0",
+ "resolved": "https://registry.npmjs.org/@floating-ui/core/-/core-1.5.0.tgz",
+ "integrity": "sha512-kK1h4m36DQ0UHGj5Ah4db7R0rHemTqqO0QLvUqi1/mUUp3LuAWbWxdxSIf/XsnH9VS6rRVPLJCncjRzUvyCLXg==",
+ "requires": {
+ "@floating-ui/utils": "^0.1.3"
+ }
+ },
+ "@floating-ui/dom": {
+ "version": "1.5.3",
+ "resolved": "https://registry.npmjs.org/@floating-ui/dom/-/dom-1.5.3.tgz",
+ "integrity": "sha512-ClAbQnEqJAKCJOEbbLo5IUlZHkNszqhuxS4fHAVxRPXPya6Ysf2G8KypnYcOTpx6I8xcgF9bbHb6g/2KpbV8qA==",
+ "requires": {
+ "@floating-ui/core": "^1.4.2",
+ "@floating-ui/utils": "^0.1.3"
+ }
+ },
+ "@floating-ui/react-dom": {
+ "version": "2.0.2",
+ "resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.0.2.tgz",
+ "integrity": "sha512-5qhlDvjaLmAst/rKb3VdlCinwTF4EYMiVxuuc/HVUjs46W0zgtbMmAZ1UTsDrRTxRmUEzl92mOtWbeeXL26lSQ==",
+ "requires": {
+ "@floating-ui/dom": "^1.5.1"
+ }
+ },
+ "@floating-ui/utils": {
+ "version": "0.1.6",
+ "resolved": "https://registry.npmjs.org/@floating-ui/utils/-/utils-0.1.6.tgz",
+ "integrity": "sha512-OfX7E2oUDYxtBvsuS4e/jSn4Q9Qb6DzgeYtsAdkPZ47znpoNsMgZw0+tVijiv3uGNR6dgNlty6r9rzIzHjtd/A=="
+ },
"@humanwhocodes/config-array": {
"version": "0.9.5",
"resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.9.5.tgz",
@@ -17771,6 +18494,111 @@
"resolved": "https://registry.npmjs.org/@leichtgewicht/ip-codec/-/ip-codec-2.0.3.tgz",
"integrity": "sha512-nkalE/f1RvRGChwBnEIoBfSEYOXnCRdleKuv6+lePbMDrMZXeDQnqak5XDOeBgrPPyPfAdcCu/B5z+v3VhplGg=="
},
+ "@mui/base": {
+ "version": "5.0.0-beta.22",
+ "resolved": "https://registry.npmjs.org/@mui/base/-/base-5.0.0-beta.22.tgz",
+ "integrity": "sha512-l4asGID5tmyerx9emJfXOKLyXzaBtdXNIFE3M+IrSZaFtGFvaQKHhc3+nxxSxPf1+G44psjczM0ekRQCdXx9HA==",
+ "requires": {
+ "@babel/runtime": "^7.23.2",
+ "@floating-ui/react-dom": "^2.0.2",
+ "@mui/types": "^7.2.8",
+ "@mui/utils": "^5.14.16",
+ "@popperjs/core": "^2.11.8",
+ "clsx": "^2.0.0",
+ "prop-types": "^15.8.1"
+ }
+ },
+ "@mui/core-downloads-tracker": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/core-downloads-tracker/-/core-downloads-tracker-5.14.16.tgz",
+ "integrity": "sha512-97isBjzH2v1K7oB4UH2f4NOkBShOynY6dhnoR2XlUk/g6bb7ZBv2I3D1hvvqPtpEigKu93e7f/jAYr5d9LOc5w=="
+ },
+ "@mui/material": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/material/-/material-5.14.16.tgz",
+ "integrity": "sha512-W4zZ4vnxgGk6/HqBwgsDHKU7x2l2NhX+r8gAwfg58Rhu3ikfY7NkIS6y8Gl3NkATc4GG1FNaGjjpQKfJx3U6Jw==",
+ "requires": {
+ "@babel/runtime": "^7.23.2",
+ "@mui/base": "5.0.0-beta.22",
+ "@mui/core-downloads-tracker": "^5.14.16",
+ "@mui/system": "^5.14.16",
+ "@mui/types": "^7.2.8",
+ "@mui/utils": "^5.14.16",
+ "@types/react-transition-group": "^4.4.8",
+ "clsx": "^2.0.0",
+ "csstype": "^3.1.2",
+ "prop-types": "^15.8.1",
+ "react-is": "^18.2.0",
+ "react-transition-group": "^4.4.5"
+ },
+ "dependencies": {
+ "react-is": {
+ "version": "18.2.0",
+ "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz",
+ "integrity": "sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w=="
+ }
+ }
+ },
+ "@mui/private-theming": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/private-theming/-/private-theming-5.14.16.tgz",
+ "integrity": "sha512-FNlL0pTSEBh8nXsVWreCHDSHk+jG8cBx1sxRbT8JVtL+PYbYPi802zfV4B00Kkf0LNRVRvAVQwojMWSR/MYGng==",
+ "requires": {
+ "@babel/runtime": "^7.23.2",
+ "@mui/utils": "^5.14.16",
+ "prop-types": "^15.8.1"
+ }
+ },
+ "@mui/styled-engine": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/styled-engine/-/styled-engine-5.14.16.tgz",
+ "integrity": "sha512-FfvYvTG/Zd+KXMMImbcMYEeQAbONGuX5Vx3gBmmtB6KyA7Mvm9Pma1ly3R0gc44yeoFd+2wBjn1feS8h42HW5w==",
+ "requires": {
+ "@babel/runtime": "^7.23.2",
+ "@emotion/cache": "^11.11.0",
+ "csstype": "^3.1.2",
+ "prop-types": "^15.8.1"
+ }
+ },
+ "@mui/system": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/system/-/system-5.14.16.tgz",
+ "integrity": "sha512-uKnPfsDqDs8bbN54TviAuoGWOmFiQLwNZ3Wvj+OBkJCzwA6QnLb/sSeCB7Pk3ilH4h4jQ0BHtbR+Xpjy9wlOuA==",
+ "requires": {
+ "@babel/runtime": "^7.23.2",
+ "@mui/private-theming": "^5.14.16",
+ "@mui/styled-engine": "^5.14.16",
+ "@mui/types": "^7.2.8",
+ "@mui/utils": "^5.14.16",
+ "clsx": "^2.0.0",
+ "csstype": "^3.1.2",
+ "prop-types": "^15.8.1"
+ }
+ },
+ "@mui/types": {
+ "version": "7.2.8",
+ "resolved": "https://registry.npmjs.org/@mui/types/-/types-7.2.8.tgz",
+ "integrity": "sha512-9u0ji+xspl96WPqvrYJF/iO+1tQ1L5GTaDOeG3vCR893yy7VcWwRNiVMmPdPNpMDqx0WV1wtEW9OMwK9acWJzQ==",
+ "requires": {}
+ },
+ "@mui/utils": {
+ "version": "5.14.16",
+ "resolved": "https://registry.npmjs.org/@mui/utils/-/utils-5.14.16.tgz",
+ "integrity": "sha512-3xV31GposHkwRbQzwJJuooWpK2ybWdEdeUPtRjv/6vjomyi97F3+68l+QVj9tPTvmfSbr2sx5c/NuvDulrdRmA==",
+ "requires": {
+ "@babel/runtime": "^7.23.2",
+ "@types/prop-types": "^15.7.9",
+ "prop-types": "^15.8.1",
+ "react-is": "^18.2.0"
+ },
+ "dependencies": {
+ "react-is": {
+ "version": "18.2.0",
+ "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz",
+ "integrity": "sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w=="
+ }
+ }
+ },
"@nodelib/fs.scandir": {
"version": "2.1.5",
"resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz",
@@ -17810,6 +18638,16 @@
"source-map": "^0.7.3"
}
},
+ "@popperjs/core": {
+ "version": "2.11.8",
+ "resolved": "https://registry.npmjs.org/@popperjs/core/-/core-2.11.8.tgz",
+ "integrity": "sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A=="
+ },
+ "@remix-run/router": {
+ "version": "1.11.0",
+ "resolved": "https://registry.npmjs.org/@remix-run/router/-/router-1.11.0.tgz",
+ "integrity": "sha512-BHdhcWgeiudl91HvVa2wxqZjSHbheSgIiDvxrF1VjFzBzpTtuDPkOdOi3Iqvc08kXtFkLjhbS+ML9aM8mJS+wQ=="
+ },
"@rollup/plugin-babel": {
"version": "5.3.1",
"resolved": "https://registry.npmjs.org/@rollup/plugin-babel/-/plugin-babel-5.3.1.tgz",
@@ -18201,6 +19039,11 @@
"resolved": "https://registry.npmjs.org/@types/prettier/-/prettier-2.6.0.tgz",
"integrity": "sha512-G/AdOadiZhnJp0jXCaBQU449W2h716OW/EoXeYkCytxKL06X1WCXB4DZpp8TpZ8eyIJVS1cw4lrlkkSYU21cDw=="
},
+ "@types/prop-types": {
+ "version": "15.7.9",
+ "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.9.tgz",
+ "integrity": "sha512-n1yyPsugYNSmHgxDFjicaI2+gCNjsBck8UX9kuofAKlc0h1bL+20oSF72KeNaW2DUlesbEVCFgyV2dPGTiY42g=="
+ },
"@types/q": {
"version": "1.5.5",
"resolved": "https://registry.npmjs.org/@types/q/-/q-1.5.5.tgz",
@@ -18216,6 +19059,24 @@
"resolved": "https://registry.npmjs.org/@types/range-parser/-/range-parser-1.2.4.tgz",
"integrity": "sha512-EEhsLsD6UsDM1yFhAvy0Cjr6VwmpMWqFBCb9w07wVugF7w9nfajxLuVmngTIpgS6svCnm6Vaw+MZhoDCKnOfsw=="
},
+ "@types/react": {
+ "version": "18.2.34",
+ "resolved": "https://registry.npmjs.org/@types/react/-/react-18.2.34.tgz",
+ "integrity": "sha512-U6eW/alrRk37FU/MS2RYMjx0Va2JGIVXELTODaTIYgvWGCV4Y4TfTUzG8DdmpDNIT0Xpj/R7GfyHOJJrDttcvg==",
+ "requires": {
+ "@types/prop-types": "*",
+ "@types/scheduler": "*",
+ "csstype": "^3.0.2"
+ }
+ },
+ "@types/react-transition-group": {
+ "version": "4.4.8",
+ "resolved": "https://registry.npmjs.org/@types/react-transition-group/-/react-transition-group-4.4.8.tgz",
+ "integrity": "sha512-QmQ22q+Pb+HQSn04NL3HtrqHwYMf4h3QKArOy5F8U5nEVMaihBs3SR10WiOM1iwPz5jIo8x/u11al+iEGZZrvg==",
+ "requires": {
+ "@types/react": "*"
+ }
+ },
"@types/resolve": {
"version": "1.17.1",
"resolved": "https://registry.npmjs.org/@types/resolve/-/resolve-1.17.1.tgz",
@@ -18229,6 +19090,11 @@
"resolved": "https://registry.npmjs.org/@types/retry/-/retry-0.12.0.tgz",
"integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA=="
},
+ "@types/scheduler": {
+ "version": "0.16.5",
+ "resolved": "https://registry.npmjs.org/@types/scheduler/-/scheduler-0.16.5.tgz",
+ "integrity": "sha512-s/FPdYRmZR8SjLWGMCuax7r3qCWQw9QKHzXVukAuuIJkXkDRwp+Pu5LMIVFi0Fxbav35WURicYr8u1QsoybnQw=="
+ },
"@types/serve-index": {
"version": "1.9.1",
"resolved": "https://registry.npmjs.org/@types/serve-index/-/serve-index-1.9.1.tgz",
@@ -19343,6 +20209,11 @@
"wrap-ansi": "^7.0.0"
}
},
+ "clsx": {
+ "version": "2.0.0",
+ "resolved": "https://registry.npmjs.org/clsx/-/clsx-2.0.0.tgz",
+ "integrity": "sha512-rQ1+kcj+ttHG0MKVGBUXwayCCF1oh39BF5COIpRzuCEv8Mwjv0XucrI2ExNTOn9IlLifGClWQcU9BrZORvtw6Q=="
+ },
"co": {
"version": "4.6.0",
"resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz",
@@ -19809,6 +20680,11 @@
}
}
},
+ "csstype": {
+ "version": "3.1.2",
+ "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.2.tgz",
+ "integrity": "sha512-I7K1Uu0MBPzaFKg4nI5Q7Vs2t+3gWWW648spaF+Rg7pI9ds18Ugn+lvg4SHczUdKlHI5LWBXyqfS8+DufyBsgQ=="
+ },
"damerau-levenshtein": {
"version": "1.0.8",
"resolved": "https://registry.npmjs.org/damerau-levenshtein/-/damerau-levenshtein-1.0.8.tgz",
@@ -19990,6 +20866,15 @@
"utila": "~0.4"
}
},
+ "dom-helpers": {
+ "version": "5.2.1",
+ "resolved": "https://registry.npmjs.org/dom-helpers/-/dom-helpers-5.2.1.tgz",
+ "integrity": "sha512-nRCa7CK3VTrM2NmGkIy4cbK7IZlgBE/PYMn55rrXefr5xXDP0LdtfPnblFDoVdcAfslJ7or6iqAUnx0CCGIWQA==",
+ "requires": {
+ "@babel/runtime": "^7.8.7",
+ "csstype": "^3.0.2"
+ }
+ },
"dom-serializer": {
"version": "1.4.1",
"resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-1.4.1.tgz",
@@ -20961,6 +21846,11 @@
"pkg-dir": "^4.1.0"
}
},
+ "find-root": {
+ "version": "1.1.0",
+ "resolved": "https://registry.npmjs.org/find-root/-/find-root-1.1.0.tgz",
+ "integrity": "sha512-NKfW6bec6GfKc0SGx1e07QZY9PE99u0Bft/0rzSD5k3sO/vwkVUpDUKVm5Gpp5Ue3YfShPFTX2070tDs5kB9Ng=="
+ },
"find-up": {
"version": "5.0.0",
"resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz",
@@ -21341,6 +22231,21 @@
"resolved": "https://registry.npmjs.org/he/-/he-1.2.0.tgz",
"integrity": "sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw=="
},
+ "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==",
+ "requires": {
+ "react-is": "^16.7.0"
+ },
+ "dependencies": {
+ "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=="
+ }
+ }
+ },
"hoopy": {
"version": "0.1.4",
"resolved": "https://registry.npmjs.org/hoopy/-/hoopy-0.1.4.tgz",
@@ -25119,6 +26024,23 @@
"resolved": "https://registry.npmjs.org/react-refresh/-/react-refresh-0.11.0.tgz",
"integrity": "sha512-F27qZr8uUqwhWZboondsPx8tnC3Ct3SxZA3V5WyEvujRyyNv0VYPhoBg1gZ8/MV5tubQp76Trw8lTv9hzRBa+A=="
},
+ "react-router": {
+ "version": "6.18.0",
+ "resolved": "https://registry.npmjs.org/react-router/-/react-router-6.18.0.tgz",
+ "integrity": "sha512-vk2y7Dsy8wI02eRRaRmOs9g2o+aE72YCx5q9VasT1N9v+lrdB79tIqrjMfByHiY5+6aYkH2rUa5X839nwWGPDg==",
+ "requires": {
+ "@remix-run/router": "1.11.0"
+ }
+ },
+ "react-router-dom": {
+ "version": "6.18.0",
+ "resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-6.18.0.tgz",
+ "integrity": "sha512-Ubrue4+Ercc/BoDkFQfc6og5zRQ4A8YxSO3Knsne+eRbZ+IepAsK249XBH/XaFuOYOYr3L3r13CXTLvYt5JDjw==",
+ "requires": {
+ "@remix-run/router": "1.11.0",
+ "react-router": "6.18.0"
+ }
+ },
"react-scripts": {
"version": "5.0.1",
"resolved": "https://registry.npmjs.org/react-scripts/-/react-scripts-5.0.1.tgz",
@@ -25174,6 +26096,17 @@
"workbox-webpack-plugin": "^6.4.1"
}
},
+ "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==",
+ "requires": {
+ "@babel/runtime": "^7.5.5",
+ "dom-helpers": "^5.0.1",
+ "loose-envify": "^1.4.0",
+ "prop-types": "^15.6.2"
+ }
+ },
"readable-stream": {
"version": "3.6.0",
"resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz",
@@ -25955,6 +26888,11 @@
"postcss-selector-parser": "^6.0.4"
}
},
+ "stylis": {
+ "version": "4.2.0",
+ "resolved": "https://registry.npmjs.org/stylis/-/stylis-4.2.0.tgz",
+ "integrity": "sha512-Orov6g6BB1sDfYgzWfTHDOxamtX1bE/zo104Dh9e6fqJ3PooipYyfJ0pUmrZO2wAvO8YbEyeFrkV91XTsGMSrw=="
+ },
"supports-color": {
"version": "5.5.0",
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
From efc1838cc25203404a95f5b56ccb562e2dbb513c Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 09:41:47 +0800
Subject: [PATCH 05/92] added input text and button elements
---
src/components/Home.js | 38 ++++++++++++++++++++++++++++++++++++++
1 file changed, 38 insertions(+)
create mode 100644 src/components/Home.js
diff --git a/src/components/Home.js b/src/components/Home.js
new file mode 100644
index 00000000..634b2a73
--- /dev/null
+++ b/src/components/Home.js
@@ -0,0 +1,38 @@
+import React, { useState } from "react";
+import { useNavigate } from "react-router-dom";
+
+const Home = () => {
+ const [username, setUsername] = useState("");
+ const navigate = useNavigate();
+
+ const handleChange = (event) => {
+ setUsername(event.target.value);
+ };
+
+ const handleClick = () => {
+ if (username === "") {
+ return;
+ }
+ navigate("/dashboard");
+ };
+
+ return (
+ <>
+ {/*EQUALS */}
+
+ >
+ );
+};
+
+export default Home;
From 70365bd3fdece85070039888cca072cec76598bd Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 09:42:42 +0800
Subject: [PATCH 06/92] added button element to navigate back to Home
---
src/components/Dashboard.js | 14 ++++++++++++++
1 file changed, 14 insertions(+)
create mode 100644 src/components/Dashboard.js
diff --git a/src/components/Dashboard.js b/src/components/Dashboard.js
new file mode 100644
index 00000000..92e67c09
--- /dev/null
+++ b/src/components/Dashboard.js
@@ -0,0 +1,14 @@
+import React from "react";
+import { useNavigate } from "react-router-dom";
+
+const Dashboard = () => {
+ const navigate = useNavigate();
+ return (
+ <>
+ Dashboard
+ navigate(-1)}>Back
+ >
+ );
+};
+
+export default Dashboard;
From c2becd37c830533815de50f19d59b56b92ac03a4 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 11:25:04 +0800
Subject: [PATCH 07/92] added a timer component to render current date
---
src/components/Timer.js | 16 ++++++++++++++++
1 file changed, 16 insertions(+)
create mode 100644 src/components/Timer.js
diff --git a/src/components/Timer.js b/src/components/Timer.js
new file mode 100644
index 00000000..f5fcf450
--- /dev/null
+++ b/src/components/Timer.js
@@ -0,0 +1,16 @@
+import React, { useState, useEffect } from "react";
+
+const Timer = () => {
+ const today = new Date();
+
+ const [currentTimeDate, setCurrentTimeDate] = useState(today);
+
+ useEffect(() => {
+ setInterval(() => {
+ setCurrentTimeDate(today);
+ }, 1000);
+ });
+ return <>{currentTimeDate.toDateString()}>;
+};
+
+export default Timer;
From 11a24aa3423b3bef43fd3da116405510a29b16f8 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 11:57:59 +0800
Subject: [PATCH 08/92] added localstorage to save username
---
src/components/Home.js | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/src/components/Home.js b/src/components/Home.js
index 634b2a73..dbd3c266 100644
--- a/src/components/Home.js
+++ b/src/components/Home.js
@@ -1,4 +1,4 @@
-import React, { useState } from "react";
+import React, { useState, useEffect } from "react";
import { useNavigate } from "react-router-dom";
const Home = () => {
@@ -16,6 +16,10 @@ const Home = () => {
navigate("/dashboard");
};
+ useEffect(() => {
+ localStorage.setItem("user", JSON.stringify(username));
+ }, [username]);
+
return (
<>
{/*EQUALS */}
From 5f677ddb62fb4f2e6b35c1d6a2fafaf6d7cb6cac Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 16:37:54 +0800
Subject: [PATCH 09/92] updated timer to display current date and time
---
src/components/Timer.js | 16 +++++++++-------
1 file changed, 9 insertions(+), 7 deletions(-)
diff --git a/src/components/Timer.js b/src/components/Timer.js
index f5fcf450..a50312ae 100644
--- a/src/components/Timer.js
+++ b/src/components/Timer.js
@@ -1,16 +1,18 @@
import React, { useState, useEffect } from "react";
const Timer = () => {
- const today = new Date();
-
- const [currentTimeDate, setCurrentTimeDate] = useState(today);
+ const [currentDate, setCurrentDate] = useState(new Date());
+ const currentTime = `${currentDate.getHours()} : ${currentDate.getMinutes()} : ${currentDate.getSeconds()}`;
useEffect(() => {
- setInterval(() => {
- setCurrentTimeDate(today);
- }, 1000);
+ setInterval(() => setCurrentDate(new Date()), 1000);
});
- return <>{currentTimeDate.toDateString()}>;
+
+ return (
+ <>
+ {`${currentDate.toDateString()}, ${currentTime}`}
+ >
+ );
};
export default Timer;
From e0eb89002921781db7a5ebff0771330b2062fbb4 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 16:40:36 +0800
Subject: [PATCH 10/92] updated greetings message
---
src/components/Greetings.js | 25 +++++++++++++++++++++++++
1 file changed, 25 insertions(+)
create mode 100644 src/components/Greetings.js
diff --git a/src/components/Greetings.js b/src/components/Greetings.js
new file mode 100644
index 00000000..69e86e76
--- /dev/null
+++ b/src/components/Greetings.js
@@ -0,0 +1,25 @@
+import React from "react";
+
+const Greetings = () => {
+ const today = new Date();
+ const currHour = today.getHours();
+ let greetings;
+
+ const greet = () => {
+ if (currHour >= 6 && currHour < 12) {
+ greetings = "Good Morning";
+ } else if (currHour >= 12 && currHour < 17) {
+ greetings = "Good Afternoon";
+ } else {
+ greetings = "Good Evening";
+ }
+ return greetings;
+ };
+ return (
+ <>
+ {greet()}
+ >
+ );
+};
+
+export default Greetings;
From b00d5565f144173ed10f83a65dff60a031710489 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 18:16:18 +0800
Subject: [PATCH 11/92] added logic to hide and unhide form
---
src/components/Dashboard.js | 30 ++++++++++++++++++++++++++++--
1 file changed, 28 insertions(+), 2 deletions(-)
diff --git a/src/components/Dashboard.js b/src/components/Dashboard.js
index 92e67c09..e17b0311 100644
--- a/src/components/Dashboard.js
+++ b/src/components/Dashboard.js
@@ -1,11 +1,37 @@
-import React from "react";
+import React, { useState } from "react";
+
import { useNavigate } from "react-router-dom";
+import Timer from "../components/Timer";
+import Greetings from "./Greetings";
+
+import Form from "./Form";
const Dashboard = () => {
+ const [show, setShow] = useState(false);
+ console.log(show);
const navigate = useNavigate();
+
+ const getName = () => {
+ return JSON.parse(localStorage.getItem("user"));
+ };
+
return (
<>
- Dashboard
+ {getName()}
+
+
+
+ What would you like to do today?
+ {}
+ setShow(true)}>Add a Trip
+
+ Ongoing trips
+ {!show ? (
+ This space is currently empty! Add a trip to start.
+ ) : (
+
+ )}
+
navigate(-1)}>Back
>
);
From c4c814ee23e105c4b0056669fb82f299a110606d Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 4 Nov 2023 21:21:19 +0800
Subject: [PATCH 12/92] imported Button component for use
---
src/components/Dashboard.js | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/src/components/Dashboard.js b/src/components/Dashboard.js
index e17b0311..ad64c128 100644
--- a/src/components/Dashboard.js
+++ b/src/components/Dashboard.js
@@ -5,6 +5,7 @@ import Timer from "../components/Timer";
import Greetings from "./Greetings";
import Form from "./Form";
+import Button from "./Button";
const Dashboard = () => {
const [show, setShow] = useState(false);
@@ -23,7 +24,7 @@ const Dashboard = () => {
What would you like to do today?
{}
- setShow(true)}>Add a Trip
+ setShow(true)} value="Add a Trip" />
Ongoing trips
{!show ? (
From 78fd366575a9aff094cb54c5bbe21b2880dbaa25 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 5 Nov 2023 14:38:44 +0800
Subject: [PATCH 13/92] created todo list
---
src/components/TodoList.js | 20 ++++++++++++++++++++
1 file changed, 20 insertions(+)
create mode 100644 src/components/TodoList.js
diff --git a/src/components/TodoList.js b/src/components/TodoList.js
new file mode 100644
index 00000000..2b63418a
--- /dev/null
+++ b/src/components/TodoList.js
@@ -0,0 +1,20 @@
+import React from "react";
+
+const ToDoList = ({ toDoList, deleteFriends }) => {
+ return (
+ <>
+
+ {toDoList.map((todo, index) => (
+ <>
+ {todo}
+ deleteFriends(index)}>
+ Delete
+
+ >
+ ))}
+
+ >
+ );
+};
+
+export default ToDoList;
From 663a323c326706c686217e211e3ed56cfda933cc Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 5 Nov 2023 14:39:15 +0800
Subject: [PATCH 14/92] updated delete functionality for todolist
---
src/components/Form.js | 50 ++++++++++++++++++++++++++++++++++++++++++
1 file changed, 50 insertions(+)
create mode 100644 src/components/Form.js
diff --git a/src/components/Form.js b/src/components/Form.js
new file mode 100644
index 00000000..db751092
--- /dev/null
+++ b/src/components/Form.js
@@ -0,0 +1,50 @@
+import React, { useState } from "react";
+import Button from "./Button";
+import ToDoList from "./TodoList";
+
+const Form = () => {
+ const [tripname, setTripname] = useState("");
+ const [friends, setFriends] = useState("");
+ const [items, setItems] = useState([]);
+
+ const addFriends = () => {
+ if (friends.length) {
+ setItems([...items, friends]);
+ setFriends("");
+ }
+ };
+
+ const deleteFriends = (todoIndex) => {
+ const newTodos = items.filter((_, index) => index !== todoIndex);
+ setItems(newTodos);
+ };
+
+ return (
+ <>
+
+ >
+ );
+};
+
+export default Form;
From eb7c04285c6631763a0f9fbeb1e48a2764ada234 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 5 Nov 2023 15:15:33 +0800
Subject: [PATCH 15/92] passed in username as props
---
src/components/Greetings.js | 5 +++--
1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/src/components/Greetings.js b/src/components/Greetings.js
index 69e86e76..e6005186 100644
--- a/src/components/Greetings.js
+++ b/src/components/Greetings.js
@@ -1,8 +1,9 @@
import React from "react";
-const Greetings = () => {
+const Greetings = ({ username }) => {
const today = new Date();
const currHour = today.getHours();
+
let greetings;
const greet = () => {
@@ -17,7 +18,7 @@ const Greetings = () => {
};
return (
<>
- {greet()}
+ {`${greet()} ${username}!`}
>
);
};
From 4fa09dbbeac9e2ae26b4849f9b22cbe6220bfacc Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 5 Nov 2023 15:20:11 +0800
Subject: [PATCH 16/92] updated greeting
---
src/components/Greetings.js | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/src/components/Greetings.js b/src/components/Greetings.js
index e6005186..9585593a 100644
--- a/src/components/Greetings.js
+++ b/src/components/Greetings.js
@@ -18,7 +18,8 @@ const Greetings = ({ username }) => {
};
return (
<>
- {`${greet()} ${username}!`}
+ {`${greet()} ${username}! `}
+ What would you like to do today?
>
);
};
From 5c13a907207d58188dde6e5c01cd845e361c6144 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Mon, 6 Nov 2023 09:00:36 +0800
Subject: [PATCH 17/92] added conditions to reflect before and after trip form
is created
---
src/components/Dashboard.js | 54 ++++++++++++++++++++++++-------------
1 file changed, 36 insertions(+), 18 deletions(-)
diff --git a/src/components/Dashboard.js b/src/components/Dashboard.js
index ad64c128..5bdc8801 100644
--- a/src/components/Dashboard.js
+++ b/src/components/Dashboard.js
@@ -1,39 +1,57 @@
import React, { useState } from "react";
-import { useNavigate } from "react-router-dom";
import Timer from "../components/Timer";
import Greetings from "./Greetings";
import Form from "./Form";
+
import Button from "./Button";
+import CreatedForm from "./CreatedForm";
const Dashboard = () => {
- const [show, setShow] = useState(false);
- console.log(show);
- const navigate = useNavigate();
+ const [showForm, setShowForm] = useState(false);
+ const [showCreatedForm, setShowCreatedForm] = useState(false);
- const getName = () => {
+ const getUsername = () => {
return JSON.parse(localStorage.getItem("user"));
};
+ const getCreatedFormNames = () => {
+ return JSON.parse(localStorage.getItem("stateObject"));
+ };
+
+ // useEffect(() => {
+ // return ()=> setShowForm(false);
+ // // });
+ // if (showCreatedForm) {
+ // return setShowForm(false);
+ // }
+
return (
<>
- {getName()}
+ {getUsername()}
-
-
- What would you like to do today?
- {}
- setShow(true)} value="Add a Trip" />
-
- Ongoing trips
- {!show ? (
- This space is currently empty! Add a trip to start.
+
+ Ongoing Trips
+ {!showForm && !showCreatedForm ? (
+ <>
+ setShowForm(true)}>Add a trip
+ This space is currently empty! Add a trip to start
+ >
+ ) : showForm && !showCreatedForm ? (
+ <>
+
+ {
+ setShowCreatedForm(true);
+ }}
+ >
+ Create Trip
+
+ >
) : (
-
+
)}
-
- navigate(-1)}>Back
>
);
};
From 40eaef16e7024de2ce6e8451d95c54d37276b413 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Mon, 6 Nov 2023 09:01:18 +0800
Subject: [PATCH 18/92] updated form list
---
src/components/Form.js | 24 ++++++++++++++++--------
1 file changed, 16 insertions(+), 8 deletions(-)
diff --git a/src/components/Form.js b/src/components/Form.js
index db751092..e1076016 100644
--- a/src/components/Form.js
+++ b/src/components/Form.js
@@ -1,6 +1,6 @@
-import React, { useState } from "react";
+import React, { useState, useEffect } from "react";
import Button from "./Button";
-import ToDoList from "./TodoList";
+import FriendList from "./FriendList";
const Form = () => {
const [tripname, setTripname] = useState("");
@@ -14,11 +14,20 @@ const Form = () => {
}
};
- const deleteFriends = (todoIndex) => {
- const newTodos = items.filter((_, index) => index !== todoIndex);
- setItems(newTodos);
+ const deleteFriends = (itemIndex) => {
+ const newItem = items.filter((_, index) => index !== itemIndex);
+ setItems(newItem);
};
+ useEffect(() => {
+ let stateObject = {
+ tripname: tripname,
+ items: items,
+ };
+
+ localStorage.setItem("stateObject", JSON.stringify(stateObject));
+ }, [tripname, items]);
+
return (
<>
>
);
From bfbf1f886c4a4c20dd7402614c358f4983ceffe0 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Mon, 6 Nov 2023 09:01:40 +0800
Subject: [PATCH 19/92] updated list
---
src/components/FriendList.js | 20 ++++++++++++++++++++
1 file changed, 20 insertions(+)
create mode 100644 src/components/FriendList.js
diff --git a/src/components/FriendList.js b/src/components/FriendList.js
new file mode 100644
index 00000000..f4ab7ff8
--- /dev/null
+++ b/src/components/FriendList.js
@@ -0,0 +1,20 @@
+import React from "react";
+
+const FriendList = ({ friendList, deleteFriends }) => {
+ return (
+ <>
+
+ {friendList.map((friend, index) => (
+ <>
+ {friend}
+ deleteFriends(index)}>
+ Delete
+
+ >
+ ))}
+
+ >
+ );
+};
+
+export default FriendList;
From a81d5f8b41b41d7233b3d7aa5617425f8dbabd6c Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Mon, 6 Nov 2023 09:03:00 +0800
Subject: [PATCH 20/92] added a created form
---
src/components/CreatedForm.js | 12 ++++++++++++
1 file changed, 12 insertions(+)
create mode 100644 src/components/CreatedForm.js
diff --git a/src/components/CreatedForm.js b/src/components/CreatedForm.js
new file mode 100644
index 00000000..88dccdf1
--- /dev/null
+++ b/src/components/CreatedForm.js
@@ -0,0 +1,12 @@
+import React from "react";
+
+const CreatedForm = ({ getNames }) => {
+ return (
+ <>
+ {getNames.tripname}
+ {getNames.items}
+ >
+ );
+};
+
+export default CreatedForm;
From d78b7d2108f8df6ca531c8b49286226faace5a52 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Mon, 6 Nov 2023 21:08:42 +0800
Subject: [PATCH 21/92] created a list to add, delete and display transactions
---
src/components/PriceDescriptionList.js | 23 +++++++++++++++++++++++
1 file changed, 23 insertions(+)
create mode 100644 src/components/PriceDescriptionList.js
diff --git a/src/components/PriceDescriptionList.js b/src/components/PriceDescriptionList.js
new file mode 100644
index 00000000..a97b33ac
--- /dev/null
+++ b/src/components/PriceDescriptionList.js
@@ -0,0 +1,23 @@
+import React from "react";
+
+const PriceDescriptionList = ({ details, deleteItems }) => {
+ console.log(details);
+ return (
+ <>
+
+ {details.map((detail, index) => (
+ <>
+
+ {detail.description} --- {detail.price} - {detail.payer}
+
+ deleteItems(index)}>
+ Delete
+
+ >
+ ))}
+
+ >
+ );
+};
+
+export default PriceDescriptionList;
From f70dc54a4c02b6901531e90002f2f4edcf366fb9 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Wed, 8 Nov 2023 11:14:12 +0800
Subject: [PATCH 22/92] added add and delete buttons for transactions
---
src/components/ItemForm.js | 76 ++++++++++++++++++++++++++++++++++++++
1 file changed, 76 insertions(+)
create mode 100644 src/components/ItemForm.js
diff --git a/src/components/ItemForm.js b/src/components/ItemForm.js
new file mode 100644
index 00000000..1a1e5824
--- /dev/null
+++ b/src/components/ItemForm.js
@@ -0,0 +1,76 @@
+import React, { useState } from "react";
+import Button from "./Button";
+import PriceDescriptionList from "./PriceDescriptionList";
+
+const ItemForm = (props) => {
+ const [payer, setPayer] = useState([props.friendsName[0]]);
+ const [description, setDescription] = useState("");
+ const [price, setPrice] = useState("");
+ const [details, setDetails] = useState([]);
+
+ let changes = {
+ description: description,
+ price: price,
+ payer: payer,
+ };
+
+ console.log(details);
+
+ const addItems = () => {
+ let storage = [];
+ if (description.length && price.length) {
+ console.log(details);
+ setDetails([...details, changes]);
+ console.log(details);
+ setPayer([props.friendsName[0]]);
+
+ setDescription("");
+ setPrice("");
+ }
+
+ JSON.parse(localStorage.getItem("transactions"));
+
+ storage.push(...details, changes);
+ localStorage.setItem("transactions", JSON.stringify(storage));
+ localStorage.getItem("transactions");
+ };
+
+ const deleteItems = (detailIndex) => {
+ const newDetails = details.filter((_, index) => index !== detailIndex);
+ setDetails(newDetails);
+ };
+
+ return (
+ <>
+ Item description:
+ setDescription(e.target.value)}
+ name="description"
+ />
+ Price:
+ setPrice(e.target.value)}
+ name="price"
+ />
+
+ setPayer(e.target.value)}
+ name="payer"
+ >
+ {props.friendsName.map((name, index) => (
+ {name}
+ ))}
+ {" "}
+ paid
+ Add
+
+ >
+ );
+};
+
+export default ItemForm;
From daedacaabdc013312bd0e38a5128171bf9e084e1 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Wed, 8 Nov 2023 18:50:03 +0800
Subject: [PATCH 23/92] added a function to sum up each payer contribution and
push it into an array
---
src/components/GetPrices.js | 17 +++++++++++++++++
1 file changed, 17 insertions(+)
create mode 100644 src/components/GetPrices.js
diff --git a/src/components/GetPrices.js b/src/components/GetPrices.js
new file mode 100644
index 00000000..4d4d686f
--- /dev/null
+++ b/src/components/GetPrices.js
@@ -0,0 +1,17 @@
+const getAllPrices = (entireData, entireFriends) => {
+ let allPrices = [];
+
+ for (let i = 0; i < entireFriends.length; i += 1) {
+ let sumOfIndividualPayer = 0;
+ for (let j = 0; j < entireData.length; j += 1) {
+ if (entireFriends[i] === entireData[j].payer) {
+ sumOfIndividualPayer += Number(entireData[j].price);
+ console.log(sumOfIndividualPayer);
+ }
+ }
+ allPrices.push(sumOfIndividualPayer);
+ }
+ return allPrices;
+};
+
+export default getAllPrices;
From 189470ea67cb4a45a8e42ae1ce34d23e8a1e6a0a Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Thu, 9 Nov 2023 11:35:29 +0800
Subject: [PATCH 24/92] added flex properties and background color
---
src/App.css | 8 ++++++++
1 file changed, 8 insertions(+)
diff --git a/src/App.css b/src/App.css
index 97b7c578..7cf694f9 100644
--- a/src/App.css
+++ b/src/App.css
@@ -1,5 +1,13 @@
+body {
+ background-color: #ffab40;
+}
+
.App {
text-align: center;
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ height: 700px;
}
.App-logo {
From 77580c272e4183b23c0fdf2e917ce09be2c0c649 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Thu, 9 Nov 2023 14:14:32 +0800
Subject: [PATCH 25/92] updated component with mui and localStorage
---
src/components/Home.js | 73 +++++++++++++++++++++++++++++++++---------
1 file changed, 58 insertions(+), 15 deletions(-)
diff --git a/src/components/Home.js b/src/components/Home.js
index dbd3c266..1864424f 100644
--- a/src/components/Home.js
+++ b/src/components/Home.js
@@ -1,5 +1,22 @@
import React, { useState, useEffect } from "react";
import { useNavigate } from "react-router-dom";
+import {
+ Button,
+ TextField,
+ Typography,
+ Stack,
+ InputAdornment,
+} from "@mui/material";
+import { createTheme } from "@mui/material/styles";
+import { AccountCircle } from "@mui/icons-material";
+
+const theme = createTheme({
+ palette: {
+ primary: {
+ main: "#00c853",
+ },
+ },
+});
const Home = () => {
const [username, setUsername] = useState("");
@@ -13,28 +30,54 @@ const Home = () => {
if (username === "") {
return;
}
+ // store username in local storage
+ localStorage.setItem("user", JSON.stringify(username));
navigate("/dashboard");
};
useEffect(() => {
- localStorage.setItem("user", JSON.stringify(username));
- }, [username]);
+ const userData = localStorage.getItem("user");
+ if (userData !== null) {
+ setUsername(JSON.parse(userData));
+ }
+ }, []);
return (
<>
- {/*EQUALS */}
-
+
+
+ Hey there!
+
+
+
+
+
+ ),
+ }}
+ >
+
+
+
+ Get Started
+
+
+
>
);
};
From 70429ef5a1a458de3b7358926f3eb5027176dfaf Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Thu, 9 Nov 2023 14:16:34 +0800
Subject: [PATCH 26/92] installed mui
---
package.json | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/package.json b/package.json
index 681597c3..ddd39858 100644
--- a/package.json
+++ b/package.json
@@ -5,7 +5,8 @@
"dependencies": {
"@emotion/react": "^11.11.1",
"@emotion/styled": "^11.11.0",
- "@mui/material": "^5.14.16",
+ "@mui/icons-material": "^5.14.16",
+ "@mui/material": "^5.14.17",
"react": "^18.1.0",
"react-dom": "^18.1.0",
"react-router-dom": "^6.18.0",
From 6feb5764c3a03da78488fed00d1ae5e6f875c8bf Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Thu, 9 Nov 2023 14:16:53 +0800
Subject: [PATCH 27/92] installed mui
---
package-lock.json | 212 +++++++++++++++++++++++++++-------------------
1 file changed, 123 insertions(+), 89 deletions(-)
diff --git a/package-lock.json b/package-lock.json
index 9bd5de8d..12573cd8 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -10,7 +10,8 @@
"dependencies": {
"@emotion/react": "^11.11.1",
"@emotion/styled": "^11.11.0",
- "@mui/material": "^5.14.16",
+ "@mui/icons-material": "^5.14.16",
+ "@mui/material": "^5.14.17",
"react": "^18.1.0",
"react-dom": "^18.1.0",
"react-router-dom": "^6.18.0",
@@ -2236,9 +2237,9 @@
}
},
"node_modules/@floating-ui/react-dom": {
- "version": "2.0.2",
- "resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.0.2.tgz",
- "integrity": "sha512-5qhlDvjaLmAst/rKb3VdlCinwTF4EYMiVxuuc/HVUjs46W0zgtbMmAZ1UTsDrRTxRmUEzl92mOtWbeeXL26lSQ==",
+ "version": "2.0.3",
+ "resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.0.3.tgz",
+ "integrity": "sha512-wOoKUw2P24/OXbNr3bbCqWgoltsyY7lFBDPVtjj/V4WDIJ5hja2C/r+CoWmS+Y75Ahndds3wa7eJRhnJxTCJaQ==",
"dependencies": {
"@floating-ui/dom": "^1.5.1"
},
@@ -2981,14 +2982,14 @@
"integrity": "sha512-nkalE/f1RvRGChwBnEIoBfSEYOXnCRdleKuv6+lePbMDrMZXeDQnqak5XDOeBgrPPyPfAdcCu/B5z+v3VhplGg=="
},
"node_modules/@mui/base": {
- "version": "5.0.0-beta.22",
- "resolved": "https://registry.npmjs.org/@mui/base/-/base-5.0.0-beta.22.tgz",
- "integrity": "sha512-l4asGID5tmyerx9emJfXOKLyXzaBtdXNIFE3M+IrSZaFtGFvaQKHhc3+nxxSxPf1+G44psjczM0ekRQCdXx9HA==",
+ "version": "5.0.0-beta.23",
+ "resolved": "https://registry.npmjs.org/@mui/base/-/base-5.0.0-beta.23.tgz",
+ "integrity": "sha512-9L8SQUGAWtd/Qi7Qem26+oSSgpY7f2iQTuvcz/rsGpyZjSomMMO6lwYeQSA0CpWM7+aN7eGoSY/WV6wxJiIxXw==",
"dependencies": {
"@babel/runtime": "^7.23.2",
"@floating-ui/react-dom": "^2.0.2",
"@mui/types": "^7.2.8",
- "@mui/utils": "^5.14.16",
+ "@mui/utils": "^5.14.17",
"@popperjs/core": "^2.11.8",
"clsx": "^2.0.0",
"prop-types": "^15.8.1"
@@ -3012,25 +3013,50 @@
}
},
"node_modules/@mui/core-downloads-tracker": {
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/core-downloads-tracker/-/core-downloads-tracker-5.14.17.tgz",
+ "integrity": "sha512-eE0uxrpJAEL2ZXkeGLKg8HQDafsiXY+6eNpP4lcv3yIjFfGbU6Hj9/P7Adt8jpU+6JIhmxvILGj2r27pX+zdrQ==",
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/mui"
+ }
+ },
+ "node_modules/@mui/icons-material": {
"version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/core-downloads-tracker/-/core-downloads-tracker-5.14.16.tgz",
- "integrity": "sha512-97isBjzH2v1K7oB4UH2f4NOkBShOynY6dhnoR2XlUk/g6bb7ZBv2I3D1hvvqPtpEigKu93e7f/jAYr5d9LOc5w==",
+ "resolved": "https://registry.npmjs.org/@mui/icons-material/-/icons-material-5.14.16.tgz",
+ "integrity": "sha512-wmOgslMEGvbHZjFLru8uH5E+pif/ciXAvKNw16q6joK6EWVWU5rDYWFknDaZhCvz8ZE/K8ZnJQ+lMG6GgHzXbg==",
+ "dependencies": {
+ "@babel/runtime": "^7.23.2"
+ },
+ "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/material": {
- "version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/material/-/material-5.14.16.tgz",
- "integrity": "sha512-W4zZ4vnxgGk6/HqBwgsDHKU7x2l2NhX+r8gAwfg58Rhu3ikfY7NkIS6y8Gl3NkATc4GG1FNaGjjpQKfJx3U6Jw==",
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/material/-/material-5.14.17.tgz",
+ "integrity": "sha512-+y0VeOLWfEA4Z98We/UH6KCo8+f2HLZDK45FY+sJf8kSojLy3VntadKtC/u0itqnXXb1Pr4wKB2tSIBW02zY4Q==",
"dependencies": {
"@babel/runtime": "^7.23.2",
- "@mui/base": "5.0.0-beta.22",
- "@mui/core-downloads-tracker": "^5.14.16",
- "@mui/system": "^5.14.16",
+ "@mui/base": "5.0.0-beta.23",
+ "@mui/core-downloads-tracker": "^5.14.17",
+ "@mui/system": "^5.14.17",
"@mui/types": "^7.2.8",
- "@mui/utils": "^5.14.16",
+ "@mui/utils": "^5.14.17",
"@types/react-transition-group": "^4.4.8",
"clsx": "^2.0.0",
"csstype": "^3.1.2",
@@ -3070,12 +3096,12 @@
"integrity": "sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w=="
},
"node_modules/@mui/private-theming": {
- "version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/private-theming/-/private-theming-5.14.16.tgz",
- "integrity": "sha512-FNlL0pTSEBh8nXsVWreCHDSHk+jG8cBx1sxRbT8JVtL+PYbYPi802zfV4B00Kkf0LNRVRvAVQwojMWSR/MYGng==",
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/private-theming/-/private-theming-5.14.17.tgz",
+ "integrity": "sha512-u4zxsCm9xmQrlhVPug+Ccrtsjv7o2+rehvrgHoh0siSguvVgVQq5O3Hh10+tp/KWQo2JR4/nCEwquSXgITS1+g==",
"dependencies": {
"@babel/runtime": "^7.23.2",
- "@mui/utils": "^5.14.16",
+ "@mui/utils": "^5.14.17",
"prop-types": "^15.8.1"
},
"engines": {
@@ -3096,9 +3122,9 @@
}
},
"node_modules/@mui/styled-engine": {
- "version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/styled-engine/-/styled-engine-5.14.16.tgz",
- "integrity": "sha512-FfvYvTG/Zd+KXMMImbcMYEeQAbONGuX5Vx3gBmmtB6KyA7Mvm9Pma1ly3R0gc44yeoFd+2wBjn1feS8h42HW5w==",
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/styled-engine/-/styled-engine-5.14.17.tgz",
+ "integrity": "sha512-AqpVjBEA7wnBvKPW168bNlqB6EN7HxTjLOY7oi275AzD/b1C7V0wqELy6NWoJb2yya5sRf7ENf4iNi3+T5cOgw==",
"dependencies": {
"@babel/runtime": "^7.23.2",
"@emotion/cache": "^11.11.0",
@@ -3127,15 +3153,15 @@
}
},
"node_modules/@mui/system": {
- "version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/system/-/system-5.14.16.tgz",
- "integrity": "sha512-uKnPfsDqDs8bbN54TviAuoGWOmFiQLwNZ3Wvj+OBkJCzwA6QnLb/sSeCB7Pk3ilH4h4jQ0BHtbR+Xpjy9wlOuA==",
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/system/-/system-5.14.17.tgz",
+ "integrity": "sha512-Ccz3XlbCqka6DnbHfpL3o3TfOeWQPR+ewvNAgm8gnS9M0yVMmzzmY6z0w/C1eebb+7ZP7IoLUj9vojg/GBaTPg==",
"dependencies": {
"@babel/runtime": "^7.23.2",
- "@mui/private-theming": "^5.14.16",
- "@mui/styled-engine": "^5.14.16",
+ "@mui/private-theming": "^5.14.17",
+ "@mui/styled-engine": "^5.14.17",
"@mui/types": "^7.2.8",
- "@mui/utils": "^5.14.16",
+ "@mui/utils": "^5.14.17",
"clsx": "^2.0.0",
"csstype": "^3.1.2",
"prop-types": "^15.8.1"
@@ -3179,9 +3205,9 @@
}
},
"node_modules/@mui/utils": {
- "version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/utils/-/utils-5.14.16.tgz",
- "integrity": "sha512-3xV31GposHkwRbQzwJJuooWpK2ybWdEdeUPtRjv/6vjomyi97F3+68l+QVj9tPTvmfSbr2sx5c/NuvDulrdRmA==",
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/utils/-/utils-5.14.17.tgz",
+ "integrity": "sha512-yxnWgSS4J6DMFPw2Dof85yBkG02VTbEiqsikymMsnZnXDurtVGTIhlNuV24GTmFTuJMzEyTTU9UF+O7zaL8LEQ==",
"dependencies": {
"@babel/runtime": "^7.23.2",
"@types/prop-types": "^15.7.9",
@@ -3830,9 +3856,9 @@
"integrity": "sha512-G/AdOadiZhnJp0jXCaBQU449W2h716OW/EoXeYkCytxKL06X1WCXB4DZpp8TpZ8eyIJVS1cw4lrlkkSYU21cDw=="
},
"node_modules/@types/prop-types": {
- "version": "15.7.9",
- "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.9.tgz",
- "integrity": "sha512-n1yyPsugYNSmHgxDFjicaI2+gCNjsBck8UX9kuofAKlc0h1bL+20oSF72KeNaW2DUlesbEVCFgyV2dPGTiY42g=="
+ "version": "15.7.10",
+ "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.10.tgz",
+ "integrity": "sha512-mxSnDQxPqsZxmeShFH+uwQ4kO4gcJcGahjjMFeLbKE95IAZiiZyiEepGZjtXJ7hN/yfu0bu9xN2ajcU0JcxX6A=="
},
"node_modules/@types/q": {
"version": "1.5.5",
@@ -3850,9 +3876,9 @@
"integrity": "sha512-EEhsLsD6UsDM1yFhAvy0Cjr6VwmpMWqFBCb9w07wVugF7w9nfajxLuVmngTIpgS6svCnm6Vaw+MZhoDCKnOfsw=="
},
"node_modules/@types/react": {
- "version": "18.2.34",
- "resolved": "https://registry.npmjs.org/@types/react/-/react-18.2.34.tgz",
- "integrity": "sha512-U6eW/alrRk37FU/MS2RYMjx0Va2JGIVXELTODaTIYgvWGCV4Y4TfTUzG8DdmpDNIT0Xpj/R7GfyHOJJrDttcvg==",
+ "version": "18.2.37",
+ "resolved": "https://registry.npmjs.org/@types/react/-/react-18.2.37.tgz",
+ "integrity": "sha512-RGAYMi2bhRgEXT3f4B92WTohopH6bIXw05FuGlmJEnv/omEn190+QYEIYxIAuIBdKgboYYdVved2p1AxZVQnaw==",
"dependencies": {
"@types/prop-types": "*",
"@types/scheduler": "*",
@@ -3860,9 +3886,9 @@
}
},
"node_modules/@types/react-transition-group": {
- "version": "4.4.8",
- "resolved": "https://registry.npmjs.org/@types/react-transition-group/-/react-transition-group-4.4.8.tgz",
- "integrity": "sha512-QmQ22q+Pb+HQSn04NL3HtrqHwYMf4h3QKArOy5F8U5nEVMaihBs3SR10WiOM1iwPz5jIo8x/u11al+iEGZZrvg==",
+ "version": "4.4.9",
+ "resolved": "https://registry.npmjs.org/@types/react-transition-group/-/react-transition-group-4.4.9.tgz",
+ "integrity": "sha512-ZVNmWumUIh5NhH8aMD9CR2hdW0fNuYInlocZHaZ+dgk/1K49j1w/HoAuK1ki+pgscQrOFRTlXeoURtuzEkV3dg==",
"dependencies": {
"@types/react": "*"
}
@@ -3881,9 +3907,9 @@
"integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA=="
},
"node_modules/@types/scheduler": {
- "version": "0.16.5",
- "resolved": "https://registry.npmjs.org/@types/scheduler/-/scheduler-0.16.5.tgz",
- "integrity": "sha512-s/FPdYRmZR8SjLWGMCuax7r3qCWQw9QKHzXVukAuuIJkXkDRwp+Pu5LMIVFi0Fxbav35WURicYr8u1QsoybnQw=="
+ "version": "0.16.6",
+ "resolved": "https://registry.npmjs.org/@types/scheduler/-/scheduler-0.16.6.tgz",
+ "integrity": "sha512-Vlktnchmkylvc9SnwwwozTv04L/e1NykF5vgoQ0XTmI8DD+wxfjQuHuvHS3p0r2jz2x2ghPs2h1FVeDirIteWA=="
},
"node_modules/@types/serve-index": {
"version": "1.9.1",
@@ -17942,9 +17968,9 @@
}
},
"@floating-ui/react-dom": {
- "version": "2.0.2",
- "resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.0.2.tgz",
- "integrity": "sha512-5qhlDvjaLmAst/rKb3VdlCinwTF4EYMiVxuuc/HVUjs46W0zgtbMmAZ1UTsDrRTxRmUEzl92mOtWbeeXL26lSQ==",
+ "version": "2.0.3",
+ "resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.0.3.tgz",
+ "integrity": "sha512-wOoKUw2P24/OXbNr3bbCqWgoltsyY7lFBDPVtjj/V4WDIJ5hja2C/r+CoWmS+Y75Ahndds3wa7eJRhnJxTCJaQ==",
"requires": {
"@floating-ui/dom": "^1.5.1"
}
@@ -18495,35 +18521,43 @@
"integrity": "sha512-nkalE/f1RvRGChwBnEIoBfSEYOXnCRdleKuv6+lePbMDrMZXeDQnqak5XDOeBgrPPyPfAdcCu/B5z+v3VhplGg=="
},
"@mui/base": {
- "version": "5.0.0-beta.22",
- "resolved": "https://registry.npmjs.org/@mui/base/-/base-5.0.0-beta.22.tgz",
- "integrity": "sha512-l4asGID5tmyerx9emJfXOKLyXzaBtdXNIFE3M+IrSZaFtGFvaQKHhc3+nxxSxPf1+G44psjczM0ekRQCdXx9HA==",
+ "version": "5.0.0-beta.23",
+ "resolved": "https://registry.npmjs.org/@mui/base/-/base-5.0.0-beta.23.tgz",
+ "integrity": "sha512-9L8SQUGAWtd/Qi7Qem26+oSSgpY7f2iQTuvcz/rsGpyZjSomMMO6lwYeQSA0CpWM7+aN7eGoSY/WV6wxJiIxXw==",
"requires": {
"@babel/runtime": "^7.23.2",
"@floating-ui/react-dom": "^2.0.2",
"@mui/types": "^7.2.8",
- "@mui/utils": "^5.14.16",
+ "@mui/utils": "^5.14.17",
"@popperjs/core": "^2.11.8",
"clsx": "^2.0.0",
"prop-types": "^15.8.1"
}
},
"@mui/core-downloads-tracker": {
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/core-downloads-tracker/-/core-downloads-tracker-5.14.17.tgz",
+ "integrity": "sha512-eE0uxrpJAEL2ZXkeGLKg8HQDafsiXY+6eNpP4lcv3yIjFfGbU6Hj9/P7Adt8jpU+6JIhmxvILGj2r27pX+zdrQ=="
+ },
+ "@mui/icons-material": {
"version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/core-downloads-tracker/-/core-downloads-tracker-5.14.16.tgz",
- "integrity": "sha512-97isBjzH2v1K7oB4UH2f4NOkBShOynY6dhnoR2XlUk/g6bb7ZBv2I3D1hvvqPtpEigKu93e7f/jAYr5d9LOc5w=="
+ "resolved": "https://registry.npmjs.org/@mui/icons-material/-/icons-material-5.14.16.tgz",
+ "integrity": "sha512-wmOgslMEGvbHZjFLru8uH5E+pif/ciXAvKNw16q6joK6EWVWU5rDYWFknDaZhCvz8ZE/K8ZnJQ+lMG6GgHzXbg==",
+ "requires": {
+ "@babel/runtime": "^7.23.2"
+ }
},
"@mui/material": {
- "version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/material/-/material-5.14.16.tgz",
- "integrity": "sha512-W4zZ4vnxgGk6/HqBwgsDHKU7x2l2NhX+r8gAwfg58Rhu3ikfY7NkIS6y8Gl3NkATc4GG1FNaGjjpQKfJx3U6Jw==",
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/material/-/material-5.14.17.tgz",
+ "integrity": "sha512-+y0VeOLWfEA4Z98We/UH6KCo8+f2HLZDK45FY+sJf8kSojLy3VntadKtC/u0itqnXXb1Pr4wKB2tSIBW02zY4Q==",
"requires": {
"@babel/runtime": "^7.23.2",
- "@mui/base": "5.0.0-beta.22",
- "@mui/core-downloads-tracker": "^5.14.16",
- "@mui/system": "^5.14.16",
+ "@mui/base": "5.0.0-beta.23",
+ "@mui/core-downloads-tracker": "^5.14.17",
+ "@mui/system": "^5.14.17",
"@mui/types": "^7.2.8",
- "@mui/utils": "^5.14.16",
+ "@mui/utils": "^5.14.17",
"@types/react-transition-group": "^4.4.8",
"clsx": "^2.0.0",
"csstype": "^3.1.2",
@@ -18540,19 +18574,19 @@
}
},
"@mui/private-theming": {
- "version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/private-theming/-/private-theming-5.14.16.tgz",
- "integrity": "sha512-FNlL0pTSEBh8nXsVWreCHDSHk+jG8cBx1sxRbT8JVtL+PYbYPi802zfV4B00Kkf0LNRVRvAVQwojMWSR/MYGng==",
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/private-theming/-/private-theming-5.14.17.tgz",
+ "integrity": "sha512-u4zxsCm9xmQrlhVPug+Ccrtsjv7o2+rehvrgHoh0siSguvVgVQq5O3Hh10+tp/KWQo2JR4/nCEwquSXgITS1+g==",
"requires": {
"@babel/runtime": "^7.23.2",
- "@mui/utils": "^5.14.16",
+ "@mui/utils": "^5.14.17",
"prop-types": "^15.8.1"
}
},
"@mui/styled-engine": {
- "version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/styled-engine/-/styled-engine-5.14.16.tgz",
- "integrity": "sha512-FfvYvTG/Zd+KXMMImbcMYEeQAbONGuX5Vx3gBmmtB6KyA7Mvm9Pma1ly3R0gc44yeoFd+2wBjn1feS8h42HW5w==",
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/styled-engine/-/styled-engine-5.14.17.tgz",
+ "integrity": "sha512-AqpVjBEA7wnBvKPW168bNlqB6EN7HxTjLOY7oi275AzD/b1C7V0wqELy6NWoJb2yya5sRf7ENf4iNi3+T5cOgw==",
"requires": {
"@babel/runtime": "^7.23.2",
"@emotion/cache": "^11.11.0",
@@ -18561,15 +18595,15 @@
}
},
"@mui/system": {
- "version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/system/-/system-5.14.16.tgz",
- "integrity": "sha512-uKnPfsDqDs8bbN54TviAuoGWOmFiQLwNZ3Wvj+OBkJCzwA6QnLb/sSeCB7Pk3ilH4h4jQ0BHtbR+Xpjy9wlOuA==",
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/system/-/system-5.14.17.tgz",
+ "integrity": "sha512-Ccz3XlbCqka6DnbHfpL3o3TfOeWQPR+ewvNAgm8gnS9M0yVMmzzmY6z0w/C1eebb+7ZP7IoLUj9vojg/GBaTPg==",
"requires": {
"@babel/runtime": "^7.23.2",
- "@mui/private-theming": "^5.14.16",
- "@mui/styled-engine": "^5.14.16",
+ "@mui/private-theming": "^5.14.17",
+ "@mui/styled-engine": "^5.14.17",
"@mui/types": "^7.2.8",
- "@mui/utils": "^5.14.16",
+ "@mui/utils": "^5.14.17",
"clsx": "^2.0.0",
"csstype": "^3.1.2",
"prop-types": "^15.8.1"
@@ -18582,9 +18616,9 @@
"requires": {}
},
"@mui/utils": {
- "version": "5.14.16",
- "resolved": "https://registry.npmjs.org/@mui/utils/-/utils-5.14.16.tgz",
- "integrity": "sha512-3xV31GposHkwRbQzwJJuooWpK2ybWdEdeUPtRjv/6vjomyi97F3+68l+QVj9tPTvmfSbr2sx5c/NuvDulrdRmA==",
+ "version": "5.14.17",
+ "resolved": "https://registry.npmjs.org/@mui/utils/-/utils-5.14.17.tgz",
+ "integrity": "sha512-yxnWgSS4J6DMFPw2Dof85yBkG02VTbEiqsikymMsnZnXDurtVGTIhlNuV24GTmFTuJMzEyTTU9UF+O7zaL8LEQ==",
"requires": {
"@babel/runtime": "^7.23.2",
"@types/prop-types": "^15.7.9",
@@ -19040,9 +19074,9 @@
"integrity": "sha512-G/AdOadiZhnJp0jXCaBQU449W2h716OW/EoXeYkCytxKL06X1WCXB4DZpp8TpZ8eyIJVS1cw4lrlkkSYU21cDw=="
},
"@types/prop-types": {
- "version": "15.7.9",
- "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.9.tgz",
- "integrity": "sha512-n1yyPsugYNSmHgxDFjicaI2+gCNjsBck8UX9kuofAKlc0h1bL+20oSF72KeNaW2DUlesbEVCFgyV2dPGTiY42g=="
+ "version": "15.7.10",
+ "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.10.tgz",
+ "integrity": "sha512-mxSnDQxPqsZxmeShFH+uwQ4kO4gcJcGahjjMFeLbKE95IAZiiZyiEepGZjtXJ7hN/yfu0bu9xN2ajcU0JcxX6A=="
},
"@types/q": {
"version": "1.5.5",
@@ -19060,9 +19094,9 @@
"integrity": "sha512-EEhsLsD6UsDM1yFhAvy0Cjr6VwmpMWqFBCb9w07wVugF7w9nfajxLuVmngTIpgS6svCnm6Vaw+MZhoDCKnOfsw=="
},
"@types/react": {
- "version": "18.2.34",
- "resolved": "https://registry.npmjs.org/@types/react/-/react-18.2.34.tgz",
- "integrity": "sha512-U6eW/alrRk37FU/MS2RYMjx0Va2JGIVXELTODaTIYgvWGCV4Y4TfTUzG8DdmpDNIT0Xpj/R7GfyHOJJrDttcvg==",
+ "version": "18.2.37",
+ "resolved": "https://registry.npmjs.org/@types/react/-/react-18.2.37.tgz",
+ "integrity": "sha512-RGAYMi2bhRgEXT3f4B92WTohopH6bIXw05FuGlmJEnv/omEn190+QYEIYxIAuIBdKgboYYdVved2p1AxZVQnaw==",
"requires": {
"@types/prop-types": "*",
"@types/scheduler": "*",
@@ -19070,9 +19104,9 @@
}
},
"@types/react-transition-group": {
- "version": "4.4.8",
- "resolved": "https://registry.npmjs.org/@types/react-transition-group/-/react-transition-group-4.4.8.tgz",
- "integrity": "sha512-QmQ22q+Pb+HQSn04NL3HtrqHwYMf4h3QKArOy5F8U5nEVMaihBs3SR10WiOM1iwPz5jIo8x/u11al+iEGZZrvg==",
+ "version": "4.4.9",
+ "resolved": "https://registry.npmjs.org/@types/react-transition-group/-/react-transition-group-4.4.9.tgz",
+ "integrity": "sha512-ZVNmWumUIh5NhH8aMD9CR2hdW0fNuYInlocZHaZ+dgk/1K49j1w/HoAuK1ki+pgscQrOFRTlXeoURtuzEkV3dg==",
"requires": {
"@types/react": "*"
}
@@ -19091,9 +19125,9 @@
"integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA=="
},
"@types/scheduler": {
- "version": "0.16.5",
- "resolved": "https://registry.npmjs.org/@types/scheduler/-/scheduler-0.16.5.tgz",
- "integrity": "sha512-s/FPdYRmZR8SjLWGMCuax7r3qCWQw9QKHzXVukAuuIJkXkDRwp+Pu5LMIVFi0Fxbav35WURicYr8u1QsoybnQw=="
+ "version": "0.16.6",
+ "resolved": "https://registry.npmjs.org/@types/scheduler/-/scheduler-0.16.6.tgz",
+ "integrity": "sha512-Vlktnchmkylvc9SnwwwozTv04L/e1NykF5vgoQ0XTmI8DD+wxfjQuHuvHS3p0r2jz2x2ghPs2h1FVeDirIteWA=="
},
"@types/serve-index": {
"version": "1.9.1",
From 1aecc6e485b726705640d4b361f27b9db33db1c5 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:32:35 +0800
Subject: [PATCH 28/92] added mui styles
---
src/components/PriceDescriptionList.js | 29 +++++++++++++++++++-------
1 file changed, 22 insertions(+), 7 deletions(-)
diff --git a/src/components/PriceDescriptionList.js b/src/components/PriceDescriptionList.js
index a97b33ac..a1666cdc 100644
--- a/src/components/PriceDescriptionList.js
+++ b/src/components/PriceDescriptionList.js
@@ -1,18 +1,33 @@
import React from "react";
+import { Button, Stack } from "@mui/material";
+import ClearIcon from "@mui/icons-material/Clear";
const PriceDescriptionList = ({ details, deleteItems }) => {
- console.log(details);
return (
<>
{details.map((detail, index) => (
<>
-
- {detail.description} --- {detail.price} - {detail.payer}
-
- deleteItems(index)}>
- Delete
-
+
+
+ Item: {detail.description}
+
+ Price: ${detail.price}
+
+ Payer: {detail.payer}
+
+
+
+ deleteItems(index)}
+ color="secondary"
+ size="small"
+ variant="contained"
+ disableRipple
+ >
+
+
+
>
))}
From d2f685a3d9aa415506e999fddfe05581e80d4555 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:33:36 +0800
Subject: [PATCH 29/92] added mui styles
---
src/components/List.js | 37 +++++++++++++++++++++++++++++++++++++
1 file changed, 37 insertions(+)
create mode 100644 src/components/List.js
diff --git a/src/components/List.js b/src/components/List.js
new file mode 100644
index 00000000..c31558d3
--- /dev/null
+++ b/src/components/List.js
@@ -0,0 +1,37 @@
+import React from "react";
+
+import { Button, Stack } from "@mui/material";
+import ClearIcon from "@mui/icons-material/Clear";
+
+const List = ({ list, deleteItems }) => {
+ return (
+ <>
+
+ {list.map((listItem, index) => (
+
+
+
+ {listItem}
+
+ deleteItems(index)}
+ color="secondary"
+ size="small"
+ disableRipple
+ >
+
+
+
+
+ ))}
+
+ >
+ );
+};
+
+export default List;
From 155a1d6b4cae89858965799a201de13afd390963 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:34:25 +0800
Subject: [PATCH 30/92] created a Form component to include CreateForm and
AddTransactionsForm
---
src/components/Forms.js | 37 +++++++++++++++++++++++++++++++++++++
1 file changed, 37 insertions(+)
create mode 100644 src/components/Forms.js
diff --git a/src/components/Forms.js b/src/components/Forms.js
new file mode 100644
index 00000000..a4f0ae91
--- /dev/null
+++ b/src/components/Forms.js
@@ -0,0 +1,37 @@
+import React, { useState } from "react";
+import CreateForm from "./CreateForm";
+import AddTransactionsForm from "./AddTransactionsForm";
+
+const isTripDataEntered = () => {
+ const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
+ if (getTripData) {
+ return true;
+ }
+ return false;
+};
+
+const Forms = () => {
+ const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
+
+ const [tripDetails, setTripDetails] = useState(
+ getTripData ? getTripData : { tripname: "", items: "" }
+ );
+ const [showTransactionForm, setshowTransactionForm] = useState(
+ false || isTripDataEntered
+ );
+
+ return (
+ <>
+ {!showTransactionForm ? (
+
+ ) : (
+
+ )}
+ >
+ );
+};
+
+export default Forms;
From b093d81e44dd43295965e3890f34d3be0b1d2234 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:35:02 +0800
Subject: [PATCH 31/92] added this component to record all transactions
---
src/components/AddTransactionsForm.js | 120 ++++++++++++++++++++++++++
1 file changed, 120 insertions(+)
create mode 100644 src/components/AddTransactionsForm.js
diff --git a/src/components/AddTransactionsForm.js b/src/components/AddTransactionsForm.js
new file mode 100644
index 00000000..653b579b
--- /dev/null
+++ b/src/components/AddTransactionsForm.js
@@ -0,0 +1,120 @@
+import React, { useState } from "react";
+
+import PriceDescriptionList from "./PriceDescriptionList";
+import { TextField, Stack, InputAdornment, Button } from "@mui/material";
+import AttachMoneyIcon from "@mui/icons-material/AttachMoney";
+import Calculate from "./Calculate";
+
+const AddTransactionsForm = ({ tripDetails }) => {
+ // const getTripData = JSON.parse(localStorage.getItem("formObject"));
+ console.log(tripDetails);
+ const [description, setDescription] = useState("");
+ const [price, setPrice] = useState("");
+ const [payer, setPayer] = useState(tripDetails.items[0]);
+
+ let getTransactionData = () => {
+ const data = JSON.parse(localStorage.getItem("transactions"));
+ if (data !== null) {
+ return data;
+ }
+ return [];
+ };
+
+ const [details, setDetails] = useState(getTransactionData);
+
+ let changes = {
+ description: description,
+ price: price,
+ payer: payer,
+ };
+
+ const addItems = (event) => {
+ event.preventDefault();
+ let storage = [];
+ if (!Number(price) && !description) {
+ return;
+ }
+
+ setDetails([...details, changes]);
+
+ setPayer(tripDetails[0]);
+
+ setDescription("");
+ setPrice("");
+
+ storage.push(...details, changes);
+ console.log(storage);
+ localStorage.setItem("transactions", JSON.stringify(storage));
+ };
+
+ const deleteItems = (detailIndex) => {
+ const newDetails = details.filter((_, index) => index !== detailIndex);
+ setDetails(newDetails);
+ };
+
+ console.log(details);
+ return (
+ <>
+ {tripDetails.tripname}
+ {tripDetails.items}
+
+
+
+ Item Description
+
+ setDescription(e.target.value)}
+ size="small"
+ >
+
+
+ Price
+ setPrice(e.target.value)}
+ size="small"
+ InputProps={{
+ startAdornment: (
+
+
+
+ ),
+ }}
+ >
+
+
+
+ setPayer(e.target.value)}
+ name="payer"
+ >
+ {tripDetails.items.map((name, index) => (
+ {name}
+ ))}
+ {" "}
+ paid
+
+
+ +
+
+
+
+
+ >
+ );
+};
+
+export default AddTransactionsForm;
From 544abc2408ee91a649935cb482ea6001260532fc Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:36:40 +0800
Subject: [PATCH 32/92] added this component to calculate expenses and display
message
---
src/components/Calculate.js | 118 ++++++++++++++++++++++++++++++++++++
1 file changed, 118 insertions(+)
create mode 100644 src/components/Calculate.js
diff --git a/src/components/Calculate.js b/src/components/Calculate.js
new file mode 100644
index 00000000..608d114d
--- /dev/null
+++ b/src/components/Calculate.js
@@ -0,0 +1,118 @@
+import React, { useState } from "react";
+
+import { Button, Box, Modal } from "@mui/material";
+import HomeIcon from "@mui/icons-material/Home";
+import { useNavigate } from "react-router-dom";
+
+const style = {
+ position: "absolute",
+ top: "50%",
+ left: "50%",
+ transform: "translate(-50%, -50%",
+ width: "400px",
+ border: "2px solid black",
+ backgroundColor: "white",
+ color: "black",
+};
+
+const Calculate = ({ getTripData, getTransactions }) => {
+ const [showMessage, setShowMessage] = useState(null);
+ const navigate = useNavigate();
+ const [open, setOpen] = useState(false);
+
+ const handleClose = () => setOpen(false);
+
+ const friends = getTripData.items;
+
+ const getAllPrices = (entireData, entireFriends) => {
+ let allPrices = [];
+
+ for (let i = 0; i < entireFriends.length; i += 1) {
+ let sumOfIndividualPayer = 0;
+ for (let j = 0; j < entireData.length; j += 1) {
+ if (entireFriends[i] === entireData[j].payer) {
+ sumOfIndividualPayer += Number(entireData[j].price);
+ }
+ }
+ allPrices.push(sumOfIndividualPayer);
+ }
+ return allPrices;
+ };
+
+ const convertToObj = (allNames, getPrices) => {
+ let newObj = {};
+
+ allNames.forEach((friend, amount) => {
+ newObj[friend] = getPrices[amount];
+ });
+ return newObj;
+ };
+
+ let getPrices = getAllPrices(getTransactions, friends);
+
+ let getNewObj = convertToObj(friends, getPrices);
+
+ const handleClick = () => {
+ let finalMessage = "";
+ const sum = getPrices.reduce((acc, curr) => curr + acc);
+
+ const meanPrices = sum / friends.length;
+
+ const sortEveryone = friends.sort(
+ (personA, personB) => getNewObj[personA] - getNewObj[personB]
+ );
+
+ const sortPrices = sortEveryone.map(
+ (person) => getNewObj[person] - meanPrices
+ );
+
+ let firstPayer = 0;
+ let lastPayer = sortEveryone.length - 1;
+ let debt;
+
+ while (firstPayer < lastPayer) {
+ debt = Math.min(-sortPrices[firstPayer], sortPrices[lastPayer]);
+ sortPrices[firstPayer] += debt;
+ sortPrices[lastPayer] -= debt;
+
+ finalMessage += `${sortEveryone[firstPayer]} owes ${sortEveryone[lastPayer]} $${debt}`;
+
+ if (sortPrices[firstPayer] === 0) {
+ firstPayer += 1;
+ } else if (sortPrices[lastPayer] === 0) {
+ lastPayer -= 1;
+ }
+ }
+ setOpen(true);
+
+ return setShowMessage(finalMessage);
+ };
+
+ const restart = () => {
+ navigate("/dashboard");
+ localStorage.removeItem("transactions");
+ localStorage.removeItem("tripDetails");
+ };
+
+ return (
+ <>
+
+
+ {showMessage}
+
+
+
+
+
+
+ Calculate Total
+ >
+ );
+};
+
+export default Calculate;
From 69dbd2b52a450dd5736ea0342bd14be6db371da3 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:37:46 +0800
Subject: [PATCH 33/92] updated component to create a trip
---
src/components/CreateForm.js | 87 ++++++++++++++++++++++++++++++++++++
1 file changed, 87 insertions(+)
create mode 100644 src/components/CreateForm.js
diff --git a/src/components/CreateForm.js b/src/components/CreateForm.js
new file mode 100644
index 00000000..277d2858
--- /dev/null
+++ b/src/components/CreateForm.js
@@ -0,0 +1,87 @@
+import React, { useState } from "react";
+import List from "./List";
+import { TextField, Stack, Button } from "@mui/material";
+
+const CreateForm = ({ setTripDetails, setshowTransactionForm }) => {
+ const [tripname, setTripname] = useState("");
+ const [friends, setFriends] = useState("");
+
+ //items refer to an array of friends
+ const [items, setItems] = useState([]);
+
+ const addFriends = (event) => {
+ event.preventDefault();
+ if (!friends) {
+ return;
+ }
+ setItems([...items, friends]);
+ setFriends("");
+ };
+
+ const deleteFriends = (itemIndex) => {
+ const newItem = items.filter((_, index) => index !== itemIndex);
+ setItems(newItem);
+ };
+ const handleSubmit = () => {
+ if (!tripname) {
+ return;
+ }
+
+ let tripDetails = {
+ tripname: tripname,
+ items: items,
+ };
+ setshowTransactionForm(true);
+ setTripDetails(tripDetails);
+
+ localStorage.setItem("tripDetails", JSON.stringify(tripDetails));
+ };
+ return (
+ <>
+
+ Name of Trip
+ setTripname(event.target.value)}
+ value={tripname}
+ size="small"
+ style={{ border: "1px solid white" }}
+ >
+
+
+
+ Add Friends
+
+
+ setFriends(event.target.value)}
+ value={friends}
+ size="small"
+ style={{ border: "1px solid white" }}
+ >
+
+ +
+
+
+
+
+ Create Form
+
+
+ >
+ );
+};
+
+export default CreateForm;
From 4a425811f4b4476fc3f739e0457e2c9bd455afbf Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:43:04 +0800
Subject: [PATCH 34/92] updated return statement with a Forms component that
includes both CreateForm and AddTransactionsForm
---
src/components/CreatedForm.js | 12 -----
src/components/Dashboard.js | 84 +++++++++++++++++++----------------
src/components/Form.js | 58 ------------------------
src/components/FriendList.js | 20 ---------
src/components/GetPrices.js | 17 -------
src/components/ItemForm.js | 76 -------------------------------
src/components/Timer.js | 18 --------
src/components/TodoList.js | 20 ---------
8 files changed, 45 insertions(+), 260 deletions(-)
delete mode 100644 src/components/CreatedForm.js
delete mode 100644 src/components/Form.js
delete mode 100644 src/components/FriendList.js
delete mode 100644 src/components/GetPrices.js
delete mode 100644 src/components/ItemForm.js
delete mode 100644 src/components/Timer.js
delete mode 100644 src/components/TodoList.js
diff --git a/src/components/CreatedForm.js b/src/components/CreatedForm.js
deleted file mode 100644
index 88dccdf1..00000000
--- a/src/components/CreatedForm.js
+++ /dev/null
@@ -1,12 +0,0 @@
-import React from "react";
-
-const CreatedForm = ({ getNames }) => {
- return (
- <>
- {getNames.tripname}
- {getNames.items}
- >
- );
-};
-
-export default CreatedForm;
diff --git a/src/components/Dashboard.js b/src/components/Dashboard.js
index 5bdc8801..bcb2fe57 100644
--- a/src/components/Dashboard.js
+++ b/src/components/Dashboard.js
@@ -1,59 +1,65 @@
import React, { useState } from "react";
-
-import Timer from "../components/Timer";
import Greetings from "./Greetings";
-
-import Form from "./Form";
-
-import Button from "./Button";
-import CreatedForm from "./CreatedForm";
+import { Stack, Button } from "@mui/material";
+import { useNavigate } from "react-router-dom";
+import Forms from "./Forms";
const Dashboard = () => {
- const [showForm, setShowForm] = useState(false);
- const [showCreatedForm, setShowCreatedForm] = useState(false);
+ const [showCreateTripForm, setShowCreateTripForm] = useState(false);
- const getUsername = () => {
- return JSON.parse(localStorage.getItem("user"));
- };
+ const navigate = useNavigate();
- const getCreatedFormNames = () => {
- return JSON.parse(localStorage.getItem("stateObject"));
- };
+ const username = JSON.parse(localStorage.getItem("user"));
- // useEffect(() => {
- // return ()=> setShowForm(false);
- // // });
- // if (showCreatedForm) {
- // return setShowForm(false);
- // }
+ const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
return (
<>
- {getUsername()}
-
-
- Ongoing Trips
- {!showForm && !showCreatedForm ? (
- <>
- setShowForm(true)}>Add a trip
- This space is currently empty! Add a trip to start
- >
- ) : showForm && !showCreatedForm ? (
- <>
-
+
+
+
+ {!showCreateTripForm && !getTripData ? (
+ <>
+ {
+ setShowCreateTripForm(true);
+ }}
+ variant="contained"
+ size="small"
+ style={{
+ backgroundColor: "#c6ff00",
+ color: "black",
+ fontWeight: "bold",
+ }}
+ disableRipple
+ >
+ Add a Trip
+
+ >
+ ) : (
+
+ )}
{
- setShowCreatedForm(true);
+ navigate("/past-trips");
}}
+ variant="contained"
+ size="small"
+ color="primary"
+ disableRipple
>
- Create Trip
+ Browse Past Trips
- >
- ) : (
-
- )}
+
+
>
);
};
export default Dashboard;
+
+// no tripname no transactions = add a trip and browse past trips buttons
+
+// once i click onto add a trip, createform appears and create a trip button appears
+//
+//
diff --git a/src/components/Form.js b/src/components/Form.js
deleted file mode 100644
index e1076016..00000000
--- a/src/components/Form.js
+++ /dev/null
@@ -1,58 +0,0 @@
-import React, { useState, useEffect } from "react";
-import Button from "./Button";
-import FriendList from "./FriendList";
-
-const Form = () => {
- const [tripname, setTripname] = useState("");
- const [friends, setFriends] = useState("");
- const [items, setItems] = useState([]);
-
- const addFriends = () => {
- if (friends.length) {
- setItems([...items, friends]);
- setFriends("");
- }
- };
-
- const deleteFriends = (itemIndex) => {
- const newItem = items.filter((_, index) => index !== itemIndex);
- setItems(newItem);
- };
-
- useEffect(() => {
- let stateObject = {
- tripname: tripname,
- items: items,
- };
-
- localStorage.setItem("stateObject", JSON.stringify(stateObject));
- }, [tripname, items]);
-
- return (
- <>
-
- >
- );
-};
-
-export default Form;
diff --git a/src/components/FriendList.js b/src/components/FriendList.js
deleted file mode 100644
index f4ab7ff8..00000000
--- a/src/components/FriendList.js
+++ /dev/null
@@ -1,20 +0,0 @@
-import React from "react";
-
-const FriendList = ({ friendList, deleteFriends }) => {
- return (
- <>
-
- {friendList.map((friend, index) => (
- <>
- {friend}
- deleteFriends(index)}>
- Delete
-
- >
- ))}
-
- >
- );
-};
-
-export default FriendList;
diff --git a/src/components/GetPrices.js b/src/components/GetPrices.js
deleted file mode 100644
index 4d4d686f..00000000
--- a/src/components/GetPrices.js
+++ /dev/null
@@ -1,17 +0,0 @@
-const getAllPrices = (entireData, entireFriends) => {
- let allPrices = [];
-
- for (let i = 0; i < entireFriends.length; i += 1) {
- let sumOfIndividualPayer = 0;
- for (let j = 0; j < entireData.length; j += 1) {
- if (entireFriends[i] === entireData[j].payer) {
- sumOfIndividualPayer += Number(entireData[j].price);
- console.log(sumOfIndividualPayer);
- }
- }
- allPrices.push(sumOfIndividualPayer);
- }
- return allPrices;
-};
-
-export default getAllPrices;
diff --git a/src/components/ItemForm.js b/src/components/ItemForm.js
deleted file mode 100644
index 1a1e5824..00000000
--- a/src/components/ItemForm.js
+++ /dev/null
@@ -1,76 +0,0 @@
-import React, { useState } from "react";
-import Button from "./Button";
-import PriceDescriptionList from "./PriceDescriptionList";
-
-const ItemForm = (props) => {
- const [payer, setPayer] = useState([props.friendsName[0]]);
- const [description, setDescription] = useState("");
- const [price, setPrice] = useState("");
- const [details, setDetails] = useState([]);
-
- let changes = {
- description: description,
- price: price,
- payer: payer,
- };
-
- console.log(details);
-
- const addItems = () => {
- let storage = [];
- if (description.length && price.length) {
- console.log(details);
- setDetails([...details, changes]);
- console.log(details);
- setPayer([props.friendsName[0]]);
-
- setDescription("");
- setPrice("");
- }
-
- JSON.parse(localStorage.getItem("transactions"));
-
- storage.push(...details, changes);
- localStorage.setItem("transactions", JSON.stringify(storage));
- localStorage.getItem("transactions");
- };
-
- const deleteItems = (detailIndex) => {
- const newDetails = details.filter((_, index) => index !== detailIndex);
- setDetails(newDetails);
- };
-
- return (
- <>
- Item description:
- setDescription(e.target.value)}
- name="description"
- />
- Price:
- setPrice(e.target.value)}
- name="price"
- />
-
- setPayer(e.target.value)}
- name="payer"
- >
- {props.friendsName.map((name, index) => (
- {name}
- ))}
- {" "}
- paid
- Add
-
- >
- );
-};
-
-export default ItemForm;
diff --git a/src/components/Timer.js b/src/components/Timer.js
deleted file mode 100644
index a50312ae..00000000
--- a/src/components/Timer.js
+++ /dev/null
@@ -1,18 +0,0 @@
-import React, { useState, useEffect } from "react";
-
-const Timer = () => {
- const [currentDate, setCurrentDate] = useState(new Date());
- const currentTime = `${currentDate.getHours()} : ${currentDate.getMinutes()} : ${currentDate.getSeconds()}`;
-
- useEffect(() => {
- setInterval(() => setCurrentDate(new Date()), 1000);
- });
-
- return (
- <>
- {`${currentDate.toDateString()}, ${currentTime}`}
- >
- );
-};
-
-export default Timer;
diff --git a/src/components/TodoList.js b/src/components/TodoList.js
deleted file mode 100644
index 2b63418a..00000000
--- a/src/components/TodoList.js
+++ /dev/null
@@ -1,20 +0,0 @@
-import React from "react";
-
-const ToDoList = ({ toDoList, deleteFriends }) => {
- return (
- <>
-
- {toDoList.map((todo, index) => (
- <>
- {todo}
- deleteFriends(index)}>
- Delete
-
- >
- ))}
-
- >
- );
-};
-
-export default ToDoList;
From 1bb3439aa51cb8802573716f002d0f3768234936 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:43:58 +0800
Subject: [PATCH 35/92] added mui styles
---
src/components/Home.js | 71 ++++++++++++++++--------------------------
1 file changed, 27 insertions(+), 44 deletions(-)
diff --git a/src/components/Home.js b/src/components/Home.js
index 1864424f..d96b623f 100644
--- a/src/components/Home.js
+++ b/src/components/Home.js
@@ -1,63 +1,48 @@
-import React, { useState, useEffect } from "react";
+import React, { useState } from "react";
import { useNavigate } from "react-router-dom";
-import {
- Button,
- TextField,
- Typography,
- Stack,
- InputAdornment,
-} from "@mui/material";
-import { createTheme } from "@mui/material/styles";
+import { Button, TextField, Stack, InputAdornment } from "@mui/material";
import { AccountCircle } from "@mui/icons-material";
-
-const theme = createTheme({
- palette: {
- primary: {
- main: "#00c853",
- },
- },
-});
+import EastIcon from "@mui/icons-material/East";
const Home = () => {
const [username, setUsername] = useState("");
const navigate = useNavigate();
- const handleChange = (event) => {
- setUsername(event.target.value);
- };
-
const handleClick = () => {
if (username === "") {
return;
}
+ setUsername(username);
// store username in local storage
localStorage.setItem("user", JSON.stringify(username));
+
navigate("/dashboard");
};
- useEffect(() => {
- const userData = localStorage.getItem("user");
- if (userData !== null) {
- setUsername(JSON.parse(userData));
- }
- }, []);
-
return (
<>
-
-
+
- Hey there!
-
-
+ Hey there,
+
+
{
+ setUsername(event.target.value);
+ }}
+ style={{
+ backgroundColor: "white",
+ fontStyle: "italic",
+ }}
InputProps={{
startAdornment: (
@@ -66,15 +51,13 @@ const Home = () => {
),
}}
>
-
-
- Get Started
+
From 8df84f56d27089eb72dcbfb02ba279970c499e0b Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:45:20 +0800
Subject: [PATCH 36/92] removed date object
---
src/components/Greetings.js | 31 ++++++++++++++++++++++---------
1 file changed, 22 insertions(+), 9 deletions(-)
diff --git a/src/components/Greetings.js b/src/components/Greetings.js
index 9585593a..8036bd66 100644
--- a/src/components/Greetings.js
+++ b/src/components/Greetings.js
@@ -1,25 +1,38 @@
-import React from "react";
+import React, { useState, useEffect } from "react";
+import { Stack } from "@mui/material";
const Greetings = ({ username }) => {
- const today = new Date();
- const currHour = today.getHours();
+ const [currentDate, setCurrentDate] = useState(new Date());
+ const currentTime = `${currentDate.getHours()} : ${currentDate.getMinutes()} : ${currentDate.getSeconds()}`;
+ const currHour = currentDate.getHours();
- let greetings;
+ useEffect(() => {
+ setInterval(() => setCurrentDate(new Date()), 1000);
+ });
const greet = () => {
+ let greetings;
if (currHour >= 6 && currHour < 12) {
- greetings = "Good Morning";
+ greetings = "Good morning";
} else if (currHour >= 12 && currHour < 17) {
- greetings = "Good Afternoon";
+ greetings = "Good afternoon";
} else {
- greetings = "Good Evening";
+ greetings = "Good evening";
}
return greetings;
};
+
+ let greetMessage = `${greet()} ${username},`;
+
return (
<>
- {`${greet()} ${username}! `}
- What would you like to do today?
+
+ {`${currentDate.toDateString()}, ${currentTime}`}
+
+
+ {greetMessage}
+
+
>
);
};
From 65164bd5d0766b00b0150823bd97669f8b432467 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:45:46 +0800
Subject: [PATCH 37/92] removed original styles and added new ones
---
src/App.css | 35 +++++++++++++++++++----------------
1 file changed, 19 insertions(+), 16 deletions(-)
diff --git a/src/App.css b/src/App.css
index 7cf694f9..d2d4df35 100644
--- a/src/App.css
+++ b/src/App.css
@@ -1,27 +1,30 @@
+* {
+ margin: 0;
+ padding: 0;
+}
+
body {
- background-color: #ffab40;
+ background-color: #004d40;
+ color: white;
+ font-family: "Garamond";
}
-.App {
- text-align: center;
+.container {
+ width: 100%;
display: flex;
justify-content: center;
align-items: center;
- height: 700px;
-}
-
-.App-logo {
- height: 40vmin;
- pointer-events: none;
+ min-height: 100vh;
+ border: 5px solid red;
}
-.App-header {
- background-color: #282c34;
- min-height: 100vh;
+.form-wrapper {
+ min-height: 80vh;
+ min-width: 40vw;
+ box-sizing: border-box;
+ padding: 25px;
display: flex;
- flex-direction: column;
- align-items: center;
justify-content: center;
- font-size: calc(10px + 2vmin);
- color: white;
+ align-items: center;
+ border: 2px solid blue;
}
From a4bf5ff505aa7c81dbd85654a4c69bf769c238a1 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 19:46:16 +0800
Subject: [PATCH 38/92] updated routes
---
src/App.js | 19 ++++++++++++++-----
1 file changed, 14 insertions(+), 5 deletions(-)
diff --git a/src/App.js b/src/App.js
index bc9f2814..be2d2cc7 100644
--- a/src/App.js
+++ b/src/App.js
@@ -2,17 +2,26 @@ import React from "react";
import { Routes, Route } from "react-router-dom";
import Home from "./components/Home";
import Dashboard from "./components/Dashboard";
+import AddTransactionsForm from "./components/AddTransactionsForm";
+import PastTrips from "./components/PastTrips";
import "./App.css";
const App = () => {
return (
<>
-
-
- } />
- } />
-
+
+
+
+ } />
+ } />
+ }
+ />
+ } />
+
+
>
);
From f52c75f8e486a6cf4496642b5b65b23714931200 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 12 Nov 2023 20:01:04 +0800
Subject: [PATCH 39/92] added item as another condition in handleSubmit
function to prevent form submission when items is null
---
src/components/CreateForm.js | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/components/CreateForm.js b/src/components/CreateForm.js
index 277d2858..d9294ad8 100644
--- a/src/components/CreateForm.js
+++ b/src/components/CreateForm.js
@@ -23,7 +23,7 @@ const CreateForm = ({ setTripDetails, setshowTransactionForm }) => {
setItems(newItem);
};
const handleSubmit = () => {
- if (!tripname) {
+ if (!tripname || !items) {
return;
}
From 630b835e64ec8058cefa21ae1ce554c822e7b6ea Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Tue, 14 Nov 2023 19:56:51 +0800
Subject: [PATCH 40/92] added user story and how to use
---
README.md | 10 ++++++++++
1 file changed, 10 insertions(+)
diff --git a/README.md b/README.md
index e273017e..a48d8dcc 100644
--- a/README.md
+++ b/README.md
@@ -13,3 +13,13 @@ Open [http://localhost:3000](http://localhost:3000) to view it in your browser.
The page will reload when you make changes.\
You may also see any lint errors in the console.
+
+# User Story
+
+As someone who hangs out mostly in groups, I want to create an app for users to create an outing with different friends. Users are able to enter input items, prices and payer for that trip before calculating the total amount split among them. This app requires the user to settle up first by restricting users to only one trip at a time.
+
+# How to use
+
+1. Create a trip by inputting trip name and companions
+2. Add the item, price and payer for each transaction
+3. Click on calculate to derive how much each person owes one another
From faeed0466c27ca7880f450da3babf683d56fe5d5 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Tue, 14 Nov 2023 21:38:29 +0800
Subject: [PATCH 41/92] added wireframe
---
README.md | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/README.md b/README.md
index a48d8dcc..e2bf01bc 100644
--- a/README.md
+++ b/README.md
@@ -23,3 +23,7 @@ As someone who hangs out mostly in groups, I want to create an app for users to
1. Create a trip by inputting trip name and companions
2. Add the item, price and payer for each transaction
3. Click on calculate to derive how much each person owes one another
+
+# Wireframe
+
+https://www.figma.com/file/oMHth5a8YZe8xgdXRjtEdS/Equals?type=design&node-id=1-2&mode=design&t=u6hTR1s1sMhXVTEQ-0
From f2b730a613c3ff6f670e017be9e58912f18e522c Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Wed, 15 Nov 2023 21:28:59 +0800
Subject: [PATCH 42/92] added inline styles to style header and footer
---
src/App.js | 17 +++++++++++++++++
1 file changed, 17 insertions(+)
diff --git a/src/App.js b/src/App.js
index be2d2cc7..01643d0e 100644
--- a/src/App.js
+++ b/src/App.js
@@ -11,6 +11,15 @@ const App = () => {
return (
<>
+
+
} />
@@ -22,6 +31,14 @@ const App = () => {
} />
+
>
);
From bd9f8f67f989d626b6a6c4abb5bc4a8086afd478 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 16:49:40 +0800
Subject: [PATCH 43/92] updated styles to center elements and also on
background colors
---
src/App.css | 63 ++++++++++++++++++++++++++++++++++++++++++-----------
1 file changed, 50 insertions(+), 13 deletions(-)
diff --git a/src/App.css b/src/App.css
index d2d4df35..f024ed73 100644
--- a/src/App.css
+++ b/src/App.css
@@ -4,27 +4,64 @@
}
body {
- background-color: #004d40;
- color: white;
- font-family: "Garamond";
+ background-color: #fff1e6;
+ color: black;
+ font-family: "Georgia";
}
-.container {
- width: 100%;
+.app-container {
+ min-width: 100vw;
+ min-height: 140vh;
+}
+
+.app-header {
+ background-color: #eddcd2;
+ position: relative;
+ width: 100vw;
+ height: 30vh;
+ border-radius: 0px 0px 140px 140px;
+ border: 2px solid red;
+}
+
+.app-logo-wrapper {
display: flex;
justify-content: center;
align-items: center;
- min-height: 100vh;
- border: 5px solid red;
+ height: 25vh;
+}
+
+.left-leaf {
+ width: 20px;
+ height: 30px;
+
+ border-radius: 0 100px;
+ background-color: #e79796;
+ transform: rotate(-15deg);
+ border: 2px solid black;
+}
+
+.right-leaf {
+ width: 20px;
+ height: 30px;
+
+ border-radius: 100px 0px;
+ background-color: #3a0ca3;
+ transform: rotate(15deg);
+ border: 2px solid black;
}
.form-wrapper {
- min-height: 80vh;
- min-width: 40vw;
- box-sizing: border-box;
- padding: 25px;
- display: flex;
+ height: 110vh;
+ border-radius: 25px;
+ background-color: #fff1e6;
+ z-index: 1;
+ position: absolute;
+ width: 80vw;
+ top: 75%;
+ left: 50%;
+ transform: translate(-50%, -50%);
justify-content: center;
align-items: center;
- border: 2px solid blue;
+ display: flex;
+ padding: 20px;
}
From 64b617ea1ef2dd826bc645bf4ca5208932d97abd Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 16:52:23 +0800
Subject: [PATCH 44/92] added div tags for logo and renamed classes
---
src/App.js | 45 +++++++++++++++------------------------------
1 file changed, 15 insertions(+), 30 deletions(-)
diff --git a/src/App.js b/src/App.js
index 01643d0e..14552913 100644
--- a/src/App.js
+++ b/src/App.js
@@ -2,43 +2,28 @@ import React from "react";
import { Routes, Route } from "react-router-dom";
import Home from "./components/Home";
import Dashboard from "./components/Dashboard";
-import AddTransactionsForm from "./components/AddTransactionsForm";
-import PastTrips from "./components/PastTrips";
import "./App.css";
const App = () => {
return (
<>
-
-
-
-
-
- } />
- } />
- }
- />
- } />
-
+
>
);
From f7afd11132af1c666129d84501fa341b433705b0 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 21:59:33 +0800
Subject: [PATCH 45/92] added css box to greeting
---
src/components/greetings/Greetings.css | 14 ++++++++++++++
1 file changed, 14 insertions(+)
create mode 100644 src/components/greetings/Greetings.css
diff --git a/src/components/greetings/Greetings.css b/src/components/greetings/Greetings.css
new file mode 100644
index 00000000..294afb63
--- /dev/null
+++ b/src/components/greetings/Greetings.css
@@ -0,0 +1,14 @@
+.greetings {
+ height: 20vh;
+ border-radius: 20px;
+ background-color: #eddcd2;
+ z-index: 2;
+ position: absolute;
+ width: 50vw;
+ top: 20%;
+ left: 50%;
+ transform: translate(-50%, -50%);
+ justify-content: center;
+ align-items: center;
+ display: flex;
+}
From eb39a471494c4424688f8d57dffe99bb26bf0618 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:00:10 +0800
Subject: [PATCH 46/92] updated greetings with css classes
---
src/components/greetings/Greetings.js | 42 +++++++++++++++++++++++++++
1 file changed, 42 insertions(+)
create mode 100644 src/components/greetings/Greetings.js
diff --git a/src/components/greetings/Greetings.js b/src/components/greetings/Greetings.js
new file mode 100644
index 00000000..7c832b24
--- /dev/null
+++ b/src/components/greetings/Greetings.js
@@ -0,0 +1,42 @@
+import React, { useState, useEffect } from "react";
+import { Stack } from "@mui/material";
+
+import "./Greetings.css";
+
+const Greetings = ({ username }) => {
+ const [currentDate, setCurrentDate] = useState(new Date());
+ const currentTime = `${currentDate.getHours()} : ${currentDate.getMinutes()} : ${currentDate.getSeconds()}`;
+ const currHour = currentDate.getHours();
+
+ useEffect(() => {
+ setInterval(() => setCurrentDate(new Date()), 1000);
+ });
+
+ const greetUser = () => {
+ let greetings;
+ if (currHour >= 6 && currHour < 12) {
+ greetings = "Good morning";
+ } else if (currHour >= 12 && currHour < 17) {
+ greetings = "Good afternoon";
+ } else {
+ greetings = "Good evening";
+ }
+ return greetings;
+ };
+
+ let greetMessage = `${greetUser()} ${username},`;
+
+ return (
+ <>
+
+ {`${currentDate.toDateString()}, ${currentTime}`}
+
+ {greetMessage}
+
+ >
+ );
+};
+
+export default Greetings;
From 6445628f30e19b3ced5550a4f562dd86926d24f2 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:07:06 +0800
Subject: [PATCH 47/92] updated styling and conditional rendering
---
src/components/Home.js | 29 +++++++++--------------------
1 file changed, 9 insertions(+), 20 deletions(-)
diff --git a/src/components/Home.js b/src/components/Home.js
index d96b623f..a44e6d85 100644
--- a/src/components/Home.js
+++ b/src/components/Home.js
@@ -1,6 +1,7 @@
import React, { useState } from "react";
import { useNavigate } from "react-router-dom";
import { Button, TextField, Stack, InputAdornment } from "@mui/material";
+
import { AccountCircle } from "@mui/icons-material";
import EastIcon from "@mui/icons-material/East";
@@ -9,40 +10,29 @@ const Home = () => {
const navigate = useNavigate();
const handleClick = () => {
- if (username === "") {
+ if (!username) {
return;
}
setUsername(username);
+
// store username in local storage
localStorage.setItem("user", JSON.stringify(username));
-
navigate("/dashboard");
};
return (
<>
-
- Hey there,
-
+ Welcome back,
{
setUsername(event.target.value);
}}
- style={{
- backgroundColor: "white",
- fontStyle: "italic",
- }}
InputProps={{
startAdornment: (
@@ -50,11 +40,10 @@ const Home = () => {
),
}}
- >
+ />
From 37aca03c62646beec9bbced0827761d63df74d20 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:08:05 +0800
Subject: [PATCH 48/92] updated styles and conditional rendering
---
src/components/Dashboard.js | 52 ++++++++++++-------------------------
1 file changed, 17 insertions(+), 35 deletions(-)
diff --git a/src/components/Dashboard.js b/src/components/Dashboard.js
index bcb2fe57..f3e6955a 100644
--- a/src/components/Dashboard.js
+++ b/src/components/Dashboard.js
@@ -1,65 +1,47 @@
import React, { useState } from "react";
-import Greetings from "./Greetings";
+import Greetings from "./greetings/Greetings";
import { Stack, Button } from "@mui/material";
-import { useNavigate } from "react-router-dom";
-import Forms from "./Forms";
-const Dashboard = () => {
- const [showCreateTripForm, setShowCreateTripForm] = useState(false);
+import Forms from "./forms/Forms";
- const navigate = useNavigate();
+const Dashboard = () => {
+ const [isTripFormShown, setIsTripFormShown] = useState(false);
const username = JSON.parse(localStorage.getItem("user"));
+ // get tripname and companions details
const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
return (
<>
-
- {!showCreateTripForm && !getTripData ? (
- <>
+ {!isTripFormShown && !getTripData ? (
+ <>
+ You have no ongoing activity. Add a trip to begin.
+
{
- setShowCreateTripForm(true);
+ setIsTripFormShown(true);
}}
- variant="contained"
- size="small"
style={{
- backgroundColor: "#c6ff00",
+ backgroundColor: "#c6c09c",
color: "black",
fontWeight: "bold",
+ width: "140px",
}}
disableRipple
>
Add a Trip
- >
- ) : (
-
- )}
- {
- navigate("/past-trips");
- }}
- variant="contained"
- size="small"
- color="primary"
- disableRipple
- >
- Browse Past Trips
-
-
+
+ >
+ ) : (
+
+ )}
>
);
};
export default Dashboard;
-
-// no tripname no transactions = add a trip and browse past trips buttons
-
-// once i click onto add a trip, createform appears and create a trip button appears
-//
-//
From 43238aa7b4f2de52d0de6f6e844064db93cc784a Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:09:07 +0800
Subject: [PATCH 49/92] added two forms with states passed as props
---
src/components/forms/Forms.js | 40 +++++++++++++++++++++++++++++++++++
1 file changed, 40 insertions(+)
create mode 100644 src/components/forms/Forms.js
diff --git a/src/components/forms/Forms.js b/src/components/forms/Forms.js
new file mode 100644
index 00000000..1bdef2e6
--- /dev/null
+++ b/src/components/forms/Forms.js
@@ -0,0 +1,40 @@
+import React, { useState } from "react";
+import CreateForm from "./CreateForm";
+import AddTransactionsForm from "./AddTransactionsForm";
+
+const isTripDataEntered = () => {
+ const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
+ if (getTripData) {
+ return true;
+ }
+ return false;
+};
+
+const Forms = () => {
+ const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
+
+ const [tripDetails, setTripDetails] = useState(
+ getTripData ? getTripData : { tripname: "", items: "" }
+ );
+ const [isTransactionFormShown, setIsTransactionFormShown] = useState(
+ false || isTripDataEntered
+ );
+
+ return (
+ <>
+ {!isTransactionFormShown ? (
+
+ ) : (
+
+ )}
+ >
+ );
+};
+
+export default Forms;
From 3205ca82bd35351d40116fa733ae9660ad71632b Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:10:15 +0800
Subject: [PATCH 50/92] updated styles and restructured code
---
src/components/forms/CreateForm.js | 111 +++++++++++++++++++++++++++++
1 file changed, 111 insertions(+)
create mode 100644 src/components/forms/CreateForm.js
diff --git a/src/components/forms/CreateForm.js b/src/components/forms/CreateForm.js
new file mode 100644
index 00000000..ce2fbc7a
--- /dev/null
+++ b/src/components/forms/CreateForm.js
@@ -0,0 +1,111 @@
+import React, { useState } from "react";
+import List from "../formLists/List";
+import { TextField, Stack, Button } from "@mui/material";
+
+const title = { fontSize: "13px", fontWeight: "bold" };
+
+const CreateForm = ({ setTripDetails, setIsTransactionFormShown }) => {
+ const [tripname, setTripname] = useState("");
+ const [friends, setFriends] = useState("");
+ const [items, setItems] = useState([]); //items refer to an array of friends
+
+ const addFriends = (event) => {
+ event.preventDefault();
+ if (!friends) {
+ return;
+ }
+ setItems([...items, friends]);
+ setFriends("");
+ };
+
+ const deleteFriends = (itemIndex) => {
+ const newItem = items.filter((_, index) => index !== itemIndex);
+ setItems(newItem);
+ };
+
+ const handleSubmit = () => {
+ if (!tripname || !items) {
+ return;
+ }
+
+ let tripDetails = {
+ tripname: tripname,
+ items: items,
+ };
+
+ setTripDetails(tripDetails);
+ setIsTransactionFormShown(true);
+ localStorage.setItem("tripDetails", JSON.stringify(tripDetails));
+ };
+
+ return (
+ <>
+
+
+ Name of Trip
+ setTripname(event.target.value)}
+ value={tripname}
+ />
+
+
+
+ Friends
+
+
+ setFriends(event.target.value)}
+ value={friends}
+ />
+
+ +
+
+
+
+
+
+
+
+
+
+ Create a Trip
+
+
+
+
+ >
+ );
+};
+
+export default CreateForm;
From 6f2da17128b541206b0bd52e4a98b7a243532d02 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:10:40 +0800
Subject: [PATCH 51/92] updated styles and restructured code
---
src/components/forms/AddTransactionsForm.js | 156 ++++++++++++++++++++
1 file changed, 156 insertions(+)
create mode 100644 src/components/forms/AddTransactionsForm.js
diff --git a/src/components/forms/AddTransactionsForm.js b/src/components/forms/AddTransactionsForm.js
new file mode 100644
index 00000000..16df3ad1
--- /dev/null
+++ b/src/components/forms/AddTransactionsForm.js
@@ -0,0 +1,156 @@
+import React, { useState } from "react";
+
+import PriceDescriptionList from "../formLists/PriceDescriptionList";
+import {
+ TextField,
+ Stack,
+ InputAdornment,
+ Button,
+ AvatarGroup,
+ Avatar,
+} from "@mui/material";
+import AttachMoneyIcon from "@mui/icons-material/AttachMoney";
+import Calculate from "../calculate/Calculate";
+
+const title = { fontSize: "13px", fontWeight: "bold" };
+
+let getTransactionData = () => {
+ const data = JSON.parse(localStorage.getItem("transactions"));
+ if (data !== null) {
+ return data;
+ }
+ return [];
+};
+
+const AddTransactionsForm = ({ tripDetails, setIsTransactionFormShown }) => {
+ const [description, setDescription] = useState("");
+ const [price, setPrice] = useState("");
+ const [payer, setPayer] = useState(tripDetails.items[0]);
+ const [details, setDetails] = useState(getTransactionData);
+
+ let changes = {
+ description: description,
+ price: price,
+ payer: payer,
+ };
+
+ const addItems = () => {
+ let storage = [];
+ if (!description) {
+ return;
+ }
+ setDetails([...details, changes]);
+ setPayer(tripDetails.items[0]);
+ setDescription("");
+ setPrice("");
+ storage.push(...details, changes);
+ localStorage.setItem("transactions", JSON.stringify(storage));
+ };
+
+ const deleteItems = (detailIndex) => {
+ const newDetails = details.filter((_, index) => index !== detailIndex);
+ setDetails(newDetails);
+ };
+
+ const friends = [];
+
+ tripDetails.items.forEach((word) => {
+ return friends.push(word.charAt(0));
+ });
+
+ return (
+ <>
+
+
+
+ {tripDetails.tripname}
+
+
+ {friends.map((friend, index) => (
+
+ {friend}
+
+ ))}
+
+
+
+
+
+ Item
+ setDescription(e.target.value)}
+ id="item-field"
+ variant="outlined"
+ style={{ width: "90px" }}
+ />
+
+
+ Price
+ setPrice(e.target.value)}
+ id="price-field"
+ variant="outlined"
+ style={{ width: "90px" }}
+ InputProps={{
+ startAdornment: (
+
+
+
+ ),
+ }}
+ />
+
+
+
+ Payer
+ setPayer(e.target.value)}
+ style={{
+ backgroundColor: "#f7ede2",
+ width: "100px",
+ padding: "10px",
+ }}
+ >
+ {tripDetails.items.map((name, index) => (
+
+ {name}
+
+ ))}
+
+
+
+
+ +
+
+
+
+
+
+ >
+ );
+};
+
+export default AddTransactionsForm;
From bd2d1e055e15312998968dbc6a8f3ed17eb25a54 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:11:51 +0800
Subject: [PATCH 52/92] added styles
---
src/components/formLists/List.js | 46 +++++++++++++++
.../formLists/PriceDescriptionList.js | 58 +++++++++++++++++++
2 files changed, 104 insertions(+)
create mode 100644 src/components/formLists/List.js
create mode 100644 src/components/formLists/PriceDescriptionList.js
diff --git a/src/components/formLists/List.js b/src/components/formLists/List.js
new file mode 100644
index 00000000..db6bfb13
--- /dev/null
+++ b/src/components/formLists/List.js
@@ -0,0 +1,46 @@
+import React from "react";
+
+const List = ({ list, deleteItems }) => {
+ return (
+ <>
+ {list.map((listItem, index) => (
+
+
+
+ deleteItems(index)}
+ style={{
+ backgroundColor: "#ffe0b2",
+ height: "35px",
+ color: "black",
+ fontWeight: "bold",
+ width: "35px",
+ }}
+ >
+ x
+
+
+
+ ))}
+ >
+ );
+};
+
+export default List;
diff --git a/src/components/formLists/PriceDescriptionList.js b/src/components/formLists/PriceDescriptionList.js
new file mode 100644
index 00000000..ceb3b4db
--- /dev/null
+++ b/src/components/formLists/PriceDescriptionList.js
@@ -0,0 +1,58 @@
+import React from "react";
+import {
+ Table,
+ TableCell,
+ TableRow,
+ TableBody,
+ TableHead,
+} from "@mui/material";
+
+const tableHeading = {
+ color: "black",
+ fontSize: "13px",
+ fontWeight: "bold",
+ backgroundColor: "#f7ede2",
+ lineHeight: "15px",
+};
+
+const PriceDescriptionList = ({ details, deleteItems }) => {
+ return (
+ <>
+
+
+
+ Item
+ Price
+ Payer
+
+
+
+ {details.map((detail, index) => (
+
+ {detail.description}
+ ${detail.price}
+ {detail.payer}
+
+
+ deleteItems(index)}
+ style={{
+ backgroundColor: "#ffe0b2",
+ height: "35px",
+ color: "black",
+ fontWeight: "bold",
+ width: "35px",
+ }}
+ >
+ x
+
+
+
+ ))}
+
+
+ >
+ );
+};
+
+export default PriceDescriptionList;
From 63ff2759205fbe7a3a712e2ca8a894eeec047c07 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:14:03 +0800
Subject: [PATCH 53/92] restructured coded, updated styles and lifted state up
to addTransactionsForm
---
src/components/calculate/Calculate.js | 150 ++++++++++++++++++++++++++
1 file changed, 150 insertions(+)
create mode 100644 src/components/calculate/Calculate.js
diff --git a/src/components/calculate/Calculate.js b/src/components/calculate/Calculate.js
new file mode 100644
index 00000000..3b98651f
--- /dev/null
+++ b/src/components/calculate/Calculate.js
@@ -0,0 +1,150 @@
+import React, { useState } from "react";
+
+import { Button, Stack, Modal } from "@mui/material";
+import HomeIcon from "@mui/icons-material/Home";
+import { useNavigate } from "react-router-dom";
+
+const modalStyles = {
+ position: "absolute",
+ top: "50%",
+ left: "50%",
+ transform: "translate(-50%, -50%)",
+ width: "270px",
+ border: "2px solid black",
+ backgroundColor: "#fff1e6",
+ color: "black",
+};
+
+const Calculate = ({
+ getTripData,
+ getTransactions,
+ setIsTransactionFormShown,
+}) => {
+ const [showMessage, setShowMessage] = useState([]);
+ const [open, setOpen] = useState(false);
+ let navigate = useNavigate();
+
+ const handleClose = () => setOpen(false);
+
+ const friends = getTripData.items;
+
+ const getAllPrices = (entireData, entireFriends) => {
+ let allPrices = [];
+
+ for (let i = 0; i < entireFriends.length; i += 1) {
+ let sumOfIndividualPayer = 0;
+ for (let j = 0; j < entireData.length; j += 1) {
+ if (entireFriends[i] === entireData[j].payer) {
+ sumOfIndividualPayer += Number(entireData[j].price);
+ }
+ }
+ allPrices.push(sumOfIndividualPayer);
+ }
+ return allPrices;
+ };
+
+ const convertToObj = (allNames, getPrices) => {
+ let newObj = {};
+
+ allNames.forEach((friend, amount) => {
+ newObj[friend] = getPrices[amount];
+ });
+ return newObj;
+ };
+
+ let getPrices = getAllPrices(getTransactions, friends);
+
+ let getNewObj = convertToObj(friends, getPrices);
+
+ const handleClick = () => {
+ let message = "";
+ const sum = getPrices.reduce((acc, curr) => curr + acc);
+
+ const meanPrices = sum / friends.length;
+
+ const sortEveryone = friends.sort(
+ (personA, personB) => getNewObj[personA] - getNewObj[personB]
+ );
+
+ const sortPrices = sortEveryone.map(
+ (person) => getNewObj[person] - meanPrices
+ );
+
+ let firstPayer = 0;
+ let lastPayer = sortEveryone.length - 1;
+ let debt;
+ let text = [];
+ while (firstPayer < lastPayer) {
+ debt = Math.min(-sortPrices[firstPayer], sortPrices[lastPayer]);
+ sortPrices[firstPayer] += debt;
+ sortPrices[lastPayer] -= debt;
+
+ message = `${sortEveryone[firstPayer]} owes ${
+ sortEveryone[lastPayer]
+ } $${debt.toFixed(2)}`;
+
+ text.push(message);
+
+ if (sortPrices[firstPayer] === 0) {
+ firstPayer += 1;
+ } else if (sortPrices[lastPayer] === 0) {
+ lastPayer -= 1;
+ }
+ }
+ setOpen(true);
+
+ return setShowMessage(text);
+ };
+
+ const restartFormCreation = () => {
+ setIsTransactionFormShown(false);
+ localStorage.removeItem("transactions");
+ localStorage.removeItem("tripDetails");
+
+ navigate("/dashboard");
+ };
+
+ return (
+ <>
+
+
+ Split
+
+
+
+
+
+ {showMessage.map((e, index) => (
+ <>
+
{e}
+
+ >
+ ))}
+
+
+
+
+
+
+ >
+ );
+};
+
+export default Calculate;
From 2e31630c90bab6a89934da2aba81eb525717954f Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:17:38 +0800
Subject: [PATCH 54/92] renamed function that converts array to object
---
src/components/calculate/Calculate.js | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/components/calculate/Calculate.js b/src/components/calculate/Calculate.js
index 3b98651f..f1dedcaa 100644
--- a/src/components/calculate/Calculate.js
+++ b/src/components/calculate/Calculate.js
@@ -43,7 +43,7 @@ const Calculate = ({
return allPrices;
};
- const convertToObj = (allNames, getPrices) => {
+ const convertArrToObj = (allNames, getPrices) => {
let newObj = {};
allNames.forEach((friend, amount) => {
@@ -54,7 +54,7 @@ const Calculate = ({
let getPrices = getAllPrices(getTransactions, friends);
- let getNewObj = convertToObj(friends, getPrices);
+ let getNewObj = convertArrToObj(friends, getPrices);
const handleClick = () => {
let message = "";
From 837b51169e7c58b696fa10f268099f73cbb9691b Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:21:24 +0800
Subject: [PATCH 55/92] updated height of form-wrapper
---
src/App.css | 7 +++----
1 file changed, 3 insertions(+), 4 deletions(-)
diff --git a/src/App.css b/src/App.css
index f024ed73..06495bd0 100644
--- a/src/App.css
+++ b/src/App.css
@@ -18,9 +18,8 @@ body {
background-color: #eddcd2;
position: relative;
width: 100vw;
- height: 30vh;
+ height: 35vh;
border-radius: 0px 0px 140px 140px;
- border: 2px solid red;
}
.app-logo-wrapper {
@@ -51,13 +50,13 @@ body {
}
.form-wrapper {
- height: 110vh;
+ height: 120vh;
border-radius: 25px;
background-color: #fff1e6;
z-index: 1;
position: absolute;
width: 80vw;
- top: 75%;
+ top: 80%;
left: 50%;
transform: translate(-50%, -50%);
justify-content: center;
From 9038a00f01745ecd3f7fe9ed7d10427b8f71964a Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:36:00 +0800
Subject: [PATCH 56/92] updated user story and how to use
---
README.md | 11 +++++++----
1 file changed, 7 insertions(+), 4 deletions(-)
diff --git a/README.md b/README.md
index e2bf01bc..7e454500 100644
--- a/README.md
+++ b/README.md
@@ -16,13 +16,16 @@ You may also see any lint errors in the console.
# User Story
-As someone who hangs out mostly in groups, I want to create an app for users to create an outing with different friends. Users are able to enter input items, prices and payer for that trip before calculating the total amount split among them. This app requires the user to settle up first by restricting users to only one trip at a time.
+My app is ideal for those who engage in groups, preferably in short duration outings. These users seek to avoid the hassle of manually calculating how much is owed to one another after numerous transactions are made. The app enables users to retrieve the trip created as well as the friends included until the final amount is calculated, or in the event that the app is closed. The app will send the user to a fresh trip only until the outing is completed. The add and delete functionality allows users to calculate existing transactions before entering new ones.
# How to use
-1. Create a trip by inputting trip name and companions
-2. Add the item, price and payer for each transaction
-3. Click on calculate to derive how much each person owes one another
+1. Get started on the app by entering a username.
+2. Create a trip by including the trip name and people involved in the trip.
+3. Add transactions by selecting the entering the item, price and payer from the drop down selection.
+4. Add and delete transactions whenever required.
+5. Click on calculate to derive how much each person owes one another.
+6. View the amount owed to one another, then hit the Home button to create a new trip.
# Wireframe
From ac88c352478399500d68f8e6f93f787429d9c178 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Fri, 17 Nov 2023 22:41:36 +0800
Subject: [PATCH 57/92] reduced top to 12%
---
src/components/greetings/Greetings.css | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/components/greetings/Greetings.css b/src/components/greetings/Greetings.css
index 294afb63..7ea850b8 100644
--- a/src/components/greetings/Greetings.css
+++ b/src/components/greetings/Greetings.css
@@ -5,7 +5,7 @@
z-index: 2;
position: absolute;
width: 50vw;
- top: 20%;
+ top: 12%;
left: 50%;
transform: translate(-50%, -50%);
justify-content: center;
From d4f8bd797919d64de581b149fc34393b549e0e1f Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 18 Nov 2023 23:04:27 +0800
Subject: [PATCH 58/92] updated styles
---
src/App.js | 53 ++++++++++++++++++++++++++++++++++++++++++-----------
1 file changed, 42 insertions(+), 11 deletions(-)
diff --git a/src/App.js b/src/App.js
index 14552913..5f53536a 100644
--- a/src/App.js
+++ b/src/App.js
@@ -2,29 +2,60 @@ import React from "react";
import { Routes, Route } from "react-router-dom";
import Home from "./components/Home";
import Dashboard from "./components/Dashboard";
+import Container from "@mui/material/Container";
+import Box from "@mui/material/Box";
import "./App.css";
const App = () => {
return (
<>
-
+
+
+
>
);
};
From 892dc2e557118e4989333d82c161d2fe7940ef7c Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 18 Nov 2023 23:04:54 +0800
Subject: [PATCH 59/92] removed styles
---
src/App.css | 50 +++++++-------------------------------------------
1 file changed, 7 insertions(+), 43 deletions(-)
diff --git a/src/App.css b/src/App.css
index 06495bd0..ad4ecebd 100644
--- a/src/App.css
+++ b/src/App.css
@@ -4,63 +4,27 @@
}
body {
- background-color: #fff1e6;
+ background-color: #e6cdb5;
color: black;
font-family: "Georgia";
}
-.app-container {
- min-width: 100vw;
- min-height: 140vh;
-}
-
-.app-header {
- background-color: #eddcd2;
- position: relative;
- width: 100vw;
- height: 35vh;
- border-radius: 0px 0px 140px 140px;
-}
-
-.app-logo-wrapper {
- display: flex;
- justify-content: center;
- align-items: center;
- height: 25vh;
-}
-
.left-leaf {
- width: 20px;
- height: 30px;
+ width: 40px;
+ height: 50px;
border-radius: 0 100px;
- background-color: #e79796;
+ background-color: #fb8c00;
transform: rotate(-15deg);
border: 2px solid black;
}
.right-leaf {
- width: 20px;
- height: 30px;
+ width: 40px;
+ height: 50px;
border-radius: 100px 0px;
- background-color: #3a0ca3;
+ background-color: #ffff00;
transform: rotate(15deg);
border: 2px solid black;
}
-
-.form-wrapper {
- height: 120vh;
- border-radius: 25px;
- background-color: #fff1e6;
- z-index: 1;
- position: absolute;
- width: 80vw;
- top: 80%;
- left: 50%;
- transform: translate(-50%, -50%);
- justify-content: center;
- align-items: center;
- display: flex;
- padding: 20px;
-}
From 04b6099afd11e2ffdb8245e9a17958e5e07434d4 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 18 Nov 2023 23:05:22 +0800
Subject: [PATCH 60/92] updated styles
---
src/components/greetings/Greetings.css | 14 ------------
src/components/greetings/Greetings.js | 30 +++++++++++++++++---------
2 files changed, 20 insertions(+), 24 deletions(-)
delete mode 100644 src/components/greetings/Greetings.css
diff --git a/src/components/greetings/Greetings.css b/src/components/greetings/Greetings.css
deleted file mode 100644
index 7ea850b8..00000000
--- a/src/components/greetings/Greetings.css
+++ /dev/null
@@ -1,14 +0,0 @@
-.greetings {
- height: 20vh;
- border-radius: 20px;
- background-color: #eddcd2;
- z-index: 2;
- position: absolute;
- width: 50vw;
- top: 12%;
- left: 50%;
- transform: translate(-50%, -50%);
- justify-content: center;
- align-items: center;
- display: flex;
-}
diff --git a/src/components/greetings/Greetings.js b/src/components/greetings/Greetings.js
index 7c832b24..c7e32b41 100644
--- a/src/components/greetings/Greetings.js
+++ b/src/components/greetings/Greetings.js
@@ -1,7 +1,5 @@
import React, { useState, useEffect } from "react";
-import { Stack } from "@mui/material";
-
-import "./Greetings.css";
+import { Stack, Box } from "@mui/material";
const Greetings = ({ username }) => {
const [currentDate, setCurrentDate] = useState(new Date());
@@ -28,13 +26,25 @@ const Greetings = ({ username }) => {
return (
<>
-
- {`${currentDate.toDateString()}, ${currentTime}`}
-
- {greetMessage}
-
+
+
+ {`${currentDate.toDateString()}, ${currentTime}`}
+
+ {greetMessage}
+
+
>
);
};
From 0d7f3de71c83835b03322672f28f7b987a235d38 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 18 Nov 2023 23:05:56 +0800
Subject: [PATCH 61/92] added Box element and updated styles
---
src/components/Dashboard.js | 75 ++++++++++++++++++++++++-------------
1 file changed, 49 insertions(+), 26 deletions(-)
diff --git a/src/components/Dashboard.js b/src/components/Dashboard.js
index f3e6955a..98952385 100644
--- a/src/components/Dashboard.js
+++ b/src/components/Dashboard.js
@@ -1,6 +1,6 @@
import React, { useState } from "react";
import Greetings from "./greetings/Greetings";
-import { Stack, Button } from "@mui/material";
+import { Stack, Button, Box } from "@mui/material";
import Forms from "./forms/Forms";
@@ -10,35 +10,58 @@ const Dashboard = () => {
const username = JSON.parse(localStorage.getItem("user"));
// get tripname and companions details
- const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
+ const getActivityData = JSON.parse(localStorage.getItem("activityDetails"));
return (
<>
-
+
- {!isTripFormShown && !getTripData ? (
- <>
- You have no ongoing activity. Add a trip to begin.
-
- {
- setIsTripFormShown(true);
- }}
- style={{
- backgroundColor: "#c6c09c",
- color: "black",
- fontWeight: "bold",
- width: "140px",
- }}
- disableRipple
- >
- Add a Trip
-
-
- >
- ) : (
-
- )}
+
+ {!isTripFormShown && !getActivityData ? (
+ <>
+
+
+ You have no ongoing activity. Add one to begin.
+
+
+ {
+ setIsTripFormShown(true);
+ }}
+ style={{
+ backgroundColor: "#ec407a",
+ color: "white",
+ fontWeight: "bold",
+ width: "140px",
+
+ display: "block",
+ margin: "auto",
+ }}
+ disableRipple
+ >
+ Add Activity
+
+
+
+ >
+ ) : (
+
+ )}
+
>
);
From 0eb46ae9a5ae713ca1a876784f53b902a3ac7b7d Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 18 Nov 2023 23:06:34 +0800
Subject: [PATCH 62/92] edited header text
---
src/components/Home.js | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/components/Home.js b/src/components/Home.js
index a44e6d85..ac91afb1 100644
--- a/src/components/Home.js
+++ b/src/components/Home.js
@@ -22,8 +22,8 @@ const Home = () => {
return (
<>
-
- Welcome back,
+
+ Hello, welcome back!
Date: Sat, 18 Nov 2023 23:07:54 +0800
Subject: [PATCH 63/92] changed previous title document to bill-splitter
---
public/index.html | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/public/index.html b/public/index.html
index bd669818..d5c7e757 100644
--- a/public/index.html
+++ b/public/index.html
@@ -24,7 +24,7 @@
work correctly both with client-side routing and a non-root public URL.
Learn how to configure a non-root public URL by running `npm run build`.
-->
- Rocket Bootcamp Project
+ Bill-splitter
You need to enable JavaScript to run this app.
From 165a73c3276be71b789f1aea093510d105821c91 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sat, 18 Nov 2023 23:11:30 +0800
Subject: [PATCH 64/92] updated userstory
---
README.md | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/README.md b/README.md
index 7e454500..3dfd8c1d 100644
--- a/README.md
+++ b/README.md
@@ -16,7 +16,7 @@ You may also see any lint errors in the console.
# User Story
-My app is ideal for those who engage in groups, preferably in short duration outings. These users seek to avoid the hassle of manually calculating how much is owed to one another after numerous transactions are made. The app enables users to retrieve the trip created as well as the friends included until the final amount is calculated, or in the event that the app is closed. The app will send the user to a fresh trip only until the outing is completed. The add and delete functionality allows users to calculate existing transactions before entering new ones.
+This bill-splitting app is handy for those who engage in pairs or in groups and are seeking to remove the hassle of dividing costs fairly with other contributors to the activity. This app is convenient when we dine out with friends, purchase gifts, or even sharing household expenditures like utilities, house maintenances, chores, fuels with housemates. This can help avoid unnecessary disagreements when the bill splitting feature simplifies the process of dividing costs equally. Each activity created is only meant for that specific activity and contributors. Users will have to re-enter all activity details after splitting.
# How to use
From 7390ce44f888eeeb7965f730908aeabb6a2faa05 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 19 Nov 2023 10:43:48 +0800
Subject: [PATCH 65/92] add box-sizing
---
src/App.css | 4 +---
1 file changed, 1 insertion(+), 3 deletions(-)
diff --git a/src/App.css b/src/App.css
index ad4ecebd..139ec1ca 100644
--- a/src/App.css
+++ b/src/App.css
@@ -1,10 +1,10 @@
* {
margin: 0;
padding: 0;
+ box-sizing: border-box;
}
body {
- background-color: #e6cdb5;
color: black;
font-family: "Georgia";
}
@@ -12,7 +12,6 @@ body {
.left-leaf {
width: 40px;
height: 50px;
-
border-radius: 0 100px;
background-color: #fb8c00;
transform: rotate(-15deg);
@@ -22,7 +21,6 @@ body {
.right-leaf {
width: 40px;
height: 50px;
-
border-radius: 100px 0px;
background-color: #ffff00;
transform: rotate(15deg);
From b8f61877177eb827999b70d62ddfdef19bb7c80f Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 19 Nov 2023 16:34:54 +0800
Subject: [PATCH 66/92] changed standard textfield to outlined textfield and
added a border
---
src/components/Home.js | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/src/components/Home.js b/src/components/Home.js
index ac91afb1..45a2325c 100644
--- a/src/components/Home.js
+++ b/src/components/Home.js
@@ -27,8 +27,9 @@ const Home = () => {
{
setUsername(event.target.value);
From 0dde7bd63e0de0b0053b3e6113d47bba2a012bdd Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 19 Nov 2023 17:13:54 +0800
Subject: [PATCH 67/92] updated import location and some styles
---
src/App.js | 66 ++++++++++++++++++++----------------------------------
1 file changed, 24 insertions(+), 42 deletions(-)
diff --git a/src/App.js b/src/App.js
index 5f53536a..ae291420 100644
--- a/src/App.js
+++ b/src/App.js
@@ -1,7 +1,7 @@
import React from "react";
import { Routes, Route } from "react-router-dom";
-import Home from "./components/Home";
-import Dashboard from "./components/Dashboard";
+import Home from "./components/pages/Home";
+import Dashboard from "./components/pages/Dashboard";
import Container from "@mui/material/Container";
import Box from "@mui/material/Box";
@@ -10,50 +10,32 @@ import "./App.css";
const App = () => {
return (
<>
-
+
+
+
+
+
-
-
-
-
-
-
- } />
- } />
-
-
+
+ } />
+ } />
+
>
From 86cf3d9a85e0173e034b11afb5ecd45288bca702 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 19 Nov 2023 17:24:28 +0800
Subject: [PATCH 68/92] updated styles
---
src/components/pages/Dashboard.js | 64 +++++++++++++++++++++++++++++++
1 file changed, 64 insertions(+)
create mode 100644 src/components/pages/Dashboard.js
diff --git a/src/components/pages/Dashboard.js b/src/components/pages/Dashboard.js
new file mode 100644
index 00000000..edb78c45
--- /dev/null
+++ b/src/components/pages/Dashboard.js
@@ -0,0 +1,64 @@
+import React, { useState } from "react";
+import Greetings from "../greetings/Greetings";
+import { Stack, Button, Box } from "@mui/material";
+
+import Forms from "../forms/Forms";
+
+const Dashboard = () => {
+ const [isTripFormShown, setIsTripFormShown] = useState(false);
+
+ const username = JSON.parse(localStorage.getItem("user"));
+
+ // get tripname and companions details
+ const getActivityData = JSON.parse(localStorage.getItem("activityDetails"));
+
+ return (
+ <>
+
+
+
+ {!isTripFormShown && !getActivityData ? (
+ <>
+
+
+ You have no ongoing activity. Add one to begin.
+
+
+ {
+ setIsTripFormShown(true);
+ }}
+ style={{
+ backgroundColor: "#693237",
+ color: "white",
+ fontWeight: "bold",
+ width: "140px",
+ display: "block",
+ margin: "auto",
+ }}
+ disableRipple
+ >
+ Add Activity
+
+
+
+ >
+ ) : (
+
+ )}
+
+
+ >
+ );
+};
+
+export default Dashboard;
From 22e889d588a275f34c90bf50efc58cfa87950d44 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 19 Nov 2023 17:48:35 +0800
Subject: [PATCH 69/92] updated initial value of state property
---
src/components/forms/Forms.js | 36 ++++++++++++++++++++---------------
1 file changed, 21 insertions(+), 15 deletions(-)
diff --git a/src/components/forms/Forms.js b/src/components/forms/Forms.js
index 1bdef2e6..653234a4 100644
--- a/src/components/forms/Forms.js
+++ b/src/components/forms/Forms.js
@@ -2,36 +2,42 @@ import React, { useState } from "react";
import CreateForm from "./CreateForm";
import AddTransactionsForm from "./AddTransactionsForm";
-const isTripDataEntered = () => {
- const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
- if (getTripData) {
+const isActivityDataEntered = () => {
+ const getActivityData = JSON.parse(localStorage.getItem("activityDetails"));
+ if (getActivityData) {
return true;
}
return false;
};
const Forms = () => {
- const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
+ const getActivityData = JSON.parse(localStorage.getItem("activityDetails"));
- const [tripDetails, setTripDetails] = useState(
- getTripData ? getTripData : { tripname: "", items: "" }
+ const [activityDetails, setActivityDetails] = useState(
+ getActivityData ? getActivityData : { activityName: "", items: "" }
);
const [isTransactionFormShown, setIsTransactionFormShown] = useState(
- false || isTripDataEntered
+ isActivityDataEntered
);
return (
<>
{!isTransactionFormShown ? (
-
+ <>
+
+ >
) : (
-
+ <>
+
+ >
)}
>
);
From 8cc472c7deac0b3383e929b1c1be3ba1a9e3a956 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 19 Nov 2023 17:50:03 +0800
Subject: [PATCH 70/92] added border colors to each textfield
---
src/components/forms/CreateForm.js | 60 +++++++++++++++---------------
1 file changed, 31 insertions(+), 29 deletions(-)
diff --git a/src/components/forms/CreateForm.js b/src/components/forms/CreateForm.js
index ce2fbc7a..acba2df8 100644
--- a/src/components/forms/CreateForm.js
+++ b/src/components/forms/CreateForm.js
@@ -4,69 +4,71 @@ import { TextField, Stack, Button } from "@mui/material";
const title = { fontSize: "13px", fontWeight: "bold" };
-const CreateForm = ({ setTripDetails, setIsTransactionFormShown }) => {
- const [tripname, setTripname] = useState("");
- const [friends, setFriends] = useState("");
- const [items, setItems] = useState([]); //items refer to an array of friends
+const CreateForm = ({ setActivityDetails, setIsTransactionFormShown }) => {
+ const [activity, setActivity] = useState("");
+ const [contributors, setcontributors] = useState("");
+ const [items, setItems] = useState([]); //items refer to an array of contributors
- const addFriends = (event) => {
+ const addcontributors = (event) => {
event.preventDefault();
- if (!friends) {
+ if (!contributors) {
return;
}
- setItems([...items, friends]);
- setFriends("");
+ setItems([...items, contributors]);
+ setcontributors("");
};
- const deleteFriends = (itemIndex) => {
+ const deletecontributors = (itemIndex) => {
const newItem = items.filter((_, index) => index !== itemIndex);
setItems(newItem);
};
const handleSubmit = () => {
- if (!tripname || !items) {
+ if (!activity || !items) {
return;
}
- let tripDetails = {
- tripname: tripname,
+ let activityDetails = {
+ activity: activity,
items: items,
};
- setTripDetails(tripDetails);
+ setActivityDetails(activityDetails);
setIsTransactionFormShown(true);
- localStorage.setItem("tripDetails", JSON.stringify(tripDetails));
+ localStorage.setItem("activityDetails", JSON.stringify(activityDetails));
};
return (
<>
- Name of Trip
+ Activity
setTripname(event.target.value)}
- value={tripname}
+ onChange={(event) => setActivity(event.target.value)}
+ value={activity}
+ style={{ border: "1px solid black" }}
/>
- Friends
+ Contributors
setFriends(event.target.value)}
- value={friends}
+ onChange={(event) => setcontributors(event.target.value)}
+ value={contributors}
+ style={{ border: "1px solid black" }}
/>
{
maxHeight: "15vh",
}}
>
-
+
- Create a Trip
+ Create an Activity
From d1bb513d98057e935e8d00c6bff0e3f7636610a8 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 19 Nov 2023 18:10:52 +0800
Subject: [PATCH 71/92] added border colors to textfield and select elements
---
src/components/forms/AddTransactionsForm.js | 34 ++++++++++++---------
1 file changed, 19 insertions(+), 15 deletions(-)
diff --git a/src/components/forms/AddTransactionsForm.js b/src/components/forms/AddTransactionsForm.js
index 16df3ad1..ab173083 100644
--- a/src/components/forms/AddTransactionsForm.js
+++ b/src/components/forms/AddTransactionsForm.js
@@ -22,10 +22,13 @@ let getTransactionData = () => {
return [];
};
-const AddTransactionsForm = ({ tripDetails, setIsTransactionFormShown }) => {
+const AddTransactionsForm = ({
+ activityDetails,
+ setIsTransactionFormShown,
+}) => {
const [description, setDescription] = useState("");
const [price, setPrice] = useState("");
- const [payer, setPayer] = useState(tripDetails.items[0]);
+ const [payer, setPayer] = useState(activityDetails.items[0]);
const [details, setDetails] = useState(getTransactionData);
let changes = {
@@ -40,7 +43,7 @@ const AddTransactionsForm = ({ tripDetails, setIsTransactionFormShown }) => {
return;
}
setDetails([...details, changes]);
- setPayer(tripDetails.items[0]);
+ setPayer(activityDetails.items[0]);
setDescription("");
setPrice("");
storage.push(...details, changes);
@@ -52,10 +55,10 @@ const AddTransactionsForm = ({ tripDetails, setIsTransactionFormShown }) => {
setDetails(newDetails);
};
- const friends = [];
+ const contributors = [];
- tripDetails.items.forEach((word) => {
- return friends.push(word.charAt(0));
+ activityDetails.items.forEach((word) => {
+ return contributors.push(word.charAt(0));
});
return (
@@ -63,13 +66,13 @@ const AddTransactionsForm = ({ tripDetails, setIsTransactionFormShown }) => {
- {tripDetails.tripname}
+ {activityDetails.activity}
- {friends.map((friend, index) => (
+ {contributors.map((friend, index) => (
{
onChange={(e) => setDescription(e.target.value)}
id="item-field"
variant="outlined"
- style={{ width: "90px" }}
+ style={{ width: "90px", border: "1px solid black" }}
/>
@@ -99,7 +102,7 @@ const AddTransactionsForm = ({ tripDetails, setIsTransactionFormShown }) => {
onChange={(e) => setPrice(e.target.value)}
id="price-field"
variant="outlined"
- style={{ width: "90px" }}
+ style={{ width: "90px", border: "1px solid black" }}
InputProps={{
startAdornment: (
@@ -117,11 +120,12 @@ const AddTransactionsForm = ({ tripDetails, setIsTransactionFormShown }) => {
onChange={(e) => setPayer(e.target.value)}
style={{
backgroundColor: "#f7ede2",
+ border: "1px solid black",
width: "100px",
padding: "10px",
}}
>
- {tripDetails.items.map((name, index) => (
+ {activityDetails.items.map((name, index) => (
{name}
@@ -132,8 +136,8 @@ const AddTransactionsForm = ({ tripDetails, setIsTransactionFormShown }) => {
{
From 89c20fdf2b7c13baa62f540af7260c5bc3c915c7 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 19 Nov 2023 18:14:33 +0800
Subject: [PATCH 72/92] updated styles
---
src/components/calculate/Calculate.js | 9 ++++-----
1 file changed, 4 insertions(+), 5 deletions(-)
diff --git a/src/components/calculate/Calculate.js b/src/components/calculate/Calculate.js
index f1dedcaa..74bea801 100644
--- a/src/components/calculate/Calculate.js
+++ b/src/components/calculate/Calculate.js
@@ -1,5 +1,4 @@
import React, { useState } from "react";
-
import { Button, Stack, Modal } from "@mui/material";
import HomeIcon from "@mui/icons-material/Home";
import { useNavigate } from "react-router-dom";
@@ -109,8 +108,8 @@ const Calculate = ({
Date: Sun, 19 Nov 2023 18:34:10 +0800
Subject: [PATCH 73/92] updated user story and how to use paragraphs
---
README.md | 17 ++++++++++-------
1 file changed, 10 insertions(+), 7 deletions(-)
diff --git a/README.md b/README.md
index 3dfd8c1d..40c039b9 100644
--- a/README.md
+++ b/README.md
@@ -16,16 +16,19 @@ You may also see any lint errors in the console.
# User Story
-This bill-splitting app is handy for those who engage in pairs or in groups and are seeking to remove the hassle of dividing costs fairly with other contributors to the activity. This app is convenient when we dine out with friends, purchase gifts, or even sharing household expenditures like utilities, house maintenances, chores, fuels with housemates. This can help avoid unnecessary disagreements when the bill splitting feature simplifies the process of dividing costs equally. Each activity created is only meant for that specific activity and contributors. Users will have to re-enter all activity details after splitting.
+This bill-splitting app is handy for those seeking to remove the hassle of dividing costs fairly with other contributors to an activity. This app is convenient when we dine out with friends, purchase gifts, or even share household expenditures like utilities, home maintenances, and cleaning with housemates. This can help avoid unnecessary disagreements when the bill splitting feature simplifies the process of dividing costs equally. Each activity created is only meant for that specific activity and contributors. Users will have to re-enter the activity name and contributors for a new activity.
# How to use
-1. Get started on the app by entering a username.
-2. Create a trip by including the trip name and people involved in the trip.
-3. Add transactions by selecting the entering the item, price and payer from the drop down selection.
-4. Add and delete transactions whenever required.
-5. Click on calculate to derive how much each person owes one another.
-6. View the amount owed to one another, then hit the Home button to create a new trip.
+1. Enter a username and click on the arrow button.
+2. Hit the Add Activity button to create a new activity.
+3. Enter activity name and contributors involved in the activity.
+4. Add and delete contributors whenever required. Then, click on Create an Activity button.
+5. Enter the item, price and payer from the drop down selection to record transactions.
+6. Add and delete transactions whenever required.
+7. Hit the Split button to derive how much each person owes one another.
+8. Hit the Home button to create a new activity.
+9. After an activity is created, transactions of the activity will be retained when browser session is closed.
# Wireframe
From 3165ea8cf702031bf39a5c2382d5738193ebf3bb Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Sun, 19 Nov 2023 18:48:59 +0800
Subject: [PATCH 74/92] added input validation for price
---
src/components/forms/AddTransactionsForm.js | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/components/forms/AddTransactionsForm.js b/src/components/forms/AddTransactionsForm.js
index ab173083..835dbcca 100644
--- a/src/components/forms/AddTransactionsForm.js
+++ b/src/components/forms/AddTransactionsForm.js
@@ -39,7 +39,7 @@ const AddTransactionsForm = ({
const addItems = () => {
let storage = [];
- if (!description) {
+ if (!description || isNaN(Number(price))) {
return;
}
setDetails([...details, changes]);
@@ -136,7 +136,7 @@ const AddTransactionsForm = ({
Date: Sun, 19 Nov 2023 19:07:27 +0800
Subject: [PATCH 75/92] removed older version of Calculate file
---
src/components/Calculate.js | 118 ------------------------------------
1 file changed, 118 deletions(-)
delete mode 100644 src/components/Calculate.js
diff --git a/src/components/Calculate.js b/src/components/Calculate.js
deleted file mode 100644
index 608d114d..00000000
--- a/src/components/Calculate.js
+++ /dev/null
@@ -1,118 +0,0 @@
-import React, { useState } from "react";
-
-import { Button, Box, Modal } from "@mui/material";
-import HomeIcon from "@mui/icons-material/Home";
-import { useNavigate } from "react-router-dom";
-
-const style = {
- position: "absolute",
- top: "50%",
- left: "50%",
- transform: "translate(-50%, -50%",
- width: "400px",
- border: "2px solid black",
- backgroundColor: "white",
- color: "black",
-};
-
-const Calculate = ({ getTripData, getTransactions }) => {
- const [showMessage, setShowMessage] = useState(null);
- const navigate = useNavigate();
- const [open, setOpen] = useState(false);
-
- const handleClose = () => setOpen(false);
-
- const friends = getTripData.items;
-
- const getAllPrices = (entireData, entireFriends) => {
- let allPrices = [];
-
- for (let i = 0; i < entireFriends.length; i += 1) {
- let sumOfIndividualPayer = 0;
- for (let j = 0; j < entireData.length; j += 1) {
- if (entireFriends[i] === entireData[j].payer) {
- sumOfIndividualPayer += Number(entireData[j].price);
- }
- }
- allPrices.push(sumOfIndividualPayer);
- }
- return allPrices;
- };
-
- const convertToObj = (allNames, getPrices) => {
- let newObj = {};
-
- allNames.forEach((friend, amount) => {
- newObj[friend] = getPrices[amount];
- });
- return newObj;
- };
-
- let getPrices = getAllPrices(getTransactions, friends);
-
- let getNewObj = convertToObj(friends, getPrices);
-
- const handleClick = () => {
- let finalMessage = "";
- const sum = getPrices.reduce((acc, curr) => curr + acc);
-
- const meanPrices = sum / friends.length;
-
- const sortEveryone = friends.sort(
- (personA, personB) => getNewObj[personA] - getNewObj[personB]
- );
-
- const sortPrices = sortEveryone.map(
- (person) => getNewObj[person] - meanPrices
- );
-
- let firstPayer = 0;
- let lastPayer = sortEveryone.length - 1;
- let debt;
-
- while (firstPayer < lastPayer) {
- debt = Math.min(-sortPrices[firstPayer], sortPrices[lastPayer]);
- sortPrices[firstPayer] += debt;
- sortPrices[lastPayer] -= debt;
-
- finalMessage += `${sortEveryone[firstPayer]} owes ${sortEveryone[lastPayer]} $${debt}`;
-
- if (sortPrices[firstPayer] === 0) {
- firstPayer += 1;
- } else if (sortPrices[lastPayer] === 0) {
- lastPayer -= 1;
- }
- }
- setOpen(true);
-
- return setShowMessage(finalMessage);
- };
-
- const restart = () => {
- navigate("/dashboard");
- localStorage.removeItem("transactions");
- localStorage.removeItem("tripDetails");
- };
-
- return (
- <>
-
-
- {showMessage}
-
-
-
-
-
-
- Calculate Total
- >
- );
-};
-
-export default Calculate;
From aa973f7531504416d050d48b215d5769623a6c02 Mon Sep 17 00:00:00 2001
From: Qiannnly <139704626+Qiannnly@users.noreply.github.com>
Date: Sun, 19 Nov 2023 19:08:41 +0800
Subject: [PATCH 76/92] removed older version of List file
---
src/components/List.js | 37 -------------------------------------
1 file changed, 37 deletions(-)
delete mode 100644 src/components/List.js
diff --git a/src/components/List.js b/src/components/List.js
deleted file mode 100644
index c31558d3..00000000
--- a/src/components/List.js
+++ /dev/null
@@ -1,37 +0,0 @@
-import React from "react";
-
-import { Button, Stack } from "@mui/material";
-import ClearIcon from "@mui/icons-material/Clear";
-
-const List = ({ list, deleteItems }) => {
- return (
- <>
-
- {list.map((listItem, index) => (
-
-
-
- {listItem}
-
- deleteItems(index)}
- color="secondary"
- size="small"
- disableRipple
- >
-
-
-
-
- ))}
-
- >
- );
-};
-
-export default List;
From f63d6676107bc8f07aebb9ecd7dbfd6bcbcacac8 Mon Sep 17 00:00:00 2001
From: Qiannnly <139704626+Qiannnly@users.noreply.github.com>
Date: Sun, 19 Nov 2023 19:09:23 +0800
Subject: [PATCH 77/92] removed older version of PriceDescriptionList file
---
src/components/PriceDescriptionList.js | 38 --------------------------
1 file changed, 38 deletions(-)
delete mode 100644 src/components/PriceDescriptionList.js
diff --git a/src/components/PriceDescriptionList.js b/src/components/PriceDescriptionList.js
deleted file mode 100644
index a1666cdc..00000000
--- a/src/components/PriceDescriptionList.js
+++ /dev/null
@@ -1,38 +0,0 @@
-import React from "react";
-import { Button, Stack } from "@mui/material";
-import ClearIcon from "@mui/icons-material/Clear";
-
-const PriceDescriptionList = ({ details, deleteItems }) => {
- return (
- <>
-
- {details.map((detail, index) => (
- <>
-
-
- Item: {detail.description}
-
- Price: ${detail.price}
-
- Payer: {detail.payer}
-
-
-
- deleteItems(index)}
- color="secondary"
- size="small"
- variant="contained"
- disableRipple
- >
-
-
-
- >
- ))}
-
- >
- );
-};
-
-export default PriceDescriptionList;
From 81a9cc1ddf7dbae942eb0f61bb211e54b8b812e3 Mon Sep 17 00:00:00 2001
From: Qiannnly <139704626+Qiannnly@users.noreply.github.com>
Date: Sun, 19 Nov 2023 19:10:13 +0800
Subject: [PATCH 78/92] removed older version of Greetings file
---
src/components/Greetings.js | 40 -------------------------------------
1 file changed, 40 deletions(-)
delete mode 100644 src/components/Greetings.js
diff --git a/src/components/Greetings.js b/src/components/Greetings.js
deleted file mode 100644
index 8036bd66..00000000
--- a/src/components/Greetings.js
+++ /dev/null
@@ -1,40 +0,0 @@
-import React, { useState, useEffect } from "react";
-import { Stack } from "@mui/material";
-
-const Greetings = ({ username }) => {
- const [currentDate, setCurrentDate] = useState(new Date());
- const currentTime = `${currentDate.getHours()} : ${currentDate.getMinutes()} : ${currentDate.getSeconds()}`;
- const currHour = currentDate.getHours();
-
- useEffect(() => {
- setInterval(() => setCurrentDate(new Date()), 1000);
- });
-
- const greet = () => {
- let greetings;
- if (currHour >= 6 && currHour < 12) {
- greetings = "Good morning";
- } else if (currHour >= 12 && currHour < 17) {
- greetings = "Good afternoon";
- } else {
- greetings = "Good evening";
- }
- return greetings;
- };
-
- let greetMessage = `${greet()} ${username},`;
-
- return (
- <>
-
- {`${currentDate.toDateString()}, ${currentTime}`}
-
-
- {greetMessage}
-
-
- >
- );
-};
-
-export default Greetings;
From 58dba3ff115eaa8c6aacf114515a564f3bdf6305 Mon Sep 17 00:00:00 2001
From: Qiannnly <139704626+Qiannnly@users.noreply.github.com>
Date: Sun, 19 Nov 2023 19:10:41 +0800
Subject: [PATCH 79/92] removed older version of AddTransactionsForm file
---
src/components/AddTransactionsForm.js | 120 --------------------------
1 file changed, 120 deletions(-)
delete mode 100644 src/components/AddTransactionsForm.js
diff --git a/src/components/AddTransactionsForm.js b/src/components/AddTransactionsForm.js
deleted file mode 100644
index 653b579b..00000000
--- a/src/components/AddTransactionsForm.js
+++ /dev/null
@@ -1,120 +0,0 @@
-import React, { useState } from "react";
-
-import PriceDescriptionList from "./PriceDescriptionList";
-import { TextField, Stack, InputAdornment, Button } from "@mui/material";
-import AttachMoneyIcon from "@mui/icons-material/AttachMoney";
-import Calculate from "./Calculate";
-
-const AddTransactionsForm = ({ tripDetails }) => {
- // const getTripData = JSON.parse(localStorage.getItem("formObject"));
- console.log(tripDetails);
- const [description, setDescription] = useState("");
- const [price, setPrice] = useState("");
- const [payer, setPayer] = useState(tripDetails.items[0]);
-
- let getTransactionData = () => {
- const data = JSON.parse(localStorage.getItem("transactions"));
- if (data !== null) {
- return data;
- }
- return [];
- };
-
- const [details, setDetails] = useState(getTransactionData);
-
- let changes = {
- description: description,
- price: price,
- payer: payer,
- };
-
- const addItems = (event) => {
- event.preventDefault();
- let storage = [];
- if (!Number(price) && !description) {
- return;
- }
-
- setDetails([...details, changes]);
-
- setPayer(tripDetails[0]);
-
- setDescription("");
- setPrice("");
-
- storage.push(...details, changes);
- console.log(storage);
- localStorage.setItem("transactions", JSON.stringify(storage));
- };
-
- const deleteItems = (detailIndex) => {
- const newDetails = details.filter((_, index) => index !== detailIndex);
- setDetails(newDetails);
- };
-
- console.log(details);
- return (
- <>
- {tripDetails.tripname}
- {tripDetails.items}
-
-
-
- Item Description
-
- setDescription(e.target.value)}
- size="small"
- >
-
-
- Price
- setPrice(e.target.value)}
- size="small"
- InputProps={{
- startAdornment: (
-
-
-
- ),
- }}
- >
-
-
-
- setPayer(e.target.value)}
- name="payer"
- >
- {tripDetails.items.map((name, index) => (
- {name}
- ))}
- {" "}
- paid
-
-
- +
-
-
-
-
- >
- );
-};
-
-export default AddTransactionsForm;
From a0075711e9cc67b8b95f9629aabdf8a57c842b83 Mon Sep 17 00:00:00 2001
From: Qiannnly <139704626+Qiannnly@users.noreply.github.com>
Date: Sun, 19 Nov 2023 19:11:10 +0800
Subject: [PATCH 80/92] removed older version of CreateForm file
---
src/components/CreateForm.js | 87 ------------------------------------
1 file changed, 87 deletions(-)
delete mode 100644 src/components/CreateForm.js
diff --git a/src/components/CreateForm.js b/src/components/CreateForm.js
deleted file mode 100644
index d9294ad8..00000000
--- a/src/components/CreateForm.js
+++ /dev/null
@@ -1,87 +0,0 @@
-import React, { useState } from "react";
-import List from "./List";
-import { TextField, Stack, Button } from "@mui/material";
-
-const CreateForm = ({ setTripDetails, setshowTransactionForm }) => {
- const [tripname, setTripname] = useState("");
- const [friends, setFriends] = useState("");
-
- //items refer to an array of friends
- const [items, setItems] = useState([]);
-
- const addFriends = (event) => {
- event.preventDefault();
- if (!friends) {
- return;
- }
- setItems([...items, friends]);
- setFriends("");
- };
-
- const deleteFriends = (itemIndex) => {
- const newItem = items.filter((_, index) => index !== itemIndex);
- setItems(newItem);
- };
- const handleSubmit = () => {
- if (!tripname || !items) {
- return;
- }
-
- let tripDetails = {
- tripname: tripname,
- items: items,
- };
- setshowTransactionForm(true);
- setTripDetails(tripDetails);
-
- localStorage.setItem("tripDetails", JSON.stringify(tripDetails));
- };
- return (
- <>
-
- Name of Trip
- setTripname(event.target.value)}
- value={tripname}
- size="small"
- style={{ border: "1px solid white" }}
- >
-
-
-
- Add Friends
-
-
- setFriends(event.target.value)}
- value={friends}
- size="small"
- style={{ border: "1px solid white" }}
- >
-
- +
-
-
-
-
- Create Form
-
-
- >
- );
-};
-
-export default CreateForm;
From eeb57b19e6d678a1ec27df39741c079c4256a6a4 Mon Sep 17 00:00:00 2001
From: Qiannnly <139704626+Qiannnly@users.noreply.github.com>
Date: Sun, 19 Nov 2023 19:11:33 +0800
Subject: [PATCH 81/92] removed older version of Forms file
---
src/components/Forms.js | 37 -------------------------------------
1 file changed, 37 deletions(-)
delete mode 100644 src/components/Forms.js
diff --git a/src/components/Forms.js b/src/components/Forms.js
deleted file mode 100644
index a4f0ae91..00000000
--- a/src/components/Forms.js
+++ /dev/null
@@ -1,37 +0,0 @@
-import React, { useState } from "react";
-import CreateForm from "./CreateForm";
-import AddTransactionsForm from "./AddTransactionsForm";
-
-const isTripDataEntered = () => {
- const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
- if (getTripData) {
- return true;
- }
- return false;
-};
-
-const Forms = () => {
- const getTripData = JSON.parse(localStorage.getItem("tripDetails"));
-
- const [tripDetails, setTripDetails] = useState(
- getTripData ? getTripData : { tripname: "", items: "" }
- );
- const [showTransactionForm, setshowTransactionForm] = useState(
- false || isTripDataEntered
- );
-
- return (
- <>
- {!showTransactionForm ? (
-
- ) : (
-
- )}
- >
- );
-};
-
-export default Forms;
From fe2be942d6a7676781a8c0fca962dedd88fcce03 Mon Sep 17 00:00:00 2001
From: Qiannnly <139704626+Qiannnly@users.noreply.github.com>
Date: Sun, 19 Nov 2023 19:12:52 +0800
Subject: [PATCH 82/92] removed older version of Dashboard file
---
src/components/Dashboard.js | 70 -------------------------------------
1 file changed, 70 deletions(-)
delete mode 100644 src/components/Dashboard.js
diff --git a/src/components/Dashboard.js b/src/components/Dashboard.js
deleted file mode 100644
index 98952385..00000000
--- a/src/components/Dashboard.js
+++ /dev/null
@@ -1,70 +0,0 @@
-import React, { useState } from "react";
-import Greetings from "./greetings/Greetings";
-import { Stack, Button, Box } from "@mui/material";
-
-import Forms from "./forms/Forms";
-
-const Dashboard = () => {
- const [isTripFormShown, setIsTripFormShown] = useState(false);
-
- const username = JSON.parse(localStorage.getItem("user"));
-
- // get tripname and companions details
- const getActivityData = JSON.parse(localStorage.getItem("activityDetails"));
-
- return (
- <>
-
-
-
- {!isTripFormShown && !getActivityData ? (
- <>
-
-
- You have no ongoing activity. Add one to begin.
-
-
- {
- setIsTripFormShown(true);
- }}
- style={{
- backgroundColor: "#ec407a",
- color: "white",
- fontWeight: "bold",
- width: "140px",
-
- display: "block",
- margin: "auto",
- }}
- disableRipple
- >
- Add Activity
-
-
-
- >
- ) : (
-
- )}
-
-
- >
- );
-};
-
-export default Dashboard;
From 790b66b2870aeec64dba4e146a11b321f2f56dfc Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Tue, 21 Nov 2023 20:50:38 +0800
Subject: [PATCH 83/92] committing latest changes
---
src/App.css | 4 ++--
src/components/forms/AddTransactionsForm.js | 2 +-
src/components/forms/Forms.js | 2 +-
src/components/greetings/Greetings.js | 5 +----
src/components/{ => pages}/Home.js | 1 -
5 files changed, 5 insertions(+), 9 deletions(-)
rename src/components/{ => pages}/Home.js (99%)
diff --git a/src/App.css b/src/App.css
index 139ec1ca..a8b6fd9d 100644
--- a/src/App.css
+++ b/src/App.css
@@ -13,7 +13,7 @@ body {
width: 40px;
height: 50px;
border-radius: 0 100px;
- background-color: #fb8c00;
+ background-color: #ec407a;
transform: rotate(-15deg);
border: 2px solid black;
}
@@ -22,7 +22,7 @@ body {
width: 40px;
height: 50px;
border-radius: 100px 0px;
- background-color: #ffff00;
+ background-color: #c18a54;
transform: rotate(15deg);
border: 2px solid black;
}
diff --git a/src/components/forms/AddTransactionsForm.js b/src/components/forms/AddTransactionsForm.js
index 835dbcca..18e11ce6 100644
--- a/src/components/forms/AddTransactionsForm.js
+++ b/src/components/forms/AddTransactionsForm.js
@@ -39,7 +39,7 @@ const AddTransactionsForm = ({
const addItems = () => {
let storage = [];
- if (!description || isNaN(Number(price))) {
+ if (!description || isNaN(Number(price)) || !price) {
return;
}
setDetails([...details, changes]);
diff --git a/src/components/forms/Forms.js b/src/components/forms/Forms.js
index 653234a4..f2bcb2e4 100644
--- a/src/components/forms/Forms.js
+++ b/src/components/forms/Forms.js
@@ -14,7 +14,7 @@ const Forms = () => {
const getActivityData = JSON.parse(localStorage.getItem("activityDetails"));
const [activityDetails, setActivityDetails] = useState(
- getActivityData ? getActivityData : { activityName: "", items: "" }
+ getActivityData ? getActivityData : { activity: "", items: "" }
);
const [isTransactionFormShown, setIsTransactionFormShown] = useState(
isActivityDataEntered
diff --git a/src/components/greetings/Greetings.js b/src/components/greetings/Greetings.js
index c7e32b41..7e90ba4b 100644
--- a/src/components/greetings/Greetings.js
+++ b/src/components/greetings/Greetings.js
@@ -28,15 +28,12 @@ const Greetings = ({ username }) => {
<>
diff --git a/src/components/Home.js b/src/components/pages/Home.js
similarity index 99%
rename from src/components/Home.js
rename to src/components/pages/Home.js
index 45a2325c..09bbfbe6 100644
--- a/src/components/Home.js
+++ b/src/components/pages/Home.js
@@ -1,7 +1,6 @@
import React, { useState } from "react";
import { useNavigate } from "react-router-dom";
import { Button, TextField, Stack, InputAdornment } from "@mui/material";
-
import { AccountCircle } from "@mui/icons-material";
import EastIcon from "@mui/icons-material/East";
From 7d907932dd467a0e4ddbca91931783afabe1dd09 Mon Sep 17 00:00:00 2001
From: qiannnly
Date: Wed, 22 Nov 2023 19:06:11 +0800
Subject: [PATCH 84/92] updated latest changes
---
public/favicon.ico | Bin 15406 -> 24174 bytes
public/index.html | 5 +++--
public/logo192.png | Bin 11410 -> 0 bytes
public/logo512.png | Bin 35785 -> 0 bytes
public/manifest.json | 10 ----------
5 files changed, 3 insertions(+), 12 deletions(-)
mode change 100755 => 100644 public/favicon.ico
delete mode 100755 public/logo192.png
delete mode 100755 public/logo512.png
diff --git a/public/favicon.ico b/public/favicon.ico
old mode 100755
new mode 100644
index c17bf23f2a9d89c137737f64a1c25eac3c88f5cc..69ccfc2944d0ec64ea3e9c2bfa8528ff7fd8e4d9
GIT binary patch
literal 24174
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
-
+
-
+
+
-
-
+
+