diff --git a/docs/spec/CodeCharacter-API.yml b/docs/spec/CodeCharacter-API.yml index 4a3ee6f..0e322f3 100644 --- a/docs/spec/CodeCharacter-API.yml +++ b/docs/spec/CodeCharacter-API.yml @@ -1570,8 +1570,44 @@ paths: description: Size of the page parameters: [] + '/stats/': + get: + summary: Get all General Stats for current user and top user + tags: + - stats + responses: + '200': + description: OK + content: + application/json: + schema: + type: array + items: + $ref: '#/components/schemas/UserMatchStats' + operationId: getStats + description: Gets all statistics for the current user + parameters: [] + components: schemas: + UserMatchStats: + title: UserMatchStats + type: object + description: User Match Stats model + properties: + avgAtk: + type: number + default: 0 + dc_wins: + type: number + default: 0 + coins: + type: number + default: 0 + required: + - avgAtk + - dc_wins + - coins PasswordLoginRequest: title: PasswordLoginRequest type: object @@ -2554,3 +2590,4 @@ tags: - name: match - name: notification - name: user + - name: stats diff --git a/package.json b/package.json index fc727ae..3974e51 100644 --- a/package.json +++ b/package.json @@ -62,6 +62,7 @@ "react-router-dom": "^6.6.1", "react-split-pane": "^0.1.92", "react-vertical-timeline-component": "^3.6.0", + "recharts": "^2.10.3", "redux": "^4.2.0", "redux-persist": "^6.0.0", "vscode-ws-jsonrpc": "^2.0.2", diff --git a/packages/client/.openapi-generator/FILES b/packages/client/.openapi-generator/FILES index 2b446d7..ed24da6 100644 --- a/packages/client/.openapi-generator/FILES +++ b/packages/client/.openapi-generator/FILES @@ -9,6 +9,7 @@ src/apis/MapApi.ts src/apis/MatchApi.ts src/apis/NotificationApi.ts src/apis/PvpGameApi.ts +src/apis/StatsApi.ts src/apis/UserApi.ts src/apis/index.ts src/index.ts diff --git a/packages/client/src/apis/StatsApi.ts b/packages/client/src/apis/StatsApi.ts new file mode 100644 index 0000000..4f15029 --- /dev/null +++ b/packages/client/src/apis/StatsApi.ts @@ -0,0 +1,91 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * CodeCharacter API + * Specification of the CodeCharacter API + * + * The version of the OpenAPI document: 2023.0.1 + * Contact: delta@nitt.edu + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import * as runtime from '../runtime'; +import type { UserMatchStats } from '../models'; + +/** + * StatsApi - interface + * + * @export + * @interface StatsApiInterface + */ +export interface StatsApiInterface { + /** + * Gets all statistics for the current user + * @summary Get all General Stats for current user and top user + * @param {*} [options] Override http request option. + * @throws {RequiredError} + * @memberof StatsApiInterface + */ + getStatsRaw( + initOverrides?: RequestInit | runtime.InitOverrideFunction, + ): Promise>>; + + /** + * Gets all statistics for the current user + * Get all General Stats for current user and top user + */ + getStats( + initOverrides?: RequestInit | runtime.InitOverrideFunction, + ): Promise>; +} + +/** + * + */ +export class StatsApi extends runtime.BaseAPI implements StatsApiInterface { + /** + * Gets all statistics for the current user + * Get all General Stats for current user and top user + */ + async getStatsRaw( + initOverrides?: RequestInit | runtime.InitOverrideFunction, + ): Promise>> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.accessToken) { + const token = this.configuration.accessToken; + const tokenString = await token('http-bearer', []); + + if (tokenString) { + headerParameters['Authorization'] = `Bearer ${tokenString}`; + } + } + const response = await this.request( + { + path: `/stats/`, + method: 'GET', + headers: headerParameters, + query: queryParameters, + }, + initOverrides, + ); + + return new runtime.JSONApiResponse(response); + } + + /** + * Gets all statistics for the current user + * Get all General Stats for current user and top user + */ + async getStats( + initOverrides?: RequestInit | runtime.InitOverrideFunction, + ): Promise> { + const response = await this.getStatsRaw(initOverrides); + return await response.value(); + } +} diff --git a/packages/client/src/apis/index.ts b/packages/client/src/apis/index.ts index 6c795c5..71d785d 100644 --- a/packages/client/src/apis/index.ts +++ b/packages/client/src/apis/index.ts @@ -10,4 +10,5 @@ export * from './MapApi'; export * from './MatchApi'; export * from './NotificationApi'; export * from './PvpGameApi'; +export * from './StatsApi'; export * from './UserApi'; diff --git a/packages/client/src/models/index.ts b/packages/client/src/models/index.ts index 4191e3b..5fc4643 100644 --- a/packages/client/src/models/index.ts +++ b/packages/client/src/models/index.ts @@ -1238,6 +1238,31 @@ export interface UpdatePasswordRequest { */ passwordConfirmation: string; } +/** + * User Match Stats model + * @export + * @interface UserMatchStats + */ +export interface UserMatchStats { + /** + * + * @type {number} + * @memberof UserMatchStats + */ + avgAtk: number; + /** + * + * @type {number} + * @memberof UserMatchStats + */ + dcWins: number; + /** + * + * @type {number} + * @memberof UserMatchStats + */ + coins: number; +} /** * User stats model * @export diff --git a/src/AllRoutes.tsx b/src/AllRoutes.tsx index 97ef247..5a403e6 100644 --- a/src/AllRoutes.tsx +++ b/src/AllRoutes.tsx @@ -31,7 +31,7 @@ const IncompleteProfile = lazy( import('./components/Auth/Auth/Login/IncompleteProfile/incompeleteProfile'), ); const Profile = lazy(() => import('./components/Profile/Profile')); - +const Statistics = lazy(() => import('./pages/Statistics/Statistics')); export default function AllRoutes(): JSX.Element { const dispatch = useAppDispatch(); const logIn = useAppSelector(isloggedIn); @@ -46,6 +46,7 @@ export default function AllRoutes(): JSX.Element { } /> } /> + } /> } /> } /> } /> diff --git a/src/assets/codes b/src/assets/codes index ce8ccff..948f577 160000 --- a/src/assets/codes +++ b/src/assets/codes @@ -1 +1 @@ -Subproject commit ce8ccff27639c3276f3ede05246d47a42971c6bf +Subproject commit 948f577896b4f4802e9701028032fe2580dcc9e1 diff --git a/src/assets/statistics.svg b/src/assets/statistics.svg new file mode 100644 index 0000000..a49072e --- /dev/null +++ b/src/assets/statistics.svg @@ -0,0 +1,22 @@ + + + + + + + + + + + + diff --git a/src/components/GraphFooter/GraphSelector.module.css b/src/components/GraphFooter/GraphSelector.module.css new file mode 100644 index 0000000..85f716e --- /dev/null +++ b/src/components/GraphFooter/GraphSelector.module.css @@ -0,0 +1,30 @@ +.title { + border: 1px solid #ffffff50 !important; + border-radius: 10px; + background: #ffffff05 !important; + font-size: 1rem; + box-shadow: none !important; + font-family: monospace !important; + align-self: end; +} + +.footer { + background-color: #10101080 !important; + backdrop-filter: blur(30px); + color: white; + font-size: 3rem; + text-align: center; + border: 1px solid #ffffff50 !important; + font-family: monospace !important; +} + +.button:hover { + background-color: transparent !important; + color: #ffffffa0; +} + +.button { + color: white; + text-align: center; + font-size: 1rem; +} diff --git a/src/components/GraphFooter/GraphSelector.tsx b/src/components/GraphFooter/GraphSelector.tsx new file mode 100644 index 0000000..ce0321c --- /dev/null +++ b/src/components/GraphFooter/GraphSelector.tsx @@ -0,0 +1,31 @@ +import { ButtonGroup, Dropdown } from 'react-bootstrap'; +import styles from './GraphSelector.module.css'; +import DropdownMenu from 'react-bootstrap/esm/DropdownMenu'; +const GraphSelecter = ({ graph, selected, setSelected }: GraphFooterProps) => { + return ( +
+ + + {graph[selected]} + + + {[...graph].map((g, i) => { + return ( + { + setSelected(i); + }} + > + {g} + + ); + })} + + +
+ ); +}; +export default GraphSelecter; diff --git a/src/components/GraphFooter/types.d.ts b/src/components/GraphFooter/types.d.ts new file mode 100644 index 0000000..80dc295 --- /dev/null +++ b/src/components/GraphFooter/types.d.ts @@ -0,0 +1,5 @@ +type GraphFooterProps = { + graph: string[]; + selected: number; + setSelected: React.Dispatch>; +}; diff --git a/src/components/GraphToolTips/GraphToolTip.module.css b/src/components/GraphToolTips/GraphToolTip.module.css new file mode 100644 index 0000000..378c8b2 --- /dev/null +++ b/src/components/GraphToolTips/GraphToolTip.module.css @@ -0,0 +1,13 @@ +.barChartToolTip { + background-color: #1a1a1aca; + backdrop-filter: blur(4rem); + color: white; + font-family: monospace; + font-size: 1rem; + font-weight: 900; + padding: 10px 10px 0px; + border-radius: 5px; + display: flex; + justify-content: center; + align-items: center; +} diff --git a/src/components/GraphToolTips/ToolTips.tsx b/src/components/GraphToolTips/ToolTips.tsx new file mode 100644 index 0000000..93a9a84 --- /dev/null +++ b/src/components/GraphToolTips/ToolTips.tsx @@ -0,0 +1,85 @@ +import styles from './GraphToolTip.module.css'; +export const BarChartToolTip = ({ active, payload }: ToolTipProps) => { + console.log(active); + console.log(payload); + if (active && payload && payload.length) { + return ( +
+
    +
  • {`Your Wins: ${payload[0].value}`}
  • +
  • {`Your Losses: ${payload[1].value}`}
  • +
+
+ ); + } + + return null; +}; + +export const LineChartToolTip = ({ active, payload }: ToolTipProps) => { + console.log(active); + console.log(payload); + + if (active && payload && payload.length) { + return ( +
+
    + {payload.length == 2 && ( +
  • {`Your Attacks ${payload[0].value}%`}
  • + )} +
  • {`Leaderboard Top: ${ + payload.at(-1).value + }%`}
  • +
+
+ ); + } + return null; +}; + +export const AreaChartToolTip = ({ active, payload }: ToolTipProps) => { + console.log(active); + console.log(payload); + + if (active && payload && payload.length) { + return ( +
+
+

Coins Used By:

+
    + {payload.length == 2 && ( +
  • {`You: ${payload[0].value}`}
  • + )} +
  • {`Leaderboard Top: ${ + payload.at(-1).value + }`}
  • +
+
+
+ ); + } + return null; +}; +export const DCToolTip = ({ active, payload }: ToolTipProps) => { + console.log(active); + console.log(payload); + + if (active && payload && payload.length) { + return ( +
+
+

Daily Challenges Attempts Made:

+
    + {payload.length == 2 && ( +
  • {`You: ${payload[0].value}`}
  • + )} +
  • {`Leaderboard Top: ${ + payload.at(-1).value + }`}
  • +
+
+
+ ); + } + return null; +}; diff --git a/src/components/GraphToolTips/types.d.ts b/src/components/GraphToolTips/types.d.ts new file mode 100644 index 0000000..51c859e --- /dev/null +++ b/src/components/GraphToolTips/types.d.ts @@ -0,0 +1,5 @@ +type ToolTipProps = { + active: any; + payload: any; + label: any; +}; diff --git a/src/components/RatingChart/RatingChart.tsx b/src/components/RatingChart/RatingChart.tsx index 1e1f2a6..9b863ef 100644 --- a/src/components/RatingChart/RatingChart.tsx +++ b/src/components/RatingChart/RatingChart.tsx @@ -94,7 +94,6 @@ function RatingHistoryChart() { setLabelItems(labels); }); }, [isLoaded]); - function fetchRatingHistory(id: string) { setIsLoaded(false); const ratingHistory = userApi.getRatingHistory(id); diff --git a/src/components/SideBar/SideBar.tsx b/src/components/SideBar/SideBar.tsx index 6cab8df..7d34a3a 100644 --- a/src/components/SideBar/SideBar.tsx +++ b/src/components/SideBar/SideBar.tsx @@ -9,6 +9,7 @@ import leaderboardIcon from '../../assets/leaderboard.svg'; import commitIcon from '../../assets/commit.svg'; import battletvIcon from '../../assets/battletv.svg'; import documentationIcon from '../../assets/documentation.svg'; +import statisticsIcon from '../../assets/statistics.svg'; import { Link, useLocation } from 'react-router-dom'; import { useEffect, useState } from 'react'; @@ -29,6 +30,7 @@ const icons = [ { icon: leaderboardIcon, route: 'leaderboard', tooltip: 'Leaderboard' }, { icon: commitIcon, route: 'history', tooltip: 'Commits' }, { icon: battletvIcon, route: 'battletv', tooltip: 'Battle TV' }, + { icon: statisticsIcon, route: 'statistics', tooltip: 'Statistics' }, ]; const SideBar: React.FunctionComponent = () => { diff --git a/src/pages/Statistics/Statistics.module.css b/src/pages/Statistics/Statistics.module.css new file mode 100644 index 0000000..34f75f7 --- /dev/null +++ b/src/pages/Statistics/Statistics.module.css @@ -0,0 +1,85 @@ +.bg { + display: flex; + justify-content: center; + align-items: center; + overflow: hidden; + background-color: #00000072; + backdrop-filter: blur(17px); + flex-direction: column; +} + +.title { + text-align: center; + padding: 20px; + color: white; + transform: translateY(-40px); + letter-spacing: 5px; + font-family: monospace, sans-serif; + font-weight: 900; + z-index: 1; +} + +.labelX { + font-family: monospace, sans-serif; + font-weight: 900; + font-size: 1rem; + width: 12.5rem; + color: grey; +} + +.graphParent { + width: 100%; + display: flex; + justify-content: center; + align-items: center; +} + +.parent { + display: grid; + height: 100%; +} + +.bg, +.footer { + grid-area: 1/1; +} + +.footer { + display: flex; + align-items: center; + justify-content: center; + height: fit-content; + padding-top: 3rem; +} + +.lines { + stroke-width: 4px !important; +} + +.axis { + font-family: monospace; + font-size: 1.1rem; + stroke-width: 4px; + font-size: 1.1rem; + font-weight: 900; +} + +.graphContainer { + margin-top: 2%; + flex-shrink: 0; + display: flex; + align-items: flex-end; + justify-content: center; + flex-direction: column; + height: fit-content; + width: fit-content; +} + +.error { + text-align: center; + color: white; + letter-spacing: 5px; + font-size: 1.5rem; + font-family: monospace, sans-serif; + font-weight: 900; +} diff --git a/src/pages/Statistics/Statistics.tsx b/src/pages/Statistics/Statistics.tsx new file mode 100644 index 0000000..39c331d --- /dev/null +++ b/src/pages/Statistics/Statistics.tsx @@ -0,0 +1,352 @@ +import styles from './Statistics.module.css'; +import { + LineChart, + Line, + XAxis, + YAxis, + CartesianGrid, + Area, + AreaChart, + Legend, + Tooltip, +} from 'recharts'; +import GraphSelecter from '../../components/GraphFooter/GraphSelector'; +import { apiConfig, ApiError } from '../../api/ApiConfig'; +import { StatsApi } from '@codecharacter-2024/client'; +import { useState, useEffect } from 'react'; +import Toast from 'react-hot-toast'; +import { + DCToolTip, + LineChartToolTip, + AreaChartToolTip, +} from '../../components/GraphToolTips/ToolTips'; + +const Statistics = () => { + const [selected, setSelected] = useState(0); + const [data, setData] = useState({}); + const [top, setTop] = useState(true); + + const fetchTop = () => { + const statisticsApi = new StatsApi(apiConfig); + statisticsApi + .getStats() + .then(response => { + const cdata = []; + for (let i = 0; i < response[0].length; i++) { + const currentDataObject = {}; + const player1Data = response[0][i]; + let player2Data = response[0][i]; + if (response.length == 2) { + setTop(false); + player2Data = response[1][i]; + } + for (const keys in player1Data) { + currentDataObject[`${keys}1`] = player1Data[keys]; + currentDataObject[`${keys}2`] = player2Data[keys]; + } + cdata.push(currentDataObject); + } + console.log(cdata); + setData(cdata); + }) + .catch(error => { + setData(null); + if (error instanceof ApiError) Toast.error(error.message); + }); + }; + useEffect(() => { + fetchTop(); + }, []); + const titles = [ + 'Average Attack Rates', + 'Coins Usage Per Match', + 'Daily Challenges Wins', + ]; + return ( + <> +
+ {data != null ? ( + <> +
+

{titles[selected]}

+
+
+
+ +
+ {selected == 0 && ( + + + + + + + + + + + + + + + } + /> + + {!top && ( + + )} + + + + + )} + {selected == 1 && ( + + + + + + + + + + + + + + + } + /> + + {!top && ( + + )} + + + + + )} + {selected == 2 && ( + + + + + + + } + /> + {!top && ( + + )} + + + )} +
+
+
+ + ) : ( +
+ Start a match for recoding statistics! +
+ )} +
+ + ); +}; + +export default Statistics; diff --git a/yarn.lock b/yarn.lock index b263086..75c4835 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1564,6 +1564,15 @@ __metadata: languageName: node linkType: hard +"@babel/runtime@npm:^7.1.2": + version: 7.23.6 + resolution: "@babel/runtime@npm:7.23.6" + dependencies: + regenerator-runtime: ^0.14.0 + checksum: 1a8eaf3d3a103ef5227b60ca7ab5c589118c36ca65ef2d64e65380b32a98a3f3b5b3ef96660fa0471b079a18b619a8317f3e7f03ab2b930c45282a8b69ed9a16 + languageName: node + linkType: hard + "@babel/runtime@npm:^7.10.4, @babel/runtime@npm:^7.11.2, @babel/runtime@npm:^7.12.1, @babel/runtime@npm:^7.12.5, @babel/runtime@npm:^7.17.2, @babel/runtime@npm:^7.20.7, @babel/runtime@npm:^7.3.1, @babel/runtime@npm:^7.4.4, @babel/runtime@npm:^7.5.0, @babel/runtime@npm:^7.5.5, @babel/runtime@npm:^7.6.3, @babel/runtime@npm:^7.7.2, @babel/runtime@npm:^7.7.6, @babel/runtime@npm:^7.8.4, @babel/runtime@npm:^7.8.7, @babel/runtime@npm:^7.9.2": version: 7.21.0 resolution: "@babel/runtime@npm:7.21.0" @@ -1759,6 +1768,7 @@ __metadata: react-split-pane: ^0.1.92 react-test-renderer: ^18.2.0 react-vertical-timeline-component: ^3.6.0 + recharts: ^2.10.3 redux: ^4.2.0 redux-persist: ^6.0.0 rollup-plugin-workbox: ^6.2.0 @@ -3980,6 +3990,75 @@ __metadata: languageName: node linkType: hard +"@types/d3-array@npm:^3.0.3": + version: 3.2.1 + resolution: "@types/d3-array@npm:3.2.1" + checksum: 8a41cee0969e53bab3f56cc15c4e6c9d76868d6daecb2b7d8c9ce71e0ececccc5a8239697cc52dadf5c665f287426de5c8ef31a49e7ad0f36e8846889a383df4 + languageName: node + linkType: hard + +"@types/d3-color@npm:*": + version: 3.1.3 + resolution: "@types/d3-color@npm:3.1.3" + checksum: 8a0e79a709929502ec4effcee2c786465b9aec51b653ba0b5d05dbfec3e84f418270dd603002d94021885061ff592f614979193bd7a02ad76317f5608560e357 + languageName: node + linkType: hard + +"@types/d3-ease@npm:^3.0.0": + version: 3.0.2 + resolution: "@types/d3-ease@npm:3.0.2" + checksum: 0885219966294bfc99548f37297e1c75e75da812a5f3ec941977ebb57dcab0a25acec5b2bbd82d09a49d387daafca08521ca269b7e4c27ddca7768189e987b54 + languageName: node + linkType: hard + +"@types/d3-interpolate@npm:^3.0.1": + version: 3.0.4 + resolution: "@types/d3-interpolate@npm:3.0.4" + dependencies: + "@types/d3-color": "*" + checksum: efd2770e174e84fc7316fdafe03cf3688451f767dde1fa6211610137f495be7f3923db7e1723a6961a0e0e9ae0ed969f4f47c038189fa0beb1d556b447922622 + languageName: node + linkType: hard + +"@types/d3-path@npm:*": + version: 3.0.2 + resolution: "@types/d3-path@npm:3.0.2" + checksum: 0107d89510e19e478c168e0e5df0c901f57e12f42f90f961a52b0b1e5b58182dde14a5b27ef66a0a769f09119f305d484dd8dc5adca17f6dd74baab87ad36a98 + languageName: node + linkType: hard + +"@types/d3-scale@npm:^4.0.2": + version: 4.0.8 + resolution: "@types/d3-scale@npm:4.0.8" + dependencies: + "@types/d3-time": "*" + checksum: 3b1906da895564f73bb3d0415033d9a8aefe7c4f516f970176d5b2ff7a417bd27ae98486e9a9aa0472001dc9885a9204279a1973a985553bdb3ee9bbc1b94018 + languageName: node + linkType: hard + +"@types/d3-shape@npm:^3.1.0": + version: 3.1.6 + resolution: "@types/d3-shape@npm:3.1.6" + dependencies: + "@types/d3-path": "*" + checksum: bd765be021019c43c8dca066a798a1de28a051d1213db6ca25f76c9e577da7ec40a592e3bda7628383ab48cb87164fe60b95eb5ec23761b2012bd0adb30c549a + languageName: node + linkType: hard + +"@types/d3-time@npm:*, @types/d3-time@npm:^3.0.0": + version: 3.0.3 + resolution: "@types/d3-time@npm:3.0.3" + checksum: a071826c80efdb1999e6406fef2db516d45f3906da3a9a4da8517fa863bae53c4c1056ca5347a20921660607d21ec874fd2febe0e961adb7be6954255587d08f + languageName: node + linkType: hard + +"@types/d3-timer@npm:^3.0.0": + version: 3.0.2 + resolution: "@types/d3-timer@npm:3.0.2" + checksum: 1643eebfa5f4ae3eb00b556bbc509444d88078208ec2589ddd8e4a24f230dd4cf2301e9365947e70b1bee33f63aaefab84cd907822aae812b9bc4871b98ab0e1 + languageName: node + linkType: hard + "@types/eslint-scope@npm:^3.7.3": version: 3.7.4 resolution: "@types/eslint-scope@npm:3.7.4" @@ -6821,6 +6900,13 @@ __metadata: languageName: node linkType: hard +"clsx@npm:^2.0.0": + version: 2.0.0 + resolution: "clsx@npm:2.0.0" + checksum: a2cfb2351b254611acf92faa0daf15220f4cd648bdf96ce369d729813b85336993871a4bf6978ddea2b81b5a130478339c20d9d0b5c6fc287e5147f0c059276e + languageName: node + linkType: hard + "co@npm:^4.6.0": version: 4.6.0 resolution: "co@npm:4.6.0" @@ -7489,6 +7575,99 @@ __metadata: languageName: node linkType: hard +"d3-array@npm:2 - 3, d3-array@npm:2.10.0 - 3, d3-array@npm:^3.1.6": + version: 3.2.4 + resolution: "d3-array@npm:3.2.4" + dependencies: + internmap: 1 - 2 + checksum: a5976a6d6205f69208478bb44920dd7ce3e788c9dceb86b304dbe401a4bfb42ecc8b04c20facde486e9adcb488b5d1800d49393a3f81a23902b68158e12cddd0 + languageName: node + linkType: hard + +"d3-color@npm:1 - 3": + version: 3.1.0 + resolution: "d3-color@npm:3.1.0" + checksum: 4931fbfda5d7c4b5cfa283a13c91a954f86e3b69d75ce588d06cde6c3628cebfc3af2069ccf225e982e8987c612aa7948b3932163ce15eb3c11cd7c003f3ee3b + languageName: node + linkType: hard + +"d3-ease@npm:^3.0.1": + version: 3.0.1 + resolution: "d3-ease@npm:3.0.1" + checksum: 06e2ee5326d1e3545eab4e2c0f84046a123dcd3b612e68858219aa034da1160333d9ce3da20a1d3486d98cb5c2a06f7d233eee1bc19ce42d1533458bd85dedcd + languageName: node + linkType: hard + +"d3-format@npm:1 - 3": + version: 3.1.0 + resolution: "d3-format@npm:3.1.0" + checksum: f345ec3b8ad3cab19bff5dead395bd9f5590628eb97a389b1dd89f0b204c7c4fc1d9520f13231c2c7cf14b7c9a8cf10f8ef15bde2befbab41454a569bd706ca2 + languageName: node + linkType: hard + +"d3-interpolate@npm:1.2.0 - 3, d3-interpolate@npm:^3.0.1": + version: 3.0.1 + resolution: "d3-interpolate@npm:3.0.1" + dependencies: + d3-color: 1 - 3 + checksum: a42ba314e295e95e5365eff0f604834e67e4a3b3c7102458781c477bd67e9b24b6bb9d8e41ff5521050a3f2c7c0c4bbbb6e187fd586daa3980943095b267e78b + languageName: node + linkType: hard + +"d3-path@npm:^3.1.0": + version: 3.1.0 + resolution: "d3-path@npm:3.1.0" + checksum: 2306f1bd9191e1eac895ec13e3064f732a85f243d6e627d242a313f9777756838a2215ea11562f0c7630c7c3b16a19ec1fe0948b1c82f3317fac55882f6ee5d8 + languageName: node + linkType: hard + +"d3-scale@npm:^4.0.2": + version: 4.0.2 + resolution: "d3-scale@npm:4.0.2" + dependencies: + d3-array: 2.10.0 - 3 + d3-format: 1 - 3 + d3-interpolate: 1.2.0 - 3 + d3-time: 2.1.1 - 3 + d3-time-format: 2 - 4 + checksum: a9c770d283162c3bd11477c3d9d485d07f8db2071665f1a4ad23eec3e515e2cefbd369059ec677c9ac849877d1a765494e90e92051d4f21111aa56791c98729e + languageName: node + linkType: hard + +"d3-shape@npm:^3.1.0": + version: 3.2.0 + resolution: "d3-shape@npm:3.2.0" + dependencies: + d3-path: ^3.1.0 + checksum: de2af5fc9a93036a7b68581ca0bfc4aca2d5a328aa7ba7064c11aedd44d24f310c20c40157cb654359d4c15c3ef369f95ee53d71221017276e34172c7b719cfa + languageName: node + linkType: hard + +"d3-time-format@npm:2 - 4": + version: 4.1.0 + resolution: "d3-time-format@npm:4.1.0" + dependencies: + d3-time: 1 - 3 + checksum: 7342bce28355378152bbd4db4e275405439cabba082d9cd01946d40581140481c8328456d91740b0fe513c51ec4a467f4471ffa390c7e0e30ea30e9ec98fcdf4 + languageName: node + linkType: hard + +"d3-time@npm:1 - 3, d3-time@npm:2.1.1 - 3, d3-time@npm:^3.0.0": + version: 3.1.0 + resolution: "d3-time@npm:3.1.0" + dependencies: + d3-array: 2 - 3 + checksum: 613b435352a78d9f31b7f68540788186d8c331b63feca60ad21c88e9db1989fe888f97f242322ebd6365e45ec3fb206a4324cd4ca0dfffa1d9b5feb856ba00a7 + languageName: node + linkType: hard + +"d3-timer@npm:^3.0.1": + version: 3.0.1 + resolution: "d3-timer@npm:3.0.1" + checksum: 1cfddf86d7bca22f73f2c427f52dfa35c49f50d64e187eb788dcad6e927625c636aa18ae4edd44d084eb9d1f81d8ca4ec305dae7f733c15846a824575b789d73 + languageName: node + linkType: hard + "d@npm:1, d@npm:^1.0.1": version: 1.0.1 resolution: "d@npm:1.0.1" @@ -7550,6 +7729,13 @@ __metadata: languageName: node linkType: hard +"decimal.js-light@npm:^2.4.1": + version: 2.5.1 + resolution: "decimal.js-light@npm:2.5.1" + checksum: f5a2c7eac1c4541c8ab8a5c8abea64fc1761cefc7794bd5f8afd57a8a78d1b51785e0c4e4f85f4895a043eaa90ddca1edc3981d1263eb6ddce60f32bf5fe66c9 + languageName: node + linkType: hard + "decode-uri-component@npm:^0.2.0": version: 0.2.2 resolution: "decode-uri-component@npm:0.2.2" @@ -7796,6 +7982,15 @@ __metadata: languageName: node linkType: hard +"dom-helpers@npm:^3.4.0": + version: 3.4.0 + resolution: "dom-helpers@npm:3.4.0" + dependencies: + "@babel/runtime": ^7.1.2 + checksum: 58d9f1c4a96daf77eddc63ae1236b826e1cddd6db66bbf39b18d7e21896d99365b376593352d52a60969d67fa4a8dbef26adc1439fa2c1b355efa37cacbaf637 + languageName: node + linkType: hard + "dom-helpers@npm:^5.0.1, dom-helpers@npm:^5.1.3, dom-helpers@npm:^5.2.0, dom-helpers@npm:^5.2.1": version: 5.2.1 resolution: "dom-helpers@npm:5.2.1" @@ -9089,7 +9284,7 @@ __metadata: languageName: node linkType: hard -"eventemitter3@npm:^4.0.7": +"eventemitter3@npm:^4.0.1, eventemitter3@npm:^4.0.7": version: 4.0.7 resolution: "eventemitter3@npm:4.0.7" checksum: 1875311c42fcfe9c707b2712c32664a245629b42bb0a5a84439762dd0fd637fc54d078155ea83c2af9e0323c9ac13687e03cfba79b03af9f40c89b4960099374 @@ -9287,6 +9482,13 @@ __metadata: languageName: node linkType: hard +"fast-equals@npm:^5.0.0": + version: 5.0.1 + resolution: "fast-equals@npm:5.0.1" + checksum: fbb3b6a74f3a0fa930afac151ff7d01639159b4fddd2678b5d50708e0ba38e9ec14602222d10dadb8398187342692c04fbef5a62b1cfcc7942fe03e754e064bc + languageName: node + linkType: hard + "fast-glob@npm:^2.2.6": version: 2.2.7 resolution: "fast-glob@npm:2.2.7" @@ -10838,6 +11040,13 @@ __metadata: languageName: node linkType: hard +"internmap@npm:1 - 2": + version: 2.0.3 + resolution: "internmap@npm:2.0.3" + checksum: 7ca41ec6aba8f0072fc32fa8a023450a9f44503e2d8e403583c55714b25efd6390c38a87161ec456bf42d7bc83aab62eb28f5aef34876b1ac4e60693d5e1d241 + languageName: node + linkType: hard + "interpret@npm:^2.2.0": version: 2.2.0 resolution: "interpret@npm:2.2.0" @@ -14960,6 +15169,13 @@ __metadata: languageName: node linkType: hard +"react-is@npm:^16.10.2, react-is@npm:^16.13.1, react-is@npm:^16.3.2, react-is@npm:^16.7.0": + version: 16.13.1 + resolution: "react-is@npm:16.13.1" + checksum: f7a19ac3496de32ca9ae12aa030f00f14a3d45374f1ceca0af707c831b2a6098ef0d6bdae51bd437b0a306d7f01d4677fcc8de7c0d331eb47ad0f46130e53c5f + languageName: node + linkType: hard + "react-is@npm:^16.12.0 || ^17.0.0 || ^18.0.0, react-is@npm:^18.0.0, react-is@npm:^18.2.0": version: 18.2.0 resolution: "react-is@npm:18.2.0" @@ -14967,13 +15183,6 @@ __metadata: languageName: node linkType: hard -"react-is@npm:^16.13.1, react-is@npm:^16.3.2, react-is@npm:^16.7.0": - version: 16.13.1 - resolution: "react-is@npm:16.13.1" - checksum: f7a19ac3496de32ca9ae12aa030f00f14a3d45374f1ceca0af707c831b2a6098ef0d6bdae51bd437b0a306d7f01d4677fcc8de7c0d331eb47ad0f46130e53c5f - languageName: node - linkType: hard - "react-lazylog@npm:^4.5.3": version: 4.5.3 resolution: "react-lazylog@npm:4.5.3" @@ -15119,6 +15328,20 @@ __metadata: languageName: node linkType: hard +"react-smooth@npm:^2.0.5": + version: 2.0.5 + resolution: "react-smooth@npm:2.0.5" + dependencies: + fast-equals: ^5.0.0 + react-transition-group: 2.9.0 + peerDependencies: + prop-types: ^15.6.0 + react: ^15.0.0 || ^16.0.0 || ^17.0.0 || ^18.0.0 + react-dom: ^15.0.0 || ^16.0.0 || ^17.0.0 || ^18.0.0 + checksum: 914c17f741e8b533ff6e3d5e3285aea0625cdd0f98e04202d01351f9516dbdc0a0e297dc22cc2377d6916fb819da8d4ed999c0314a4c186592ca51870012e6f7 + languageName: node + linkType: hard + "react-split-pane@npm:^0.1.92": version: 0.1.92 resolution: "react-split-pane@npm:0.1.92" @@ -15179,6 +15402,21 @@ __metadata: languageName: node linkType: hard +"react-transition-group@npm:2.9.0": + version: 2.9.0 + resolution: "react-transition-group@npm:2.9.0" + dependencies: + dom-helpers: ^3.4.0 + loose-envify: ^1.4.0 + prop-types: ^15.6.2 + react-lifecycles-compat: ^3.0.4 + peerDependencies: + react: ">=15.0.0" + react-dom: ">=15.0.0" + checksum: d8c9e50aabdc2cfc324e5cdb0ad1c6eecb02e1c0cd007b26d5b30ccf49015e900683dd489348c71fba4055858308d9ba7019e0d37d0e8d37bd46ed098788f670 + languageName: node + linkType: hard + "react-transition-group@npm:^4.3.0, react-transition-group@npm:^4.4.2": version: 4.4.5 resolution: "react-transition-group@npm:4.4.5" @@ -15332,6 +15570,35 @@ __metadata: languageName: node linkType: hard +"recharts-scale@npm:^0.4.4": + version: 0.4.5 + resolution: "recharts-scale@npm:0.4.5" + dependencies: + decimal.js-light: ^2.4.1 + checksum: e970377190a610e684a32c7461c7684ac3603c2e0ac0020bbba1eea9d099b38138143a8e80bf769bb49c0b7cecf22a2f5c6854885efed2d56f4540d4aa7052bd + languageName: node + linkType: hard + +"recharts@npm:^2.10.3": + version: 2.10.3 + resolution: "recharts@npm:2.10.3" + dependencies: + clsx: ^2.0.0 + eventemitter3: ^4.0.1 + lodash: ^4.17.19 + react-is: ^16.10.2 + react-smooth: ^2.0.5 + recharts-scale: ^0.4.4 + tiny-invariant: ^1.3.1 + victory-vendor: ^36.6.8 + peerDependencies: + prop-types: ^15.6.0 + react: ^16.0.0 || ^17.0.0 || ^18.0.0 + react-dom: ^16.0.0 || ^17.0.0 || ^18.0.0 + checksum: 503c9fefa8648e0e8834a11ccc09fdcc310d391807438f4c0567b1888d7cd5f7a1f65f020afb981ec54ad6f96d31ebe757ab9025e93782edabc5c741f1aa946a + languageName: node + linkType: hard + "redent@npm:^1.0.0": version: 1.0.0 resolution: "redent@npm:1.0.0" @@ -15403,6 +15670,13 @@ __metadata: languageName: node linkType: hard +"regenerator-runtime@npm:^0.14.0": + version: 0.14.1 + resolution: "regenerator-runtime@npm:0.14.1" + checksum: 9f57c93277b5585d3c83b0cf76be47b473ae8c6d9142a46ce8b0291a04bb2cf902059f0f8445dcabb3fb7378e5fe4bb4ea1e008876343d42e46d3b484534ce38 + languageName: node + linkType: hard + "regenerator-transform@npm:^0.15.1": version: 0.15.1 resolution: "regenerator-transform@npm:0.15.1" @@ -17243,6 +17517,13 @@ __metadata: languageName: node linkType: hard +"tiny-invariant@npm:^1.3.1": + version: 1.3.1 + resolution: "tiny-invariant@npm:1.3.1" + checksum: 872dbd1ff20a21303a2fd20ce3a15602cfa7fcf9b228bd694a52e2938224313b5385a1078cb667ed7375d1612194feaca81c4ecbe93121ca1baebe344de4f84c + languageName: node + linkType: hard + "tmpl@npm:1.0.5": version: 1.0.5 resolution: "tmpl@npm:1.0.5" @@ -18131,6 +18412,28 @@ __metadata: languageName: node linkType: hard +"victory-vendor@npm:^36.6.8": + version: 36.7.0 + resolution: "victory-vendor@npm:36.7.0" + dependencies: + "@types/d3-array": ^3.0.3 + "@types/d3-ease": ^3.0.0 + "@types/d3-interpolate": ^3.0.1 + "@types/d3-scale": ^4.0.2 + "@types/d3-shape": ^3.1.0 + "@types/d3-time": ^3.0.0 + "@types/d3-timer": ^3.0.0 + d3-array: ^3.1.6 + d3-ease: ^3.0.1 + d3-interpolate: ^3.0.1 + d3-scale: ^4.0.2 + d3-shape: ^3.1.0 + d3-time: ^3.0.0 + d3-timer: ^3.0.1 + checksum: f69560f1d06ecdf87b46f9e832e9479b142b848e2485ccd922d09e162e2431eca80729a343ef690a21b7ceeba2bbf63d6be9c3cf864112d7734158d7f5978622 + languageName: node + linkType: hard + "vite-plugin-dts@npm:^0.9.9": version: 0.9.10 resolution: "vite-plugin-dts@npm:0.9.10"