diff --git a/.eslintrc b/.eslintrc index b6d9ff81..9c185f84 100644 --- a/.eslintrc +++ b/.eslintrc @@ -18,6 +18,7 @@ "airbnb-base", "airbnb/rules/react", "airbnb-typescript", + "@unocss", "prettier", ], "plugins": [ @@ -203,6 +204,7 @@ ] } ], + "import/extensions": "off", "no-restricted-syntax": [ "error", "ForInStatement", diff --git a/.storybook/preview.tsx b/.storybook/preview.tsx index 19ed3029..cf094ffc 100644 --- a/.storybook/preview.tsx +++ b/.storybook/preview.tsx @@ -1,6 +1,6 @@ -import ExtensionRoot from 'src/views/components/common/ExtensionRoot/ExtensionRoot'; import type { Preview } from '@storybook/react'; import React from 'react'; +import ExtensionRoot from 'src/views/components/common/ExtensionRoot/ExtensionRoot'; const preview: Preview = { parameters: { diff --git a/.storybook/vite-storybook.config.ts b/.storybook/vite-storybook.config.ts index ac47f942..047953c6 100644 --- a/.storybook/vite-storybook.config.ts +++ b/.storybook/vite-storybook.config.ts @@ -1,5 +1,7 @@ import react from '@vitejs/plugin-react-swc'; import { resolve } from 'path'; +import UnoCSS from 'unocss/vite'; +import Icons from 'unplugin-icons/vite'; import { defineConfig } from 'vite'; const root = resolve(__dirname, '../src'); @@ -11,16 +13,16 @@ console.log(root); // https://vitejs.dev/config/ export default defineConfig({ - plugins: [react()], - resolve: { - alias: { - src: root, - '@assets': assetsDir, - '@pages': pagesDir, - '@public': publicDir, - '@shared': resolve(root, 'shared'), - '@background': resolve(pagesDir, 'background'), - '@views': resolve(root, 'views'), + plugins: [react(), UnoCSS(), Icons({ compiler: 'jsx', jsx: 'react' })], + resolve: { + alias: { + src: root, + '@assets': assetsDir, + '@pages': pagesDir, + '@public': publicDir, + '@shared': resolve(root, 'shared'), + '@background': resolve(pagesDir, 'background'), + '@views': resolve(root, 'views'), + }, }, - }, }); diff --git a/package.json b/package.json index 2963a66b..e8515d4e 100644 --- a/package.json +++ b/package.json @@ -32,7 +32,7 @@ }, "devDependencies": { "@crxjs/vite-plugin": "2.0.0-beta.21", - "@iconify-json/ic": "^1.1.17", + "@iconify-json/material-symbols": "^1.1.72", "@storybook/addon-designs": "^7.0.9", "@storybook/addon-essentials": "^7.6.12", "@storybook/addon-links": "^7.6.12", @@ -40,6 +40,8 @@ "@storybook/react": "^7.6.12", "@storybook/react-vite": "^7.6.12", "@storybook/test": "^7.6.12", + "@svgr/core": "^8.1.0", + "@svgr/plugin-jsx": "^8.1.0", "@types/chrome": "^0.0.260", "@types/node": "^20.11.16", "@types/prompts": "^2.4.9", @@ -49,6 +51,12 @@ "@types/uuid": "^9.0.8", "@typescript-eslint/eslint-plugin": "^6.20.0", "@typescript-eslint/parser": "^6.20.0", + "@unocss/eslint-config": "^0.58.4", + "@unocss/postcss": "^0.58.4", + "@unocss/preset-uno": "^0.58.4", + "@unocss/preset-web-fonts": "^0.58.4", + "@unocss/transformer-directives": "^0.58.4", + "@unocss/transformer-variant-group": "^0.58.4", "@vitejs/plugin-react-swc": "^3.6.0", "cssnano": "^6.0.3", "cssnano-preset-advanced": "^6.0.3", @@ -75,6 +83,7 @@ "react-devtools": "^5.0.0", "storybook": "^7.6.12", "typescript": "^5.3.3", + "unocss": "^0.58.4", "unplugin-icons": "^0.18.3", "vite": "^5.0.12", "vite-plugin-inspect": "^0.8.3" diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 686b23b0..4310cf74 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -54,9 +54,9 @@ devDependencies: '@crxjs/vite-plugin': specifier: 2.0.0-beta.21 version: 2.0.0-beta.21(patch_hash=xq4uab3o3kbvv4gixvawl2aj5q) - '@iconify-json/ic': - specifier: ^1.1.17 - version: 1.1.17 + '@iconify-json/material-symbols': + specifier: ^1.1.72 + version: 1.1.72 '@storybook/addon-designs': specifier: ^7.0.9 version: 7.0.9(@storybook/addon-docs@7.6.12)(@storybook/addons@7.6.11)(@storybook/components@7.6.12)(@storybook/manager-api@7.6.12)(@storybook/preview-api@7.6.12)(@storybook/theming@7.6.12)(react-dom@18.2.0)(react@18.2.0) @@ -78,6 +78,12 @@ devDependencies: '@storybook/test': specifier: ^7.6.12 version: 7.6.12 + '@svgr/core': + specifier: ^8.1.0 + version: 8.1.0(typescript@5.3.3) + '@svgr/plugin-jsx': + specifier: ^8.1.0 + version: 8.1.0(@svgr/core@8.1.0) '@types/chrome': specifier: ^0.0.260 version: 0.0.260 @@ -105,6 +111,24 @@ devDependencies: '@typescript-eslint/parser': specifier: ^6.20.0 version: 6.20.0(eslint@8.56.0)(typescript@5.3.3) + '@unocss/eslint-config': + specifier: ^0.58.4 + version: 0.58.4(eslint@8.56.0)(typescript@5.3.3) + '@unocss/postcss': + specifier: ^0.58.4 + version: 0.58.4(postcss@8.4.33) + '@unocss/preset-uno': + specifier: ^0.58.4 + version: 0.58.4 + '@unocss/preset-web-fonts': + specifier: ^0.58.4 + version: 0.58.4 + '@unocss/transformer-directives': + specifier: ^0.58.4 + version: 0.58.4 + '@unocss/transformer-variant-group': + specifier: ^0.58.4 + version: 0.58.4 '@vitejs/plugin-react-swc': specifier: ^3.6.0 version: 3.6.0(vite@5.0.12) @@ -183,9 +207,12 @@ devDependencies: typescript: specifier: ^5.3.3 version: 5.3.3 + unocss: + specifier: ^0.58.4 + version: 0.58.4(postcss@8.4.33)(vite@5.0.12) unplugin-icons: specifier: ^0.18.3 - version: 0.18.3 + version: 0.18.3(@svgr/core@8.1.0) vite: specifier: ^5.0.12 version: 5.0.12(@types/node@20.11.16)(sass@1.70.0) @@ -209,7 +236,7 @@ packages: engines: {node: '>=6.0.0'} dependencies: '@jridgewell/gen-mapping': 0.3.3 - '@jridgewell/trace-mapping': 0.3.19 + '@jridgewell/trace-mapping': 0.3.22 /@antfu/install-pkg@0.1.1: resolution: {integrity: sha512-LyB/8+bSfa0DFGC06zpCEfs89/XoWZwws5ygEa5D+Xsm3OfI+aXQ86VgVG7Acyef+rSZ5HE7J8rrxzrQeM3PjQ==} @@ -328,7 +355,7 @@ packages: dependencies: '@babel/compat-data': 7.23.5 '@babel/helper-validator-option': 7.23.5 - browserslist: 4.22.2 + browserslist: 4.22.3 lru-cache: 5.1.1 semver: 6.3.1 @@ -2190,8 +2217,8 @@ packages: resolution: {integrity: sha512-dvuCeX5fC9dXgJn9t+X5atfmgQAzUOWqS1254Gh0m6i8wKd10ebXkfNKiRK+1GWi/yTvvLDHpoxLr0xxxeslWw==} dev: true - /@iconify-json/ic@1.1.17: - resolution: {integrity: sha512-EvAjZzVESmN36zlyefylePUNaU2BQ3eRKVZ6KQSQ2bG01ppoZaiFZRri74VTyvp5Mlv2yn68ux1fgCoT+etGmA==} + /@iconify-json/material-symbols@1.1.72: + resolution: {integrity: sha512-5IRqdI4HSbdatHBn6NZG+O9M1pJA39IrUhoBD824dXkKKE/3OmS2aU16w1hAhnr7n/euBqclkXAeUG3rDs0l1A==} dependencies: '@iconify/types': 2.0.0 dev: true @@ -2340,7 +2367,6 @@ packages: dependencies: '@jridgewell/resolve-uri': 3.1.1 '@jridgewell/sourcemap-codec': 1.4.15 - dev: true /@juggle/resize-observer@3.4.0: resolution: {integrity: sha512-dfLbk+PwWvFzSxwk3n5ySL0hfBog779o8h68wK/7/APo/7cgyWp5jcXockbxdk5kFRkbeXWm4Fbi9FrdN381sA==} @@ -2406,6 +2432,11 @@ packages: dev: true optional: true + /@pkgr/core@0.1.1: + resolution: {integrity: sha512-cq8o4cWH0ibXh9VGi5P20Tu9XF/0fFXl9EUinr9QfTM7a7p0oTA4iJRCQWppXR1Pg8dSM0UCItCkPwsk9qWWYA==} + engines: {node: ^12.20.0 || ^14.18.0 || >=16.0.0} + dev: true + /@pkgr/utils@2.4.2: resolution: {integrity: sha512-POgTXhjrTfbTV63DiFXav4lBHiICLKKwDeaKn9Nphwj7WH6m0hMMCaJkMyRWjgtPFyRKRVoMXXjczsTQRDEhYw==} engines: {node: ^12.20.0 || ^14.18.0 || >=16.0.0} @@ -3966,6 +3997,132 @@ packages: file-system-cache: 2.3.0 dev: true + /@svgr/babel-plugin-add-jsx-attribute@8.0.0(@babel/core@7.23.9): + resolution: {integrity: sha512-b9MIk7yhdS1pMCZM8VeNfUlSKVRhsHZNMl5O9SfaX0l0t5wjdgu4IDzGB8bpnGBBOjGST3rRFVsaaEtI4W6f7g==} + engines: {node: '>=14'} + peerDependencies: + '@babel/core': ^7.0.0-0 + dependencies: + '@babel/core': 7.23.9 + dev: true + + /@svgr/babel-plugin-remove-jsx-attribute@8.0.0(@babel/core@7.23.9): + resolution: {integrity: sha512-BcCkm/STipKvbCl6b7QFrMh/vx00vIP63k2eM66MfHJzPr6O2U0jYEViXkHJWqXqQYjdeA9cuCl5KWmlwjDvbA==} + engines: {node: '>=14'} + peerDependencies: + '@babel/core': ^7.0.0-0 + dependencies: + '@babel/core': 7.23.9 + dev: true + + /@svgr/babel-plugin-remove-jsx-empty-expression@8.0.0(@babel/core@7.23.9): + resolution: {integrity: sha512-5BcGCBfBxB5+XSDSWnhTThfI9jcO5f0Ai2V24gZpG+wXF14BzwxxdDb4g6trdOux0rhibGs385BeFMSmxtS3uA==} + engines: {node: '>=14'} + peerDependencies: + '@babel/core': ^7.0.0-0 + dependencies: + '@babel/core': 7.23.9 + dev: true + + /@svgr/babel-plugin-replace-jsx-attribute-value@8.0.0(@babel/core@7.23.9): + resolution: {integrity: sha512-KVQ+PtIjb1BuYT3ht8M5KbzWBhdAjjUPdlMtpuw/VjT8coTrItWX6Qafl9+ji831JaJcu6PJNKCV0bp01lBNzQ==} + engines: {node: '>=14'} + peerDependencies: + '@babel/core': ^7.0.0-0 + dependencies: + '@babel/core': 7.23.9 + dev: true + + /@svgr/babel-plugin-svg-dynamic-title@8.0.0(@babel/core@7.23.9): + resolution: {integrity: sha512-omNiKqwjNmOQJ2v6ge4SErBbkooV2aAWwaPFs2vUY7p7GhVkzRkJ00kILXQvRhA6miHnNpXv7MRnnSjdRjK8og==} + engines: {node: '>=14'} + peerDependencies: + '@babel/core': ^7.0.0-0 + dependencies: + '@babel/core': 7.23.9 + dev: true + + /@svgr/babel-plugin-svg-em-dimensions@8.0.0(@babel/core@7.23.9): + resolution: {integrity: sha512-mURHYnu6Iw3UBTbhGwE/vsngtCIbHE43xCRK7kCw4t01xyGqb2Pd+WXekRRoFOBIY29ZoOhUCTEweDMdrjfi9g==} + engines: {node: '>=14'} + peerDependencies: + '@babel/core': ^7.0.0-0 + dependencies: + '@babel/core': 7.23.9 + dev: true + + /@svgr/babel-plugin-transform-react-native-svg@8.1.0(@babel/core@7.23.9): + resolution: {integrity: sha512-Tx8T58CHo+7nwJ+EhUwx3LfdNSG9R2OKfaIXXs5soiy5HtgoAEkDay9LIimLOcG8dJQH1wPZp/cnAv6S9CrR1Q==} + engines: {node: '>=14'} + peerDependencies: + '@babel/core': ^7.0.0-0 + dependencies: + '@babel/core': 7.23.9 + dev: true + + /@svgr/babel-plugin-transform-svg-component@8.0.0(@babel/core@7.23.9): + resolution: {integrity: sha512-DFx8xa3cZXTdb/k3kfPeaixecQLgKh5NVBMwD0AQxOzcZawK4oo1Jh9LbrcACUivsCA7TLG8eeWgrDXjTMhRmw==} + engines: {node: '>=12'} + peerDependencies: + '@babel/core': ^7.0.0-0 + dependencies: + '@babel/core': 7.23.9 + dev: true + + /@svgr/babel-preset@8.1.0(@babel/core@7.23.9): + resolution: {integrity: sha512-7EYDbHE7MxHpv4sxvnVPngw5fuR6pw79SkcrILHJ/iMpuKySNCl5W1qcwPEpU+LgyRXOaAFgH0KhwD18wwg6ug==} + engines: {node: '>=14'} + peerDependencies: + '@babel/core': ^7.0.0-0 + dependencies: + '@babel/core': 7.23.9 + '@svgr/babel-plugin-add-jsx-attribute': 8.0.0(@babel/core@7.23.9) + '@svgr/babel-plugin-remove-jsx-attribute': 8.0.0(@babel/core@7.23.9) + '@svgr/babel-plugin-remove-jsx-empty-expression': 8.0.0(@babel/core@7.23.9) + '@svgr/babel-plugin-replace-jsx-attribute-value': 8.0.0(@babel/core@7.23.9) + '@svgr/babel-plugin-svg-dynamic-title': 8.0.0(@babel/core@7.23.9) + '@svgr/babel-plugin-svg-em-dimensions': 8.0.0(@babel/core@7.23.9) + '@svgr/babel-plugin-transform-react-native-svg': 8.1.0(@babel/core@7.23.9) + '@svgr/babel-plugin-transform-svg-component': 8.0.0(@babel/core@7.23.9) + dev: true + + /@svgr/core@8.1.0(typescript@5.3.3): + resolution: {integrity: sha512-8QqtOQT5ACVlmsvKOJNEaWmRPmcojMOzCz4Hs2BGG/toAp/K38LcsMRyLp349glq5AzJbCEeimEoxaX6v/fLrA==} + engines: {node: '>=14'} + dependencies: + '@babel/core': 7.23.9 + '@svgr/babel-preset': 8.1.0(@babel/core@7.23.9) + camelcase: 6.3.0 + cosmiconfig: 8.3.6(typescript@5.3.3) + snake-case: 3.0.4 + transitivePeerDependencies: + - supports-color + - typescript + dev: true + + /@svgr/hast-util-to-babel-ast@8.0.0: + resolution: {integrity: sha512-EbDKwO9GpfWP4jN9sGdYwPBU0kdomaPIL2Eu4YwmgP+sJeXT+L7bMwJUBnhzfH8Q2qMBqZ4fJwpCyYsAN3mt2Q==} + engines: {node: '>=14'} + dependencies: + '@babel/types': 7.23.9 + entities: 4.5.0 + dev: true + + /@svgr/plugin-jsx@8.1.0(@svgr/core@8.1.0): + resolution: {integrity: sha512-0xiIyBsLlr8quN+WyuxooNW9RJ0Dpr8uOnH/xrCVO8GLUcwHISwj1AG0k+LFzteTkAA0GbX0kj9q6Dk70PTiPA==} + engines: {node: '>=14'} + peerDependencies: + '@svgr/core': '*' + dependencies: + '@babel/core': 7.23.9 + '@svgr/babel-preset': 8.1.0(@babel/core@7.23.9) + '@svgr/core': 8.1.0(typescript@5.3.3) + '@svgr/hast-util-to-babel-ast': 8.0.0 + svg-parser: 2.0.4 + transitivePeerDependencies: + - supports-color + dev: true + /@swc/core-darwin-arm64@1.3.107: resolution: {integrity: sha512-47tD/5vSXWxPd0j/ZllyQUg4bqalbQTsmqSw0J4dDdS82MWqCAwUErUrAZPRjBkjNQ6Kmrf5rpCWaGTtPw+ngw==} engines: {node: '>=10'} @@ -4718,6 +4875,246 @@ packages: resolution: {integrity: sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==} dev: true + /@unocss/astro@0.58.4(vite@5.0.12): + resolution: {integrity: sha512-feS8+f3oPmCeR1XF7isQjs3Z9ojM5Ssv0vCNR/dexPFdROfccK/7sIu1YnHWtVg1trPc1kMfI8XJRqfrHMdd5w==} + peerDependencies: + vite: ^2.9.0 || ^3.0.0-0 || ^4.0.0 || ^5.0.0-0 + peerDependenciesMeta: + vite: + optional: true + dependencies: + '@unocss/core': 0.58.4 + '@unocss/reset': 0.58.4 + '@unocss/vite': 0.58.4(vite@5.0.12) + vite: 5.0.12(@types/node@20.11.16)(sass@1.70.0) + transitivePeerDependencies: + - rollup + dev: true + + /@unocss/cli@0.58.4: + resolution: {integrity: sha512-8dAs1TzzWCtb3FxoTsVtR2+JGkdmchuP0RvGlSywADf5FqYn9nbP0m3z4STtpPavHO9JaGbabStyjS0nA8Ck6w==} + engines: {node: '>=14'} + hasBin: true + dependencies: + '@ampproject/remapping': 2.2.1 + '@rollup/pluginutils': 5.1.0 + '@unocss/config': 0.58.4 + '@unocss/core': 0.58.4 + '@unocss/preset-uno': 0.58.4 + cac: 6.7.14 + chokidar: 3.5.3 + colorette: 2.0.20 + consola: 3.2.3 + fast-glob: 3.3.2 + magic-string: 0.30.5 + pathe: 1.1.2 + perfect-debounce: 1.0.0 + transitivePeerDependencies: + - rollup + dev: true + + /@unocss/config@0.58.4: + resolution: {integrity: sha512-b/inDCOnhUPzobhj+SxRI7xeSwoAQU+3D3J5JoWZNPBI4OaJdwpuz40uLXl9VsPz5N6dc8/qa+FrSsgCjUcLTg==} + engines: {node: '>=14'} + dependencies: + '@unocss/core': 0.58.4 + unconfig: 0.3.11 + dev: true + + /@unocss/core@0.58.4: + resolution: {integrity: sha512-wh4pxXUCkhC+C/0ct74PMYeZgX+oWuHj2mnvr09nM0WmvOm1HeeISrDCCBGcxmKbErUk+D1v3JgzXF7b6j2l4g==} + dev: true + + /@unocss/eslint-config@0.58.4(eslint@8.56.0)(typescript@5.3.3): + resolution: {integrity: sha512-NJ0NJmEJBKSmglFKOJvEXdlj5ERgiQLKBZtsSiTUmuKk8srLkSUZv5QJ4iQl/uygxRY8ugNUyiEOfQs6a1iTUw==} + engines: {node: '>=14'} + dependencies: + '@unocss/eslint-plugin': 0.58.4(eslint@8.56.0)(typescript@5.3.3) + transitivePeerDependencies: + - eslint + - supports-color + - typescript + dev: true + + /@unocss/eslint-plugin@0.58.4(eslint@8.56.0)(typescript@5.3.3): + resolution: {integrity: sha512-wWXqs4+MbgqVgkpSqenO9QRxxixL7dA3U/tVgz6q7CwhmKc0fczEpYd04TUR2oLYhl9fnj15UcYNGdG+GCNt0Q==} + engines: {node: '>=14'} + dependencies: + '@typescript-eslint/utils': 6.20.0(eslint@8.56.0)(typescript@5.3.3) + '@unocss/config': 0.58.4 + '@unocss/core': 0.58.4 + magic-string: 0.30.5 + synckit: 0.9.0 + transitivePeerDependencies: + - eslint + - supports-color + - typescript + dev: true + + /@unocss/extractor-arbitrary-variants@0.58.4: + resolution: {integrity: sha512-TQlVtSQk8YdBU9KuTA5k6JBJ8d/aPrIsCWjDPfBvAqDvrll/dzwBCLoLTQMdCHFjCXCOYWKPum1ET+Wn9R+XbA==} + dependencies: + '@unocss/core': 0.58.4 + dev: true + + /@unocss/inspector@0.58.4: + resolution: {integrity: sha512-BbsaIMqP6dqa3qCfkC0nkvjCg11JRigvFPU4319imTPcTHQNQSg35t2mVFPGZ+QYHlU/3ouBeogUQfJDHBmtVQ==} + dependencies: + '@unocss/core': 0.58.4 + '@unocss/rule-utils': 0.58.4 + gzip-size: 6.0.0 + sirv: 2.0.4 + dev: true + + /@unocss/postcss@0.58.4(postcss@8.4.33): + resolution: {integrity: sha512-pg2qCGakV1TyMApPdvuvqqmPDhgogPWF14J97BT5zIfGYITAJSmBsm7d3+06w6EuqIS+vcYRw+qCV3oX6qTeiA==} + engines: {node: '>=14'} + peerDependencies: + postcss: ^8.4.21 + dependencies: + '@unocss/config': 0.58.4 + '@unocss/core': 0.58.4 + '@unocss/rule-utils': 0.58.4 + css-tree: 2.3.1 + fast-glob: 3.3.2 + magic-string: 0.30.5 + postcss: 8.4.33 + dev: true + + /@unocss/preset-attributify@0.58.4: + resolution: {integrity: sha512-r7pDXgcOgGMmrMoqM4/w20KKn4PxF+/vpElatAGXW3V/tHJWFOLGzk+wYeCMgMxeC+vPzqyJkjTfoqYlZrlokQ==} + dependencies: + '@unocss/core': 0.58.4 + dev: true + + /@unocss/preset-icons@0.58.4: + resolution: {integrity: sha512-xdOe3PLfEWS4y+rA7Gxh/kDI82VkW0PbdoYO2FBwXH7a0JegdUDD5zuOTsTKAIymvQ7eVH53WXN9mcuhfNmdvQ==} + dependencies: + '@iconify/utils': 2.1.20 + '@unocss/core': 0.58.4 + ofetch: 1.3.3 + transitivePeerDependencies: + - supports-color + dev: true + + /@unocss/preset-mini@0.58.4: + resolution: {integrity: sha512-cpIWUYxLi4VCkkjxpNJOVqH9D32NX1ebRFaoAVnvCRsoj5TRsZJSdxs0WMN7reHT/CUHh0Wh6d3TfMCFxzbZ4g==} + dependencies: + '@unocss/core': 0.58.4 + '@unocss/extractor-arbitrary-variants': 0.58.4 + '@unocss/rule-utils': 0.58.4 + dev: true + + /@unocss/preset-tagify@0.58.4: + resolution: {integrity: sha512-1E3vQvg5Qy4tbgovvrV0JaIXFfcdhK4NCSz+MuUk5ZYgKGVDh4IEw0WPuic534nlLm9+YFqyCSLLyIs3bT/GYQ==} + dependencies: + '@unocss/core': 0.58.4 + dev: true + + /@unocss/preset-typography@0.58.4: + resolution: {integrity: sha512-0Opt3Y0At4F03092iwGgz7HswRC2ElBXHR+IO9wWxSbldtpdmKzFJ/GBHEalzQjacWnyyzmRjabjA2quoQ8FQA==} + dependencies: + '@unocss/core': 0.58.4 + '@unocss/preset-mini': 0.58.4 + dev: true + + /@unocss/preset-uno@0.58.4: + resolution: {integrity: sha512-FWBPGIt0UcQHu58l75kvhB4vF2v+s2m0OW9DnIrPm3aY7Qj3q4yA2wdahR37qSsH+6vR3JP4+mV9WBrGjIsjrQ==} + dependencies: + '@unocss/core': 0.58.4 + '@unocss/preset-mini': 0.58.4 + '@unocss/preset-wind': 0.58.4 + '@unocss/rule-utils': 0.58.4 + dev: true + + /@unocss/preset-web-fonts@0.58.4: + resolution: {integrity: sha512-vcy20fIK37GdhesRpiWGvCvkJDQsSiRF1jxw3dy8J5n9kFpIV8DQoPWUIE0ePF4i5ky2dHSDxKaNOP1bxHdKGA==} + dependencies: + '@unocss/core': 0.58.4 + ofetch: 1.3.3 + dev: true + + /@unocss/preset-wind@0.58.4: + resolution: {integrity: sha512-e2F0HsqPXw+nD85MKIZ63mx5yUx5g8iPOtMw9/eEUeK67HrD+jFxeLq0hAM3ou3a4589QIzeg23LXAkM7gCzvg==} + dependencies: + '@unocss/core': 0.58.4 + '@unocss/preset-mini': 0.58.4 + '@unocss/rule-utils': 0.58.4 + dev: true + + /@unocss/reset@0.58.4: + resolution: {integrity: sha512-ZZTrAdl4WWmMjQdOqcOSWdgFH6kdFKZjPu4c6Ijxk7KvY2BW3nttTTBa7IYeuXFHVfcExUFqlOgRurt+NeWYyQ==} + dev: true + + /@unocss/rule-utils@0.58.4: + resolution: {integrity: sha512-52Jp4I+joGTaDm7ehB/7uZ2kJL+9BZcYRDUVk4IDacDH5W9yxf1F75LzYT8jJVWXD/HIhiS0r9V6qhcBq2OWZw==} + engines: {node: '>=14'} + dependencies: + '@unocss/core': 0.58.4 + magic-string: 0.30.5 + dev: true + + /@unocss/scope@0.58.4: + resolution: {integrity: sha512-JrX98xoYnv0HN41WyzlvCCU1T3jnDOry+V8mm2dB9DvByzxI484X6gtKbOXlJFAPwOlZPU5Bru/XTDaL6yQQww==} + dev: true + + /@unocss/transformer-attributify-jsx-babel@0.58.4: + resolution: {integrity: sha512-yJd+OxAdgAxSQHVrqC6z19ibPqwwWO7J0TFf2caiP3hidSJ0iOvxcC0h62YCMr9dg4MsCpXaiHmGzxXbWGJ9nQ==} + dependencies: + '@babel/core': 7.23.9 + '@babel/plugin-syntax-jsx': 7.23.3(@babel/core@7.23.9) + '@babel/preset-typescript': 7.23.3(@babel/core@7.23.9) + '@unocss/core': 0.58.4 + transitivePeerDependencies: + - supports-color + dev: true + + /@unocss/transformer-attributify-jsx@0.58.4: + resolution: {integrity: sha512-Y4YMVkgY/EF7x0llV8Y42WGs8b77hbXkPstRLNeRD5x8KBNKnjYUXADwhTBEKXjDR8/y5Ewie8u43i1nbh1XuA==} + dependencies: + '@unocss/core': 0.58.4 + dev: true + + /@unocss/transformer-compile-class@0.58.4: + resolution: {integrity: sha512-GPz462ogvtb64W0iweuB0Dcm1snGsGte0RlVpFUeG2eWlVqKMRvNRtYuive2Ky2zSZKefWJQBGk3Ti+7CM4wFA==} + dependencies: + '@unocss/core': 0.58.4 + dev: true + + /@unocss/transformer-directives@0.58.4: + resolution: {integrity: sha512-5g2XVhwpmu2IrGHqPwxh+S3ZtkC/AwAtLIBLWB1QNhY3HVzAAaOzcif6uarngrCTTDQSDmsjzm8TSAq26LtCmQ==} + dependencies: + '@unocss/core': 0.58.4 + '@unocss/rule-utils': 0.58.4 + css-tree: 2.3.1 + dev: true + + /@unocss/transformer-variant-group@0.58.4: + resolution: {integrity: sha512-zpJ4TMor7aJ3SoLJm4jNBOSqikyXUdQEO1AxkILd9Zcn7JWRgudfFXiXnFP+WGJcs9mMLoUiISxzT8SKNCckfA==} + dependencies: + '@unocss/core': 0.58.4 + dev: true + + /@unocss/vite@0.58.4(vite@5.0.12): + resolution: {integrity: sha512-TqD5fIXv6NF3v10FFrCII//GRbkou6Dn/OzW+d4T5f0KM5+T6DutljpYUdGo0+2QXKDroUWLAspFUaZUx8iwVw==} + peerDependencies: + vite: ^2.9.0 || ^3.0.0-0 || ^4.0.0 || ^5.0.0-0 + dependencies: + '@ampproject/remapping': 2.2.1 + '@rollup/pluginutils': 5.1.0 + '@unocss/config': 0.58.4 + '@unocss/core': 0.58.4 + '@unocss/inspector': 0.58.4 + '@unocss/scope': 0.58.4 + '@unocss/transformer-directives': 0.58.4 + chokidar: 3.5.3 + fast-glob: 3.3.2 + magic-string: 0.30.5 + vite: 5.0.12(@types/node@20.11.16)(sass@1.70.0) + transitivePeerDependencies: + - rollup + dev: true + /@vitejs/plugin-react-swc@3.6.0(vite@5.0.12): resolution: {integrity: sha512-XFRbsGgpGxGzEV5i5+vRiro1bwcIaZDIdBRP16qwm+jP68ue/S8FJTBEgOeojtVDYrbSua3XFp71kC8VJE6v+g==} peerDependencies: @@ -5451,16 +5848,6 @@ packages: update-browserslist-db: 1.0.11(browserslist@4.21.9) dev: true - /browserslist@4.22.2: - resolution: {integrity: sha512-0UgcrvQmBDvZHFGdYUehrCNIazki7/lUP3kkoi/r3YB2amZbFM9J43ZRkJTXBUZK4gmx56+Sqk9+Vs9mwZx9+A==} - engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} - hasBin: true - dependencies: - caniuse-lite: 1.0.30001571 - electron-to-chromium: 1.4.616 - node-releases: 2.0.14 - update-browserslist-db: 1.0.13(browserslist@4.22.2) - /browserslist@4.22.3: resolution: {integrity: sha512-UAp55yfwNv0klWNapjs/ktHoguxuQNGnOzxYmfnXIS+8AsRDZkSDxg7R1AX3GKzn078SBI5dzwzj/Yx0Or0e3A==} engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} @@ -5470,7 +5857,6 @@ packages: electron-to-chromium: 1.4.650 node-releases: 2.0.14 update-browserslist-db: 1.0.13(browserslist@4.22.3) - dev: true /bser@2.1.1: resolution: {integrity: sha512-gQxTNE/GAfIIrmHLUE3oJyp5FO6HRBfhjnw4/wMmA63ZGDJnWBmgY/lyQBpnDUkGmAhbSe39tx2d/iTOAfglwQ==} @@ -5522,6 +5908,11 @@ packages: engines: {node: '>= 0.8'} dev: true + /cac@6.7.14: + resolution: {integrity: sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==} + engines: {node: '>=8'} + dev: true + /cacheable-lookup@5.0.4: resolution: {integrity: sha512-2/kNscPhpcxrOigMZzbiWF7dz8ilhb/nIHU3EyZiXWXpeq/au8qJ8VhdftMkty3n7Gj6HIGalQG8oiBNB3AJgA==} engines: {node: '>=10.6.0'} @@ -5570,6 +5961,11 @@ packages: engines: {node: '>=6'} dev: true + /camelcase@6.3.0: + resolution: {integrity: sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==} + engines: {node: '>=10'} + dev: true + /caniuse-api@3.0.0: resolution: {integrity: sha512-bsTwuIg/BZZK/vreVTYYbSWoe2F+71P7K5QGEX+pT250DZbfU1MQ5prOKpPR+LL6uWKK3KMwMCAS74QB3Um1uw==} dependencies: @@ -5583,12 +5979,8 @@ packages: resolution: {integrity: sha512-SFpUDoSLCaE5XYL2jfqe9ova/pbQHEmbheDf5r4diNwbAgR3qxM9NQtfsiSscjqoya5K7kFcHPUQ+VsUkIJR4A==} dev: true - /caniuse-lite@1.0.30001571: - resolution: {integrity: sha512-tYq/6MoXhdezDLFZuCO/TKboTzuQ/xR5cFdgXPfDtM7/kchBO3b4VWghE/OAi/DV7tTdhmLjZiZBZi1fA/GheQ==} - /caniuse-lite@1.0.30001581: resolution: {integrity: sha512-whlTkwhqV2tUmP3oYhtNfaWGYHDdS3JYFQBKXxcUR9qqPWsRhFHhoISO2Xnl/g0xyKzht9mI1LZpiNWfMzHixQ==} - dev: true /capture-stack-trace@1.0.2: resolution: {integrity: sha512-X/WM2UQs6VMHUtjUDnZTRI+i1crWteJySFzr9UpGoQa4WQffXVTTXuekjl7TjZRlcF2XfjgITT0HxZ9RnxeT0w==} @@ -5790,6 +6182,10 @@ packages: resolution: {integrity: sha512-jeC1axXpnb0/2nn/Y1LPuLdgXBLH7aDcHu4KEKfqw3CUhX7ZpfBSlPKyqXE6btIgEzfWtrX3/tyBCaCvXvMkOw==} dev: true + /colorette@2.0.20: + resolution: {integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==} + dev: true + /combined-stream@1.0.8: resolution: {integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==} engines: {node: '>= 0.8'} @@ -5938,6 +6334,22 @@ packages: yaml: 1.10.2 dev: true + /cosmiconfig@8.3.6(typescript@5.3.3): + resolution: {integrity: sha512-kcZ6+W5QzcJ3P1Mt+83OUv/oHFqZHIx8DuxG6eZ5RGMERoLqp4BuGjhHLYGK+Kf5XVkQvqBSmAy/nGWN3qDgEA==} + engines: {node: '>=14'} + peerDependencies: + typescript: '>=4.9.5' + peerDependenciesMeta: + typescript: + optional: true + dependencies: + import-fresh: 3.3.0 + js-yaml: 4.1.0 + parse-json: 5.2.0 + path-type: 4.0.0 + typescript: 5.3.3 + dev: true + /create-error-class@3.0.2: resolution: {integrity: sha512-gYTKKexFO3kh200H1Nit76sRwRtOY32vQd3jpAQKpLtZqyNsSQNfI4N7o3eP2wUjV35pTWKRYqFUDBvUha/Pkw==} engines: {node: '>=0.10.0'} @@ -6306,6 +6718,10 @@ packages: engines: {node: '>=6'} dev: true + /destr@2.0.2: + resolution: {integrity: sha512-65AlobnZMiCET00KaFFjUefxDX0khFA/E4myqZ7a6Sq1yZtR8+FVIvilVX66vF2uobSumxooYZChiRPCKNqhmg==} + dev: true + /destroy@1.2.0: resolution: {integrity: sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==} engines: {node: '>= 0.8', npm: 1.2.8000 || >= 1.4.16} @@ -6415,6 +6831,13 @@ packages: domhandler: 5.0.3 dev: true + /dot-case@3.0.4: + resolution: {integrity: sha512-Kv5nKlh6yRrdrGvxeJ2e5y2eRUpkUosIW4A2AS38zwSz27zu7ufDwQPi5Jhs3XAlGNetl3bmnGhQsMtkKJnj3w==} + dependencies: + no-case: 3.0.4 + tslib: 2.6.2 + dev: true + /dot-prop@4.2.1: resolution: {integrity: sha512-l0p4+mIuJIua0mhxGoh4a+iNL9bmeK5DvnSVQa6T0OhrVmaEa1XScX5Etc673FePCJOArq/4Pa2cLGODUWTPOQ==} engines: {node: '>=4'} @@ -6469,12 +6892,8 @@ packages: resolution: {integrity: sha512-r6dCgNpRhPwiWlxbHzZQ/d9swfPaEJGi8ekqRBwQYaR3WmA5VkqQfBWSDDjuJU1ntO+W9tHx8OHV/96Q8e0dVw==} dev: true - /electron-to-chromium@1.4.616: - resolution: {integrity: sha512-1n7zWYh8eS0L9Uy+GskE0lkBUNK83cXTVJI0pU3mGprFsbfSdAc15VTFbo+A+Bq4pwstmL30AVcEU3Fo463lNg==} - /electron-to-chromium@1.4.650: resolution: {integrity: sha512-sYSQhJCJa4aGA1wYol5cMQgekDBlbVfTRavlGZVr3WZpDdOPcp6a6xUnFfrt8TqZhsBYYbDxJZCjGfHuGupCRQ==} - dev: true /electron@23.3.8: resolution: {integrity: sha512-mxhKme3fUShiwOQR1HK8s/JXoiBfqq/jVZaEoWB4etFEiGTdRClXNo+y82eyY2zCOHFM0gVncZ7kdXiVtwvkzQ==} @@ -8687,6 +9106,11 @@ packages: supports-color: 8.1.1 dev: true + /jiti@1.21.0: + resolution: {integrity: sha512-gFqAIbuKyyso/3G2qhiO2OM6shY6EPP/R0+mkDbyspxKazh8BXDC5FiFsUjlczgdNz/vfra0da2y+aHrusLG/Q==} + hasBin: true + dev: true + /js-tokens@4.0.0: resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} @@ -8993,6 +9417,12 @@ packages: get-func-name: 2.0.2 dev: true + /lower-case@2.0.2: + resolution: {integrity: sha512-7fm3l3NAF9WfN6W3JOmf5drwpVqX78JtoGJ3A6W0a6ZnldM41w2fV5D490psKFTpMds8TJse/eHLFFsNHHjHgg==} + dependencies: + tslib: 2.6.2 + dev: true + /lowercase-keys@1.0.1: resolution: {integrity: sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==} engines: {node: '>=0.10.0'} @@ -9323,6 +9753,13 @@ packages: resolution: {integrity: sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==} dev: true + /no-case@3.0.4: + resolution: {integrity: sha512-fgAN3jGAh+RoxUGZHTSOLJIqUc2wmoBwGR4tbpNAKmmovFoWq0OdRkb0VkldReO2a2iBT/OEulG9XSUc10r3zg==} + dependencies: + lower-case: 2.0.2 + tslib: 2.6.2 + dev: true + /node-dir@0.1.17: resolution: {integrity: sha512-tmPX422rYgofd4epzrNoOXiE8XFZYOcCq1vD7MAXCDO+O+zndlA2ztdKKMa+EeuBG5tHETpr4ml4RGgpqDCCAg==} engines: {node: '>= 0.10.5'} @@ -9516,6 +9953,14 @@ packages: es-abstract: 1.22.3 dev: true + /ofetch@1.3.3: + resolution: {integrity: sha512-s1ZCMmQWXy4b5K/TW9i/DtiN8Ku+xCiHcjQ6/J/nDdssirrQNOoB165Zu8EqLMA2lln1JUth9a0aW9Ap2ctrUg==} + dependencies: + destr: 2.0.2 + node-fetch-native: 1.6.1 + ufo: 1.3.2 + dev: true + /ohash@1.1.3: resolution: {integrity: sha512-zuHHiGTYTA1sYJ/wZN+t5HKZaH23i4yI1HMwbuXm24Nid7Dv0KcuRlKoNKS9UNfAVSBlnGLcuQrnOKWOZoEGaw==} dev: true @@ -9690,7 +10135,7 @@ packages: resolution: {integrity: sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==} engines: {node: '>=8'} dependencies: - '@babel/code-frame': 7.22.5 + '@babel/code-frame': 7.23.5 error-ex: 1.3.2 json-parse-even-better-errors: 2.3.1 lines-and-columns: 1.2.4 @@ -11196,6 +11641,13 @@ packages: engines: {node: '>=8'} dev: true + /snake-case@3.0.4: + resolution: {integrity: sha512-LAOh4z89bGQvl9pFfNF8V146i7o7/CqFPbqzYgP+yYzDIDeS9HaNFtXABamRW+AQzEVODcvE79ljJ+8a9YSdMg==} + dependencies: + dot-case: 3.0.4 + tslib: 2.6.2 + dev: true + /source-map-js@1.0.2: resolution: {integrity: sha512-R0XvVJ9WusLiqTCEiGCmICCMplcCkIwwR11mOSD9CR5u+IXYdiseeEuXCVAjS54zqwkLcPNnmU4OeJ6tUrWhDw==} engines: {node: '>=0.10.0'} @@ -11513,6 +11965,10 @@ packages: engines: {node: '>= 0.4'} dev: true + /svg-parser@2.0.4: + resolution: {integrity: sha512-e4hG1hRwoOdRb37cIMSgzNsxyzKfayW6VOflrwvR+/bzrkyxY/31WkbgnQpgtrNp1SdpJvpUAGTa/ZoiPNDuRQ==} + dev: true + /svgo@3.2.0: resolution: {integrity: sha512-4PP6CMW/V7l/GmKRKzsLR8xxjdHTV4IMvhTnpuHwwBazSIlw5W/5SmPjN8Dwyt7lKbSJrRDgp4t9ph0HgChFBQ==} engines: {node: '>=14.0.0'} @@ -11539,6 +11995,14 @@ packages: tslib: 2.6.2 dev: true + /synckit@0.9.0: + resolution: {integrity: sha512-7RnqIMq572L8PeEzKeBINYEJDDxpcH8JEgLwUqBd3TkofhFRbkq4QLR0u+36avGAhCRbk2nnmjcW9SE531hPDg==} + engines: {node: ^14.18.0 || >=16.0.0} + dependencies: + '@pkgr/core': 0.1.1 + tslib: 2.6.2 + dev: true + /tapable@1.1.3: resolution: {integrity: sha512-4WK/bYZmj8xLr+HUCODHGF1ZFzsYffasLUgEiMBY4fgtltdO6B4WJtlSbPaDTLpYTcGVwM2qLnFTICEcNxs3kA==} engines: {node: '>=6'} @@ -11890,6 +12354,15 @@ packages: which-boxed-primitive: 1.0.2 dev: true + /unconfig@0.3.11: + resolution: {integrity: sha512-bV/nqePAKv71v3HdVUn6UefbsDKQWRX+bJIkiSm0+twIds6WiD2bJLWWT3i214+J/B4edufZpG2w7Y63Vbwxow==} + dependencies: + '@antfu/utils': 0.7.7 + defu: 6.1.4 + jiti: 1.21.0 + mlly: 1.5.0 + dev: true + /undici-types@5.26.5: resolution: {integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==} @@ -11964,12 +12437,51 @@ packages: engines: {node: '>= 10.0.0'} dev: true + /unocss@0.58.4(postcss@8.4.33)(vite@5.0.12): + resolution: {integrity: sha512-JYeQddAIObJPr6nuxahOgku0MIzjIaQ2P73KtJr0zSuzx6kiq20jf67FgDIOP1Ks6s7iJd7Ga3yuY2h49XjDjg==} + engines: {node: '>=14'} + peerDependencies: + '@unocss/webpack': 0.58.4 + vite: ^2.9.0 || ^3.0.0-0 || ^4.0.0 || ^5.0.0-0 + peerDependenciesMeta: + '@unocss/webpack': + optional: true + vite: + optional: true + dependencies: + '@unocss/astro': 0.58.4(vite@5.0.12) + '@unocss/cli': 0.58.4 + '@unocss/core': 0.58.4 + '@unocss/extractor-arbitrary-variants': 0.58.4 + '@unocss/postcss': 0.58.4(postcss@8.4.33) + '@unocss/preset-attributify': 0.58.4 + '@unocss/preset-icons': 0.58.4 + '@unocss/preset-mini': 0.58.4 + '@unocss/preset-tagify': 0.58.4 + '@unocss/preset-typography': 0.58.4 + '@unocss/preset-uno': 0.58.4 + '@unocss/preset-web-fonts': 0.58.4 + '@unocss/preset-wind': 0.58.4 + '@unocss/reset': 0.58.4 + '@unocss/transformer-attributify-jsx': 0.58.4 + '@unocss/transformer-attributify-jsx-babel': 0.58.4 + '@unocss/transformer-compile-class': 0.58.4 + '@unocss/transformer-directives': 0.58.4 + '@unocss/transformer-variant-group': 0.58.4 + '@unocss/vite': 0.58.4(vite@5.0.12) + vite: 5.0.12(@types/node@20.11.16)(sass@1.70.0) + transitivePeerDependencies: + - postcss + - rollup + - supports-color + dev: true + /unpipe@1.0.0: resolution: {integrity: sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==} engines: {node: '>= 0.8'} dev: true - /unplugin-icons@0.18.3: + /unplugin-icons@0.18.3(@svgr/core@8.1.0): resolution: {integrity: sha512-6EHPMXOq7XL8JAULzX0o3KqOsJHhYfpDfB1WvBWwZJH/PutIkV/ahRpHytucQ1evfRFuv/DVIozEmFIhP1xRxA==} peerDependencies: '@svgr/core': '>=7.0.0' @@ -11992,6 +12504,7 @@ packages: '@antfu/install-pkg': 0.3.1 '@antfu/utils': 0.7.7 '@iconify/utils': 2.1.20 + '@svgr/core': 8.1.0(typescript@5.3.3) debug: 4.3.4 kolorist: 1.8.0 local-pkg: 0.5.0 @@ -12030,16 +12543,6 @@ packages: picocolors: 1.0.0 dev: true - /update-browserslist-db@1.0.13(browserslist@4.22.2): - resolution: {integrity: sha512-xebP81SNcPuNpPP3uzeW1NYXxI3rxyJzF3pD6sH4jE7o/IX+WtSpwnVU+qIsDPyk0d3hmFQ7mjqc6AtV604hbg==} - hasBin: true - peerDependencies: - browserslist: '>= 4.21.0' - dependencies: - browserslist: 4.22.2 - escalade: 3.1.1 - picocolors: 1.0.0 - /update-browserslist-db@1.0.13(browserslist@4.22.3): resolution: {integrity: sha512-xebP81SNcPuNpPP3uzeW1NYXxI3rxyJzF3pD6sH4jE7o/IX+WtSpwnVU+qIsDPyk0d3hmFQ7mjqc6AtV604hbg==} hasBin: true @@ -12049,7 +12552,6 @@ packages: browserslist: 4.22.3 escalade: 3.1.1 picocolors: 1.0.0 - dev: true /update-notifier@2.5.0: resolution: {integrity: sha512-gwMdhgJHGuj/+wHJJs9e6PcCszpxR1b236igrOkUofGhqJuG+amlIKwApH1IW1WWl7ovZxsX49lMBWLxSdm5Dw==} diff --git a/postcss.config.cjs b/postcss.config.cjs index 8ad5633c..deea0319 100644 --- a/postcss.config.cjs +++ b/postcss.config.cjs @@ -1,14 +1,10 @@ /* eslint-disable global-require */ /** @type {import('postcss-load-config').Config} */ const config = { - plugins: - process.env.NODE_ENV !== 'development' - ? [ - require('cssnano')({ - preset: 'advanced', - }), - ] - : [], + plugins: { + cssnano: process.env.NODE_ENV !== 'development' ? {} : false, + // '@unocss/postcss': {}, + }, }; module.exports = config; diff --git a/public/fonts/roboto-flex.woff2 b/public/fonts/roboto-flex.woff2 new file mode 100644 index 00000000..a572fdad Binary files /dev/null and b/public/fonts/roboto-flex.woff2 differ diff --git a/src/shared/util/icons.tsx b/src/shared/util/icons.tsx new file mode 100644 index 00000000..88f4ebfd --- /dev/null +++ b/src/shared/util/icons.tsx @@ -0,0 +1,24 @@ +import React, { SVGProps } from 'react'; +import ClosedIcon from '~icons/material-symbols/lock'; +import WaitlistIcon from '~icons/material-symbols/timelapse'; +import CancelledIcon from '~icons/material-symbols/warning'; +import { Status } from '../types/Course'; + +/** + * Get Icon component based on status + * @param props.status status + * @returns React.ReactElement - the icon component + */ +export function StatusIcon(props: SVGProps & { status: Status }): React.ReactElement { + const { status, ...rest } = props; + + switch (props.status) { + case Status.WAITLISTED: + return ; + case Status.CLOSED: + return ; + case Status.CANCELLED: + return ; + default: + } +} diff --git a/src/stories/components/CalendarCourseCell.stories.tsx b/src/stories/components/CalendarCourseCell.stories.tsx new file mode 100644 index 00000000..647a766d --- /dev/null +++ b/src/stories/components/CalendarCourseCell.stories.tsx @@ -0,0 +1,67 @@ +import { Meta, StoryObj } from '@storybook/react'; +import React from 'react'; +import { Course, Status } from 'src/shared/types/Course'; +import { CourseMeeting, DAY_MAP } from 'src/shared/types/CourseMeeting'; +import { CourseSchedule } from 'src/shared/types/CourseSchedule'; +import Instructor from 'src/shared/types/Instructor'; +import CalendarCourseCell from 'src/views/components/common/CalendarCourseCell/CalendarCourseCell'; + +const meta = { + title: 'Components/Common/CalendarCourseCell', + component: CalendarCourseCell, + parameters: { + layout: 'centered', + }, + tags: ['autodocs'], + argTypes: { + course: { control: 'object' }, + meetingIdx: { control: 'number' }, + color: { control: 'color' }, + }, + render: (args: any) => ( +
+ +
+ ), +} satisfies Meta; +export default meta; + +type Story = StoryObj; + +export const Default: Story = { + args: { + course: new Course({ + uniqueId: 123, + number: '311C', + fullName: "311C - Bevo's Default Course", + courseName: "Bevo's Default Course", + department: 'BVO', + creditHours: 3, + status: Status.WAITLISTED, + instructors: [new Instructor({ firstName: '', lastName: 'Bevo', fullName: 'Bevo' })], + isReserved: false, + url: '', + flags: [], + schedule: new CourseSchedule({ + meetings: [ + new CourseMeeting({ + days: [DAY_MAP.M, DAY_MAP.W, DAY_MAP.F], + startTime: 480, + endTime: 570, + location: { + building: 'UTC', + room: '123', + }, + }), + ], + }), + instructionMode: 'In Person', + semester: { + year: 2024, + season: 'Spring', + }, + }), + meetingIdx: 0, + color: 'red', + }, +}; diff --git a/src/stories/components/Text.stories.tsx b/src/stories/components/Text.stories.tsx new file mode 100644 index 00000000..ecedaf92 --- /dev/null +++ b/src/stories/components/Text.stories.tsx @@ -0,0 +1,57 @@ +import { Button } from 'src/views/components/common/Button/Button'; +import type { Meta, StoryObj } from '@storybook/react'; +import React from 'react'; +import Text from '../../views/components/common/Text/Text'; + +// More on how to set up stories at: https://storybook.js.org/docs/writing-stories#default-export +const meta = { + title: 'Components/Common/Text', + component: Text, + parameters: { + // Optional parameter to center the component in the Canvas. More info: https://storybook.js.org/docs/configure/story-layout + layout: 'centered', + }, + // This component will have an automatically generated Autodocs entry: https://storybook.js.org/docs/writing-docs/autodocs + tags: ['autodocs'], + // More on argTypes: https://storybook.js.org/docs/api/argtypes + args: { + children: 'The quick brown fox jumps over the lazy dog.', + }, + argTypes: { + children: { control: 'text' }, + }, +} satisfies Meta; + +export default meta; +type Story = StoryObj; + +// More on writing stories with args: https://storybook.js.org/docs/writing-stories/args +export const Default: Story = { + args: {}, +}; + +export const AllVariants: Story = { + args: { + children: 'The quick brown fox jumps over the lazy dog.', + }, + render: props => ( +
+ + + + + + + + + + +
+ ), + parameters: { + design: { + type: 'figma', + url: 'https://www.figma.com/file/8tsCay2FRqctrdcZ3r9Ahw/UTRP?type=design&node-id=324-389&mode=design&t=BoS5xBrpSsjgQXqv-4', + }, + }, +}; diff --git a/src/tsconfig.json b/src/tsconfig.json index 1eff978f..2cdcaead 100644 --- a/src/tsconfig.json +++ b/src/tsconfig.json @@ -8,7 +8,7 @@ ], "types": [ "chrome", - "node" + "node", ], }, } diff --git a/src/views/components/common/CalendarCourseCell/CalendarCourseCell.tsx b/src/views/components/common/CalendarCourseCell/CalendarCourseCell.tsx new file mode 100644 index 00000000..27b2519e --- /dev/null +++ b/src/views/components/common/CalendarCourseCell/CalendarCourseCell.tsx @@ -0,0 +1,50 @@ +import React from 'react'; +import { Course, Status } from 'src/shared/types/Course'; +import { CourseMeeting } from 'src/shared/types/CourseMeeting'; +import ClosedIcon from '~icons/material-symbols/lock'; +import WaitlistIcon from '~icons/material-symbols/timelapse'; +import CancelledIcon from '~icons/material-symbols/warning'; +import Text from '../Text/Text'; + +export interface CalendarCourseBlockProps { + /** The Course that the meeting is for. */ + course: Course; + /* index into course meeting array to display */ + meetingIdx?: number; + /** The background color for the course. */ + color: string; +} + +const CalendarCourseBlock: React.FC = ({ course, meetingIdx }: CalendarCourseBlockProps) => { + let meeting: CourseMeeting | null = meetingIdx !== undefined ? course.schedule.meetings[meetingIdx] : null; + let rightIcon: React.ReactNode | null = null; + if (course.status === Status.WAITLISTED) { + rightIcon = ; + } else if (course.status === Status.CLOSED) { + rightIcon = ; + } else if (course.status === Status.CANCELLED) { + rightIcon = ; + } + + return ( +
+
+ + {course.department} {course.number} - {course.instructors[0].lastName} + + + {`${meeting.getTimeString({ separator: '–', capitalize: true })}${ + meeting.location ? ` – ${meeting.location.building}` : '' + }`} + +
+ {rightIcon && ( +
+ {rightIcon} +
+ )} +
+ ); +}; + +export default CalendarCourseBlock; diff --git a/src/views/components/common/ExtensionRoot/ExtensionRoot.tsx b/src/views/components/common/ExtensionRoot/ExtensionRoot.tsx index f01be7c7..9bc27972 100644 --- a/src/views/components/common/ExtensionRoot/ExtensionRoot.tsx +++ b/src/views/components/common/ExtensionRoot/ExtensionRoot.tsx @@ -1,6 +1,8 @@ import React from 'react'; import styles from './ExtensionRoot.module.scss'; +import 'uno.css'; + interface Props { testId?: string; } diff --git a/src/views/components/common/Text/Text.module.scss b/src/views/components/common/Text/Text.module.scss index be6fd28b..1f52a96b 100644 --- a/src/views/components/common/Text/Text.module.scss +++ b/src/views/components/common/Text/Text.module.scss @@ -2,59 +2,64 @@ @use 'src/views/styles/fonts.module.scss'; .text { - font-family: 'Inter', sans-serif; - color: colors.$charcoal; - line-height: initial; + font-family: 'Roboto Flex', sans-serif; + line-height: normal; + font-style: normal; } -.light_weight { - font-weight: fonts.$light_weight; +.mini { + font-size: 0.79rem; + font-weight: 500; } -.regular_weight { - font-weight: fonts.$regular_weight; +.small { + font-size: 0.88875rem; + font-weight: 500; } -.normal_weight { - font-weight: fonts.$normal_weight; +.p { + font-size: 1rem; + font-weight: 400; + letter-spacing: 0.025rem; } -.semi_bold_weight { - font-weight: fonts.$semi_bold_weight; +.h4 { + font-size: 1.125rem; + font-weight: 500; } -.bold_weight { - font-weight: fonts.$bold_weight; +.h3-course { + font-size: 0.6875rem; + font-weight: 400; + line-height: 100%; /* 0.6875rem */ } -.black_weight { - font-weight: fonts.$black_weight; +.h3 { + font-size: 1.26563rem; + font-weight: 600; + text-transform: uppercase; } -.x_small_size { - font-size: fonts.$x_small_size; +.h2-course { + font-size: 1rem; + font-weight: 500; + letter-spacing: 0.03125rem; + text-transform: capitalize; } -.xx_small_size { - font-size: fonts.$xx_small_size; +.h2 { + font-size: 1.42375rem; + font-weight: 500; } -.small_size { - font-size: fonts.$small_size; +.h1-course { + font-size: 1rem; + font-weight: 600; + text-transform: capitalize; } -.medium_size { - font-size: fonts.$medium_size; -} - -.large_size { - font-size: fonts.$large_size; -} - -.x_large_size { - font-size: fonts.$x_large_size; -} - -.xx_large_size { - font-size: fonts.$xx_large_size; +.h1 { + font-size: 1.60188rem; + font-weight: 700; + text-transform: uppercase; } diff --git a/src/views/components/common/Text/Text.tsx b/src/views/components/common/Text/Text.tsx index 15ce7c82..99d62d28 100644 --- a/src/views/components/common/Text/Text.tsx +++ b/src/views/components/common/Text/Text.tsx @@ -1,50 +1,32 @@ import classNames from 'classnames'; import React, { PropsWithChildren } from 'react'; -import colors, { Color } from '@views/styles/colors.module.scss'; -import { Size, Weight } from '@views/styles/fonts.module.scss'; import styles from './Text.module.scss'; /** * */ export type TextProps = { - color?: Color; - weight?: Weight; - size?: Size; - span?: boolean; - className?: string; - onClick?: () => void; - title?: string; - align?: React.CSSProperties['textAlign']; - style?: React.CSSProperties; -}; + variant?: Variant; +} & ( + | (React.HTMLAttributes & { as?: 'span' }) + | (React.HTMLAttributes & { as: 'div' }) +); + +const variants = ['mini', 'small', 'p', 'h4', 'h3-course', 'h3', 'h2-course', 'h2', 'h1-course', 'h1'] as const; + +type Variant = (typeof variants)[number]; /** * A reusable Text component with props that build on top of the design system for the extension */ -export default function Text(props: PropsWithChildren) { - const style: React.CSSProperties = { - ...props.style, - textAlign: props.align, - color: props.color ? colors[props.color] : undefined, - }; +export default function Text({ variant, as, className, ...props }: PropsWithChildren) { + const mergedClassName = classNames(styles.text, styles[variant], className); - const weightClass = `${props.weight ?? 'regular'}_weight`; - const fontSizeClass = `${props.size ?? 'medium'}_size`; - - const className = classNames(styles.text, styles[weightClass], styles[fontSizeClass], props.className); - - if (props.span) { - return ( - - {props.children} - - ); - } + if (as === 'div') return
; return ( -
+ {props.children} -
+ ); } diff --git a/src/views/styles/fonts.module.scss b/src/views/styles/fonts.module.scss index 5e609a2f..13459619 100644 --- a/src/views/styles/fonts.module.scss +++ b/src/views/styles/fonts.module.scss @@ -1,13 +1,20 @@ -@each $weights in '100' '200' '300' '400' '500' '600' '700' '800' '900' { +@each $weight in '100' '200' '300' '400' '500' '600' '700' '800' '900' { @font-face { font-family: 'Inter'; - src: url('@public/fonts/inter-#{$weights}.woff2') format('woff2'); + src: url('@public/fonts/inter-#{$weight}.woff2') format('woff2'); font-display: auto; font-style: normal; - font-weight: #{$weights}; + font-weight: #{$weight}; } } +@font-face { + font-family: 'Roboto Flex'; + src: url('@public/fonts/roboto-flex.woff2') format('woff2'); + font-display: swap; + font-style: normal; +} + @font-face { font-family: 'Material Icons Round'; font-style: normal; @@ -16,34 +23,12 @@ src: url('@public/fonts/material-icons.woff2') format('woff2'); } -$light_weight: 300; -$regular_weight: 400; -$normal_weight: 500; -$semi_bold_weight: 600; -$bold_weight: 700; -$black_weight: 900; +$normal_weight: 500; // Used by , will be removed later -$xx_small_size: 4px; -$x_small_size: 8px; -$small_size: 12px; $medium_size: 16px; -$large_size: 20px; -$x_large_size: 32px; -$xx_large_size: 48px; :export { - light_weight: $light_weight; - regular_weight: $regular_weight; normal_weight: $normal_weight; - semi_bold_weight: $semi_bold_weight; - bold_weight: $bold_weight; - black_weight: $black_weight; - xx_small_size: $xx_small_size; - x_small_size: $x_small_size; - small_size: $small_size; medium_size: $medium_size; - large_size: $large_size; - x_large_size: $x_large_size; - xx_large_size: $xx_large_size; } diff --git a/src/views/styles/fonts.module.scss.d.ts b/src/views/styles/fonts.module.scss.d.ts index 4d426ae1..f51017c4 100644 --- a/src/views/styles/fonts.module.scss.d.ts +++ b/src/views/styles/fonts.module.scss.d.ts @@ -2,25 +2,14 @@ * the type for all the weight scss variables exported from fonts.module.scss */ export interface IWeights { - light_weight: number; - regular_weight: number; normal_weight: number; - bold_weight: number; - semi_bold_weight: number; - black_weight: number; } /** * the type for all the size scss variables exported from fonts.module.scss */ export interface ISizes { - xx_small_size: number; - x_small_size: number; - small_size: number; medium_size: number; - large_size: number; - x_large_size: number; - xx_large_size: number; } /** A utility type that removes the _weight postfix from the variable names for weights */ diff --git a/src/vite-env.d.ts b/src/vite-env.d.ts index 11f02fe2..21ff17fa 100644 --- a/src/vite-env.d.ts +++ b/src/vite-env.d.ts @@ -1 +1,2 @@ /// +/// diff --git a/tsconfig.json b/tsconfig.json index e483d033..f2267ecc 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -16,6 +16,7 @@ "moduleResolution": "node", "types": [ "vite/client", + "unplugin-icons/types/react", "node" ], "noFallthroughCasesInSwitch": true, @@ -53,6 +54,7 @@ "package.json", ".eslintrc", "postcss.config.cjs", - ".storybook" + ".storybook", + "unocss.config.ts", ] } diff --git a/unocss.config.ts b/unocss.config.ts new file mode 100644 index 00000000..a5cadfc9 --- /dev/null +++ b/unocss.config.ts @@ -0,0 +1,58 @@ +import presetUno from '@unocss/preset-uno'; +import presetWebFonts from '@unocss/preset-web-fonts'; +import transformerDirectives from '@unocss/transformer-directives'; +import transformerVariantGroup from '@unocss/transformer-variant-group'; +import { defineConfig } from 'unocss'; + +export default defineConfig({ + rules: [ + ['btn-transition', { transition: 'color 180ms, border-color 150ms, background-color 150ms, transform 50ms' }], + [ + 'ring-offset-0', + { + '--un-ring-offset-width': '0px', + }, + ], + ], + shortcuts: { + focusable: 'outline-none ring-blue-500/50 dark:ring-blue-400/60 ring-0 focus-visible:ring-4', + }, + theme: { + easing: { + 'in-out-expo': 'cubic-bezier(.46, 0, .21, 1)', + 'out-expo': 'cubic-bezier(0.19, 1, 0.22, 1)', + }, + colors: { + ut: { + 'burnt-orange': '#BF5700', + black: '#333F48', + orange: '#f8971f', + yellow: '#ffd600', + 'light-green': '#a6cd57', + green: '#579d42', + teal: '#00a9b7', + blue: '#005f86', + gray: '#9cadb7', + 'off-white': '#d6d2c4', + concrete: '#95a5a6', + }, + theme: { + red: '#af2e2d', + black: '#1a2024', + }, + }, + }, + + presets: [ + presetUno(), + presetWebFonts({ + provider: 'none', + fonts: { + sans: { + name: 'Roboto Flex', + }, + }, + }), + ], + transformers: [transformerVariantGroup(), transformerDirectives()], +}); diff --git a/vite.config.ts b/vite.config.ts index 077efb8f..7676a4e1 100644 --- a/vite.config.ts +++ b/vite.config.ts @@ -1,6 +1,7 @@ import { crx } from '@crxjs/vite-plugin'; import react from '@vitejs/plugin-react-swc'; import { resolve } from 'path'; +import UnoCSS from 'unocss/vite'; import Icons from 'unplugin-icons/vite'; import { Plugin, ResolvedConfig, ViteDevServer, defineConfig } from 'vite'; import inspect from 'vite-plugin-inspect'; @@ -45,7 +46,8 @@ let server: ViteDevServer; export default defineConfig({ plugins: [ react(), - Icons({ compiler: 'jsx' }), + UnoCSS(), + Icons({ compiler: 'jsx', jsx: 'react' }), crx({ manifest }), inspect(), {