diff --git a/package-lock.json b/package-lock.json index bb2322d..b2c5f10 100644 --- a/package-lock.json +++ b/package-lock.json @@ -11,7 +11,8 @@ "@formatjs/intl-durationformat": "^0.10.1" }, "devDependencies": { - "@iconify/svelte": "^5.2.1", + "@iconify/css-svelte": "^1.0.0", + "@iconify/json": "^2.2.439", "@react2svelte/swipeable": "^0.1.4", "@svelte-put/dragscroll": "^4.0.0", "@sveltejs/adapter-auto": "^7.0.0", @@ -41,9 +42,24 @@ "tailwindcss": "^4.0.9", "tslib": "^2.8.1", "typescript": "^5.9.3", + "unplugin-icons": "^23.0.1", "vite": "^7.3.1" } }, + "node_modules/@antfu/install-pkg": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@antfu/install-pkg/-/install-pkg-1.1.0.tgz", + "integrity": "sha512-MGQsmw10ZyI+EJo45CdSER4zEb+p31LpDAFp2Z3gkSd1yqVZGi0Ebx++YTEMonJy4oChEMLsxZ64j8FH6sSqtQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "package-manager-detector": "^1.3.0", + "tinyexec": "^1.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + } + }, "node_modules/@babel/code-frame": { "version": "7.29.0", "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.29.0.tgz", @@ -2252,10 +2268,10 @@ "url": "https://github.com/sponsors/nzakas" } }, - "node_modules/@iconify/svelte": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/@iconify/svelte/-/svelte-5.2.1.tgz", - "integrity": "sha512-zHmsIPmnIhGd5gc95bNN5FL+GifwMZv7M2rlZEpa7IXYGFJm/XGHdWf6PWQa6OBoC+R69WyiPO9NAj5wjfjbow==", + "node_modules/@iconify/css-svelte": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@iconify/css-svelte/-/css-svelte-1.0.0.tgz", + "integrity": "sha512-S9kZ+U/hQ+QVHZVLKu06xiVi0rII4DJCh2Z6M1m7IOyECBD7A1emk5pRx4fWG9Zp7ZOHL8dWO90sxtsaOPZBJw==", "dev": true, "license": "MIT", "dependencies": { @@ -2265,7 +2281,18 @@ "url": "https://github.com/sponsors/cyberalien" }, "peerDependencies": { - "svelte": ">5.0.0" + "svelte": ">4.0.0" + } + }, + "node_modules/@iconify/json": { + "version": "2.2.439", + "resolved": "https://registry.npmjs.org/@iconify/json/-/json-2.2.439.tgz", + "integrity": "sha512-DFpo7ZqntngeDaVFtsj+AydUrJoEPW0FIpMrmngo3iHxLXpqcNe5lhztPqvVBoXllbohomcA1YRjRO/ljo7AnQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@iconify/types": "*", + "pathe": "^2.0.3" } }, "node_modules/@iconify/types": { @@ -2275,6 +2302,18 @@ "dev": true, "license": "MIT" }, + "node_modules/@iconify/utils": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@iconify/utils/-/utils-3.1.0.tgz", + "integrity": "sha512-Zlzem1ZXhI1iHeeERabLNzBHdOa4VhQbqAcOQaMKuTuyZCpwKbC2R4Dd0Zo3g9EAc+Y4fiarO8HIHRAth7+skw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@antfu/install-pkg": "^1.1.0", + "@iconify/types": "^2.0.0", + "mlly": "^1.8.0" + } + }, "node_modules/@jridgewell/gen-mapping": { "version": "0.3.13", "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.13.tgz", @@ -2455,19 +2494,6 @@ "node": ">= 8.0.0" } }, - "node_modules/@rollup/pluginutils/node_modules/picomatch": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", - "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8.6" - }, - "funding": { - "url": "https://github.com/sponsors/jonschlinkert" - } - }, "node_modules/@rollup/rollup-android-arm-eabi": { "version": "4.57.1", "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.57.1.tgz", @@ -2846,9 +2872,9 @@ } }, "node_modules/@sveltejs/adapter-auto": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/@sveltejs/adapter-auto/-/adapter-auto-7.0.0.tgz", - "integrity": "sha512-ImDWaErTOCkRS4Gt+5gZuymKFBobnhChXUZ9lhUZLahUgvA4OOvRzi3sahzYgbxGj5nkA6OV0GAW378+dl/gyw==", + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/@sveltejs/adapter-auto/-/adapter-auto-7.0.1.tgz", + "integrity": "sha512-dvuPm1E7M9NI/+canIQ6KKQDU2AkEefEZ2Dp7cY6uKoPq9Z/PhOXABe526UdW2mN986gjVkuSLkOYIBnS/M2LQ==", "dev": true, "license": "MIT", "peerDependencies": { @@ -2866,9 +2892,9 @@ } }, "node_modules/@sveltejs/kit": { - "version": "2.50.2", - "resolved": "https://registry.npmjs.org/@sveltejs/kit/-/kit-2.50.2.tgz", - "integrity": "sha512-875hTUkEbz+MyJIxWbQjfMaekqdmEKUUfR7JyKcpfMRZqcGyrO9Gd+iS1D/Dx8LpE5FEtutWGOtlAh4ReSAiOA==", + "version": "2.51.0", + "resolved": "https://registry.npmjs.org/@sveltejs/kit/-/kit-2.51.0.tgz", + "integrity": "sha512-BkcfxVVYmfxHGYLugemb7TWW+y/MNZbxXHXJ141lyyi2ozq0Q4kbqoV0cBGlh7F0vNtCMvfr7UPnxIaBjcP9gg==", "dev": true, "license": "MIT", "dependencies": { @@ -3275,6 +3301,13 @@ "undici-types": "~7.16.0" } }, + "node_modules/@types/trusted-types": { + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/@types/trusted-types/-/trusted-types-2.0.7.tgz", + "integrity": "sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==", + "dev": true, + "license": "MIT" + }, "node_modules/@types/unist": { "version": "2.0.11", "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.11.tgz", @@ -3686,6 +3719,13 @@ "dev": true, "license": "MIT" }, + "node_modules/confbox": { + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/confbox/-/confbox-0.2.4.tgz", + "integrity": "sha512-ysOGlgTFbN2/Y6Cg3Iye8YKulHw+R2fNXHrgSmXISQdMnomY6eNDprVdW9R5xBguEqI954+S6709UyiO7B+6OQ==", + "dev": true, + "license": "MIT" + }, "node_modules/convert-source-map": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz", @@ -4170,6 +4210,13 @@ "node": ">=0.10.0" } }, + "node_modules/exsolve": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/exsolve/-/exsolve-1.0.8.tgz", + "integrity": "sha512-LmDxfWXwcTArk8fUEnOfSZpHOJ6zOMUJKOtFLFqJLoKJetuQG874Uc7/Kki7zFLzYybmZhp1M7+98pfMqeX8yA==", + "dev": true, + "license": "MIT" + }, "node_modules/fast-deep-equal": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", @@ -4917,6 +4964,24 @@ "node": ">=10" } }, + "node_modules/local-pkg": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/local-pkg/-/local-pkg-1.1.2.tgz", + "integrity": "sha512-arhlxbFRmoQHl33a0Zkle/YWlmNwoyt6QNZEIJcqNbdrsix5Lvc4HyyI3EnwxTYlZYc32EbYrQ8SzEZ7dqgg9A==", + "dev": true, + "license": "MIT", + "dependencies": { + "mlly": "^1.7.4", + "pkg-types": "^2.3.0", + "quansync": "^0.2.11" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + } + }, "node_modules/locate-character": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/locate-character/-/locate-character-3.0.0.tgz", @@ -5085,19 +5150,6 @@ "node": ">=8.6" } }, - "node_modules/micromatch/node_modules/picomatch": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", - "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8.6" - }, - "funding": { - "url": "https://github.com/sponsors/jonschlinkert" - } - }, "node_modules/minimatch": { "version": "3.1.2", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", @@ -5121,6 +5173,38 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/mlly": { + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/mlly/-/mlly-1.8.0.tgz", + "integrity": "sha512-l8D9ODSRWLe2KHJSifWGwBqpTZXIXTeo8mlKjY+E2HAakaTeNpqAyBZ8GSqLzHgw4XmHmC8whvpjJNMbFZN7/g==", + "dev": true, + "license": "MIT", + "dependencies": { + "acorn": "^8.15.0", + "pathe": "^2.0.3", + "pkg-types": "^1.3.1", + "ufo": "^1.6.1" + } + }, + "node_modules/mlly/node_modules/confbox": { + "version": "0.1.8", + "resolved": "https://registry.npmjs.org/confbox/-/confbox-0.1.8.tgz", + "integrity": "sha512-RMtmw0iFkeR4YV+fUOSucriAQNb9g8zFR52MWCtl+cCZOFRNL6zeB395vPzFhEjjn4fMxXudmELnl/KF/WrK6w==", + "dev": true, + "license": "MIT" + }, + "node_modules/mlly/node_modules/pkg-types": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/pkg-types/-/pkg-types-1.3.1.tgz", + "integrity": "sha512-/Jm5M4RvtBFVkKWRu2BLUTNP8/M2a+UwuAX+ae4770q1qVGtfjG+WTCupoZixokjmHiry8uI+dlY8KXYV5HVVQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "confbox": "^0.1.8", + "mlly": "^1.7.4", + "pathe": "^2.0.1" + } + }, "node_modules/mri": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/mri/-/mri-1.2.0.tgz", @@ -5190,8 +5274,7 @@ "https://github.com/sponsors/sxzz", "https://opencollective.com/debug" ], - "license": "MIT", - "peer": true + "license": "MIT" }, "node_modules/optionator": { "version": "0.9.4", @@ -5243,6 +5326,13 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/package-manager-detector": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/package-manager-detector/-/package-manager-detector-1.6.0.tgz", + "integrity": "sha512-61A5ThoTiDG/C8s8UMZwSorAGwMJ0ERVGj2OjoW5pAalsNOg15+iQiPzrLJ4jhZ1HJzmC2PIHT2oEiH3R5fzNA==", + "dev": true, + "license": "MIT" + }, "node_modules/parent-module": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", @@ -5283,6 +5373,13 @@ "dev": true, "license": "MIT" }, + "node_modules/pathe": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/pathe/-/pathe-2.0.3.tgz", + "integrity": "sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==", + "dev": true, + "license": "MIT" + }, "node_modules/picocolors": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", @@ -5291,18 +5388,30 @@ "license": "ISC" }, "node_modules/picomatch": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.3.tgz", - "integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==", + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", + "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", "dev": true, "license": "MIT", "engines": { - "node": ">=12" + "node": ">=8.6" }, "funding": { "url": "https://github.com/sponsors/jonschlinkert" } }, + "node_modules/pkg-types": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pkg-types/-/pkg-types-2.3.0.tgz", + "integrity": "sha512-SIqCzDRg0s9npO5XQ3tNZioRY1uK06lA41ynBC1YmFTmnY6FjUjVt6s4LoADmwoig1qqD0oK8h1p/8mlMx8Oig==", + "dev": true, + "license": "MIT", + "dependencies": { + "confbox": "^0.2.2", + "exsolve": "^1.0.7", + "pathe": "^2.0.3" + } + }, "node_modules/postcss": { "version": "8.5.6", "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.6.tgz", @@ -5590,6 +5699,23 @@ "node": ">=6" } }, + "node_modules/quansync": { + "version": "0.2.11", + "resolved": "https://registry.npmjs.org/quansync/-/quansync-0.2.11.tgz", + "integrity": "sha512-AifT7QEbW9Nri4tAwR5M/uzpBuqfZf+zwaEM/QkzEjj7NBuFD2rBuy0K3dE+8wltbezDV7JMA0WfnCPYRSYbXA==", + "dev": true, + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/antfu" + }, + { + "type": "individual", + "url": "https://github.com/sponsors/sxzz" + } + ], + "license": "MIT" + }, "node_modules/queue-microtask": { "version": "1.2.3", "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", @@ -5957,9 +6083,9 @@ } }, "node_modules/svelte": { - "version": "5.50.2", - "resolved": "https://registry.npmjs.org/svelte/-/svelte-5.50.2.tgz", - "integrity": "sha512-WCxzm3BBf+Ase6RwiDPR4G36cM4Kb0NuhmLK6x44I+D6reaxizDDg8kBkk4jT/19+Rgmc44eZkOvMO6daoSFIw==", + "version": "5.51.0", + "resolved": "https://registry.npmjs.org/svelte/-/svelte-5.51.0.tgz", + "integrity": "sha512-TOtjs5SjPi1iCXJ7aHwQBY+PEyk0koIc1FCKNFyS9kQuN4FBma9nRuxM4f4A0b5SCdej812vf2Rcql2I0s9FZg==", "dev": true, "license": "MIT", "dependencies": { @@ -5967,6 +6093,7 @@ "@jridgewell/sourcemap-codec": "^1.5.0", "@sveltejs/acorn-typescript": "^1.0.5", "@types/estree": "^1.0.5", + "@types/trusted-types": "^2.0.7", "acorn": "^8.12.1", "aria-query": "^5.3.1", "axobject-query": "^4.1.0", @@ -5984,9 +6111,9 @@ } }, "node_modules/svelte-check": { - "version": "4.3.6", - "resolved": "https://registry.npmjs.org/svelte-check/-/svelte-check-4.3.6.tgz", - "integrity": "sha512-uBkz96ElE3G4pt9E1Tw0xvBfIUQkeH794kDQZdAUk795UVMr+NJZpuFSS62vcmO/DuSalK83LyOwhgWq8YGU1Q==", + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/svelte-check/-/svelte-check-4.4.0.tgz", + "integrity": "sha512-gB3FdEPb8tPO3Y7Dzc6d/Pm/KrXAhK+0Fk+LkcysVtupvAh6Y/IrBCEZNupq57oh0hcwlxCUamu/rq7GtvfSEg==", "dev": true, "license": "MIT", "dependencies": { @@ -6159,6 +6286,16 @@ "node": ">=10" } }, + "node_modules/tinyexec": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/tinyexec/-/tinyexec-1.0.2.tgz", + "integrity": "sha512-W/KYk+NFhkmsYpuHq5JykngiOCnxeVL8v8dFnqxSD8qEEdRfXk1SDM6JzNqcERbcGYj9tMrDQBYV9cjgnunFIg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + } + }, "node_modules/tinyglobby": { "version": "0.2.15", "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.15.tgz", @@ -6176,6 +6313,19 @@ "url": "https://github.com/sponsors/SuperchupuDev" } }, + "node_modules/tinyglobby/node_modules/picomatch": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.3.tgz", + "integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, "node_modules/to-regex-range": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", @@ -6232,6 +6382,13 @@ "node": ">=14.17" } }, + "node_modules/ufo": { + "version": "1.6.3", + "resolved": "https://registry.npmjs.org/ufo/-/ufo-1.6.3.tgz", + "integrity": "sha512-yDJTmhydvl5lJzBmy/hyOAA0d+aqCBuwl818haVdYCRrWV84o7YyeVm4QlVHStqNrrJSTb6jKuFAVqAFsr+K3Q==", + "dev": true, + "license": "MIT" + }, "node_modules/undici-types": { "version": "7.16.0", "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.16.0.tgz", @@ -6339,6 +6496,72 @@ "url": "https://opencollective.com/unified" } }, + "node_modules/unplugin": { + "version": "2.3.11", + "resolved": "https://registry.npmjs.org/unplugin/-/unplugin-2.3.11.tgz", + "integrity": "sha512-5uKD0nqiYVzlmCRs01Fhs2BdkEgBS3SAVP6ndrBsuK42iC2+JHyxM05Rm9G8+5mkmRtzMZGY8Ct5+mliZxU/Ww==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/remapping": "^2.3.5", + "acorn": "^8.15.0", + "picomatch": "^4.0.3", + "webpack-virtual-modules": "^0.6.2" + }, + "engines": { + "node": ">=18.12.0" + } + }, + "node_modules/unplugin-icons": { + "version": "23.0.1", + "resolved": "https://registry.npmjs.org/unplugin-icons/-/unplugin-icons-23.0.1.tgz", + "integrity": "sha512-rv0XEJepajKzDLvRUWASM8K+8+/CCfZn2jtogXqg6RIp7kpatRc/aFrVJn8ANQA09e++lPEEv9yX8cC9enc+QQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@antfu/install-pkg": "^1.1.0", + "@iconify/utils": "^3.1.0", + "local-pkg": "^1.1.2", + "obug": "^2.1.1", + "unplugin": "^2.3.11" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + }, + "peerDependencies": { + "@svgr/core": ">=7.0.0", + "@svgx/core": "^1.0.1", + "@vue/compiler-sfc": "^3.0.2", + "svelte": "^3.0.0 || ^4.0.0 || ^5.0.0" + }, + "peerDependenciesMeta": { + "@svgr/core": { + "optional": true + }, + "@svgx/core": { + "optional": true + }, + "@vue/compiler-sfc": { + "optional": true + }, + "svelte": { + "optional": true + } + } + }, + "node_modules/unplugin/node_modules/picomatch": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.3.tgz", + "integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, "node_modules/update-browserslist-db": { "version": "1.2.3", "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.2.3.tgz", @@ -6477,6 +6700,19 @@ } } }, + "node_modules/vite/node_modules/picomatch": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.3.tgz", + "integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, "node_modules/vitefu": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/vitefu/-/vitefu-1.1.1.tgz", @@ -6498,6 +6734,13 @@ } } }, + "node_modules/webpack-virtual-modules": { + "version": "0.6.2", + "resolved": "https://registry.npmjs.org/webpack-virtual-modules/-/webpack-virtual-modules-0.6.2.tgz", + "integrity": "sha512-66/V2i5hQanC51vBQKPH4aI8NMAcBW59FVBs+rC7eGHupMyfn34q7rZIE+ETlJ+XTevqfUhVVBgSUNSW2flEUQ==", + "dev": true, + "license": "MIT" + }, "node_modules/which": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", @@ -6571,6 +6814,22 @@ "dev": true, "license": "ISC" }, + "node_modules/yaml": { + "version": "2.8.2", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.8.2.tgz", + "integrity": "sha512-mplynKqc1C2hTVYxd0PU2xQAc22TI1vShAYGksCCfxbn/dFwnHTNi1bvYsBTkhdUNtGIf5xNOg938rrSSYvS9A==", + "extraneous": true, + "license": "ISC", + "bin": { + "yaml": "bin.mjs" + }, + "engines": { + "node": ">= 14.6" + }, + "funding": { + "url": "https://github.com/sponsors/eemeli" + } + }, "node_modules/yocto-queue": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", diff --git a/package.json b/package.json index 3e3d315..2406c41 100644 --- a/package.json +++ b/package.json @@ -11,7 +11,8 @@ "check:watch": "svelte-kit sync && svelte-check --tsconfig ./tsconfig.json --watch" }, "devDependencies": { - "@iconify/svelte": "^5.2.1", + "@iconify/css-svelte": "^1.0.0", + "@iconify/json": "^2.2.439", "@react2svelte/swipeable": "^0.1.4", "@svelte-put/dragscroll": "^4.0.0", "@sveltejs/adapter-auto": "^7.0.0", @@ -41,6 +42,7 @@ "tailwindcss": "^4.0.9", "tslib": "^2.8.1", "typescript": "^5.9.3", + "unplugin-icons": "^23.0.1", "vite": "^7.3.1" }, "type": "module", diff --git a/src/app.d.ts b/src/app.d.ts index 520d030..8ceb0ec 100644 --- a/src/app.d.ts +++ b/src/app.d.ts @@ -1,8 +1,14 @@ +/// +/// +/// + import type { DurationFormatConstructor, DurationFormatOptions as _DurationFormatOptions, DurationInput as _DurationInput, } from '@formatjs/intl-durationformat/src/types'; +import type { Component } from 'svelte'; +import 'unplugin-icons/types/svelte'; declare global { // rndtrash: Терпим. https://github.com/microsoft/TypeScript/issues/60608 @@ -15,7 +21,7 @@ declare global { namespace App { interface Route { label: string; - icon: string; + icon?: Component | string; href: string; } diff --git a/src/lib/components/BlogCard.svelte b/src/lib/components/BlogCard.svelte index aa704c9..d16643f 100644 --- a/src/lib/components/BlogCard.svelte +++ b/src/lib/components/BlogCard.svelte @@ -9,13 +9,12 @@ @@ -38,8 +43,8 @@ )} {highlightClasses('text-slate-50')}" > - {#if icon} - + {#if IconComponent} + {/if} {dateString diff --git a/src/lib/components/HoverIcon.svelte b/src/lib/components/HoverIcon.svelte index 71b5914..3ae8f0d 100644 --- a/src/lib/components/HoverIcon.svelte +++ b/src/lib/components/HoverIcon.svelte @@ -1,12 +1,23 @@ - {#if src} - {#if isUrl(src)} - - {:else} - - {/if} + {#if IconComponent} + + {:else if typeof src === 'string' && isUrl(src)} + {:else} {alt ?? 'Без иконки'} {/if} diff --git a/src/lib/components/IconBlock.svelte b/src/lib/components/IconBlock.svelte index 1d4922a..6253672 100644 --- a/src/lib/components/IconBlock.svelte +++ b/src/lib/components/IconBlock.svelte @@ -1,18 +1,27 @@
- + {caption}
- + {@render children()}
diff --git a/src/lib/components/InfoBlock.svelte b/src/lib/components/InfoBlock.svelte index 4c21118..cbaf62c 100644 --- a/src/lib/components/InfoBlock.svelte +++ b/src/lib/components/InfoBlock.svelte @@ -1,12 +1,11 @@ - - + + {@render children()} diff --git a/src/lib/components/SocialButton.svelte b/src/lib/components/SocialButton.svelte index 6a13ab1..5f47859 100644 --- a/src/lib/components/SocialButton.svelte +++ b/src/lib/components/SocialButton.svelte @@ -1,24 +1,29 @@
- +
- + {@render children()}
-
\ No newline at end of file + diff --git a/src/lib/components/SocialHyperlink.svelte b/src/lib/components/SocialHyperlink.svelte index 49d97dc..8cef357 100644 --- a/src/lib/components/SocialHyperlink.svelte +++ b/src/lib/components/SocialHyperlink.svelte @@ -1,23 +1,32 @@ - + - + - + {@render children()} - \ No newline at end of file + diff --git a/src/lib/components/WarningBlock.svelte b/src/lib/components/WarningBlock.svelte index 50c9cf5..0ce2218 100644 --- a/src/lib/components/WarningBlock.svelte +++ b/src/lib/components/WarningBlock.svelte @@ -1,12 +1,11 @@ - - + + {@render children()} diff --git a/src/lib/util/Blogs.ts b/src/lib/util/Blogs.ts index 223ca87..60ae962 100644 --- a/src/lib/util/Blogs.ts +++ b/src/lib/util/Blogs.ts @@ -1,3 +1,5 @@ +import type { Component } from "svelte"; + export const THUMBNAIL_DEFAULT = "https://teasanctuary.ru/common/background-day.webp"; export const BLOG_POST_FRESHNESS_MILLIS = 3 * 24 * 60 * 60 * 1000; // 3 дня @@ -97,16 +99,20 @@ const bptToString: Record = { 'update': 'Обновление' }; -const bptToIcon: Record = { - 'article': 'material-symbols:article', - 'event': 'material-symbols:event', - 'update': 'material-symbols:autorenew' +import ArticleIcon from '~icons/material-symbols/article'; +import EventIcon from '~icons/material-symbols/event'; +import UpdateIcon from '~icons/material-symbols/autorenew'; + +const bptToIcon: Record = { + 'article': ArticleIcon, + 'event': EventIcon, + 'update': UpdateIcon }; export function blogPostTypeToString(type: App.BlogPostType): string { return bptToString[type] ?? bptToString['article']; } -export function blogPostTypeToIcon(type: App.BlogPostType): string { +export function blogPostTypeToIconComponent(type: App.BlogPostType): Component { return bptToIcon[type] ?? bptToIcon['article']; } diff --git a/src/lib/util/LinkResolver.ts b/src/lib/util/LinkResolver.ts index 5304204..cd9842a 100644 --- a/src/lib/util/LinkResolver.ts +++ b/src/lib/util/LinkResolver.ts @@ -1,27 +1,47 @@ +import type { Component } from "svelte"; +import { browser } from '$app/environment'; + +import DefaultLinkIcon from '~icons/material-symbols/link'; +import SteamIcon from '~icons/simple-icons/steam'; +import TelegramIcon from '~icons/simple-icons/telegram'; +import TwitterIcon from '~icons/simple-icons/x'; +import GitHubIcon from '~icons/simple-icons/github'; +import YouTubeIcon from '~icons/simple-icons/youtube'; +import ItchIoIcon from '~icons/simple-icons/itchdotio'; +import DiscordIcon from '~icons/simple-icons/discord'; +import GameBananaIcon from '~icons/simple-icons/gamebanana'; +import BlueSkyIcon from '~icons/simple-icons/bluesky'; +import HamsterIcon from '~icons/fluent-emoji-high-contrast/hamster'; +import GitIcon from '~icons/devicon-plain/git'; +import EmailIcon from '~icons/material-symbols/alternate-email'; +import RssIcon from '~icons/material-symbols/rss-feed'; + +type LinkIcon = Component | string; + // TODO: чашки на иконках выглядят страшненько, пока что пусть лучше будет голая ссылка -const icons: Record = { - none: 'material-symbols:link', - 'steamcommunity.com': 'simple-icons:steam', - 'steampowered.com': 'simple-icons:steam', - 't.me': 'simple-icons:telegram', - 'twitter.com': 'simple-icons:x', - 'x.com': 'simple-icons:x', - 'github.com': 'simple-icons:github', - 'youtube.com': 'simple-icons:youtube', - 'itch.io': 'simple-icons:itchdotio', - 'discord.com': 'simple-icons:discord', - 'discord.gg': 'simple-icons:discord', - 'gamebanana.com': 'simple-icons:gamebanana', - 'bsky.app': 'simple-icons:bluesky', - 'bsky.social': 'simple-icons:bluesky', +const icons: Record = { + none: DefaultLinkIcon, + 'steamcommunity.com': SteamIcon, + 'steampowered.com': SteamIcon, + 't.me': TelegramIcon, + 'twitter.com': TwitterIcon, + 'x.com': TwitterIcon, + 'github.com': GitHubIcon, + 'youtube.com': YouTubeIcon, + 'itch.io': ItchIoIcon, + 'discord.com': DiscordIcon, + 'discord.gg': DiscordIcon, + 'gamebanana.com': GameBananaIcon, + 'bsky.app': BlueSkyIcon, + 'bsky.social': BlueSkyIcon, // https://хамяк.рф - 'xn--80auf8a2c.xn--p1ai': 'fluent-emoji-high-contrast:hamster', + 'xn--80auf8a2c.xn--p1ai': HamsterIcon, // 'teasanctuary.ru': '/icons/tea-sanctuary-white.svg', 'hl.teasanctuary.ru': '/icons/half-life.svg', - 'git.teasanctuary.ru': 'devicon-plain:git', + 'git.teasanctuary.ru': GitIcon, // localhost: '/icons/tea-sanctuary-white.svg', - email: 'material-symbols:alternate-email', - rss: 'material-symbols:rss-feed' + email: EmailIcon, + rss: RssIcon }; // Особые случаи, когда одним доменом второго уровня не ограничишься (например, randomtrash.itch.io) @@ -51,7 +71,9 @@ const specialResolvers: Record string> = { 'steampowered.com': (url) => 'steampowered.com', } -function getIconFromUrl(url: URL): string | undefined { +function getIconNameFromUrl(url?: URL): string | undefined { + if (!url) return undefined; + const href = url.href; if (href.startsWith('mailto:')) return 'email'; @@ -66,15 +88,16 @@ function getIconFromUrl(url: URL): string | undefined { return hostname; } -export function tryGetIcon(link: string): string { +const baseURI = browser ? document.baseURI : 'https://teasanctuary.ru'; +export function tryGetIcon(link: string): LinkIcon { let url: URL; try { - url = new URL(link, document.baseURI); + url = new URL(link, baseURI); } catch { return icons['none']; } - return icons[getIconFromUrl(url) ?? ''] ?? icons['none']; + return icons[getIconNameFromUrl(url) ?? ''] ?? icons['none']; } /** diff --git a/src/routes/+layout.svelte b/src/routes/+layout.svelte index 178b482..41b8d1c 100644 --- a/src/routes/+layout.svelte +++ b/src/routes/+layout.svelte @@ -3,13 +3,42 @@ import { page } from '$app/state'; import '$src/syntax-highlight.css'; // https://github.com/PrismJS/prism-themes import NavBar from '$lib/components/NavBar.svelte'; + import type { Snippet } from 'svelte'; + + import TeaIcon from '~icons/material-symbols/emoji-food-beverage'; + import TeamIcon from '~icons/material-symbols/groups'; + import BlogIcon from '~icons/material-symbols/newspaper'; + import ProjectsIcon from '~icons/material-symbols/work'; + import ContactsIcon from '~icons/material-symbols/chat'; + + let { children }: { children: Snippet } = $props(); const routes: App.Route[] = [ - { label: 'главная', icon: 'material-symbols:emoji-food-beverage', href: '/' }, - { label: 'команда', icon: 'material-symbols:groups', href: '/team' }, - { label: 'блог', icon: 'material-symbols:newspaper', href: '/blog' }, - { label: 'проекты', icon: 'material-symbols:work', href: '/projects' }, - { label: 'контакты', icon: 'material-symbols:chat', href: '/contact' } + { + label: 'главная', + icon: TeaIcon, + href: '/' + }, + { + label: 'команда', + icon: TeamIcon, + href: '/team' + }, + { + label: 'блог', + icon: BlogIcon, + href: '/blog' + }, + { + label: 'проекты', + icon: ProjectsIcon, + href: '/projects' + }, + { + label: 'контакты', + icon: ContactsIcon, + href: '/contact' + } ]; @@ -33,7 +62,7 @@
- + {@render children()}