From 66151b909cee05be5b33091564b7395834abe9f2 Mon Sep 17 00:00:00 2001 From: unknown Date: Thu, 29 Jun 2023 07:43:19 +0200 Subject: [PATCH] Edit prettier config --- .eslintrc.cjs | 86 +++---- .prettierrc | 17 +- package-lock.json | 366 +++++++++++++++++++++++++++ package.json | 103 ++++---- playwright.config.ts | 12 +- postcss.config.cjs | 12 +- src/app.d.ts | 6 +- src/app.html | 36 +-- src/index.d.ts | 176 ++++++------- src/index.test.ts | 6 +- src/lib/AI.ts | 250 +++++++++--------- src/lib/Doodad.ts | 48 ++-- src/lib/Item.ts | 166 ++++++------ src/lib/Level.ts | 416 +++++++++++++++--------------- src/lib/Npc.ts | 44 ++-- src/lib/Player.ts | 430 +++++++++++++++---------------- src/lib/animation.ts | 206 +++++++-------- src/lib/camera.ts | 12 +- src/lib/color.ts | 18 +- src/lib/dice.ts | 24 +- src/lib/fight.ts | 40 +-- src/lib/game.ts | 90 +++---- src/lib/grid.ts | 30 +-- src/lib/helpers.ts | 48 ++-- src/lib/maps/level-0.json | 520 +++++++++++++++++++------------------- src/lib/maps/level-1.json | 350 ++++++++++++------------- src/lib/scripts.ts | 178 ++++++------- src/stores/dialogs.ts | 52 ++-- src/stores/editor.ts | 24 +- src/stores/keyboard.ts | 28 +- src/stores/logs.ts | 2 +- src/stores/player.ts | 34 +-- src/stores/store.ts | 84 +++--- src/stores/textures.ts | 20 +- src/stores/ui.ts | 20 +- svelte.config.js | 34 +-- tailwind.config.cjs | 10 +- tests/test.ts | 4 +- tsconfig.json | 30 +-- vite.config.ts | 14 +- 40 files changed, 2208 insertions(+), 1838 deletions(-) diff --git a/.eslintrc.cjs b/.eslintrc.cjs index 643ec26..b2e172e 100644 --- a/.eslintrc.cjs +++ b/.eslintrc.cjs @@ -1,45 +1,45 @@ module.exports = { - root: true, - extends: [ - 'eslint:recommended', - 'plugin:@typescript-eslint/recommended', - 'plugin:@typescript-eslint/recommended-requiring-type-checking', - 'plugin:@typescript-eslint/strict', - 'plugin:svelte/recommended', - 'prettier' - ], - parser: '@typescript-eslint/parser', - plugins: ['@typescript-eslint'], - parserOptions: { - sourceType: 'module', - ecmaVersion: 2020, - extraFileExtensions: ['.svelte'], - project: ['./tsconfig.json'], - tsconfigRootDir: __dirname - }, - env: { - browser: true, - es2017: true, - node: true - }, - overrides: [ - { - files: ['*.svelte'], - parser: 'svelte-eslint-parser', - parserOptions: { - parser: '@typescript-eslint/parser' - } - } - ], - rules: { - 'no-unused-vars': 'off', - '@typescript-eslint/no-unused-vars': [ - 'warn', - { - argsIgnorePattern: '_', - varsIgnorePattern: '_', - caughtErrorsIgnorePattern: '_' - } - ] - } + root: true, + extends: [ + 'eslint:recommended', + 'plugin:@typescript-eslint/recommended', + 'plugin:@typescript-eslint/recommended-requiring-type-checking', + 'plugin:@typescript-eslint/strict', + 'plugin:svelte/recommended', + 'prettier' + ], + parser: '@typescript-eslint/parser', + plugins: ['@typescript-eslint'], + parserOptions: { + sourceType: 'module', + ecmaVersion: 2020, + extraFileExtensions: ['.svelte'], + project: ['./tsconfig.json'], + tsconfigRootDir: __dirname + }, + env: { + browser: true, + es2017: true, + node: true + }, + overrides: [ + { + files: ['*.svelte'], + parser: 'svelte-eslint-parser', + parserOptions: { + parser: '@typescript-eslint/parser' + } + } + ], + rules: { + 'no-unused-vars': 'off', + '@typescript-eslint/no-unused-vars': [ + 'warn', + { + argsIgnorePattern: '_', + varsIgnorePattern: '_', + caughtErrorsIgnorePattern: '_' + } + ] + } }; diff --git a/.prettierrc b/.prettierrc index a77fdde..4ad1054 100644 --- a/.prettierrc +++ b/.prettierrc @@ -1,9 +1,12 @@ { - "useTabs": true, - "singleQuote": true, - "trailingComma": "none", - "printWidth": 100, - "plugins": ["prettier-plugin-svelte"], - "pluginSearchDirs": ["."], - "overrides": [{ "files": "*.svelte", "options": { "parser": "svelte" } }] + "useTabs": false, + "singleQuote": true, + "trailingComma": "none", + "printWidth": 100, + "plugins": ["prettier-plugin-svelte"], + "pluginSearchDirs": ["."], + "overrides": [{ "files": "*.svelte", "options": { "parser": "svelte" } }], + "importOrder": ["^$components/(.*)$", "^$lib/(.*)$", "^$stores/(.*)$", "^[./]"], + "importOrderSeparation": true, + "importOrderSortSpecifiers": true } diff --git a/package-lock.json b/package-lock.json index ecb99ca..b20c887 100644 --- a/package-lock.json +++ b/package-lock.json @@ -17,6 +17,7 @@ "@sveltejs/kit": "^1.5.0", "@threlte/core": "^6.0.0-next.8", "@threlte/extras": "^5.0.0-next.13", + "@trivago/prettier-plugin-sort-imports": "^4.1.1", "@types/fast-astar": "^1.0.0", "@types/three": "^0.152.1", "@typescript-eslint/eslint-plugin": "^5.45.0", @@ -54,6 +55,315 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/@babel/code-frame": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.22.5.tgz", + "integrity": "sha512-Xmwn266vad+6DAqEB2A6V/CcZVp62BbwVmcOJc2RPuwih1kw02TjQvWVWlcKGbBPd+8/0V5DEkOcizRGYsspYQ==", + "dev": true, + "dependencies": { + "@babel/highlight": "^7.22.5" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/generator": { + "version": "7.17.7", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.17.7.tgz", + "integrity": "sha512-oLcVCTeIFadUoArDTwpluncplrYBmTCCZZgXCbgNGvOBBiSDDK3eWO4b/+eOTli5tKv1lg+a5/NAXg+nTcei1w==", + "dev": true, + "dependencies": { + "@babel/types": "^7.17.0", + "jsesc": "^2.5.1", + "source-map": "^0.5.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/generator/node_modules/source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha512-LbrmJOMUSdEVxIKvdcJzQC+nQhe8FUZQTXQy6+I75skNgn3OoQ0DZA8YnFa7gp8tqtL3KPf1kmo0R5DoApeSGQ==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/@babel/helper-environment-visitor": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/helper-environment-visitor/-/helper-environment-visitor-7.22.5.tgz", + "integrity": "sha512-XGmhECfVA/5sAt+H+xpSg0mfrHq6FzNr9Oxh7PSEBBRUb/mL7Kz3NICXb194rCqAEdxkhPT1a88teizAFyvk8Q==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-function-name": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.22.5.tgz", + "integrity": "sha512-wtHSq6jMRE3uF2otvfuD3DIvVhOsSNshQl0Qrd7qC9oQJzHvOL4qQXlQn2916+CXGywIjpGuIkoyZRRxHPiNQQ==", + "dev": true, + "dependencies": { + "@babel/template": "^7.22.5", + "@babel/types": "^7.22.5" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-function-name/node_modules/@babel/types": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.22.5.tgz", + "integrity": "sha512-zo3MIHGOkPOfoRXitsgHLjEXmlDaD/5KU1Uzuc9GNiZPhSqVxVRtxuPaSBZDsYZ9qV88AjtMtWW7ww98loJ9KA==", + "dev": true, + "dependencies": { + "@babel/helper-string-parser": "^7.22.5", + "@babel/helper-validator-identifier": "^7.22.5", + "to-fast-properties": "^2.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-hoist-variables": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/helper-hoist-variables/-/helper-hoist-variables-7.22.5.tgz", + "integrity": "sha512-wGjk9QZVzvknA6yKIUURb8zY3grXCcOZt+/7Wcy8O2uctxhplmUPkOdlgoNhmdVee2c92JXbf1xpMtVNbfoxRw==", + "dev": true, + "dependencies": { + "@babel/types": "^7.22.5" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-hoist-variables/node_modules/@babel/types": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.22.5.tgz", + "integrity": "sha512-zo3MIHGOkPOfoRXitsgHLjEXmlDaD/5KU1Uzuc9GNiZPhSqVxVRtxuPaSBZDsYZ9qV88AjtMtWW7ww98loJ9KA==", + "dev": true, + "dependencies": { + "@babel/helper-string-parser": "^7.22.5", + "@babel/helper-validator-identifier": "^7.22.5", + "to-fast-properties": "^2.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-split-export-declaration": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.22.5.tgz", + "integrity": "sha512-thqK5QFghPKWLhAV321lxF95yCg2K3Ob5yw+M3VHWfdia0IkPXUtoLH8x/6Fh486QUvzhb8YOWHChTVen2/PoQ==", + "dev": true, + "dependencies": { + "@babel/types": "^7.22.5" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-split-export-declaration/node_modules/@babel/types": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.22.5.tgz", + "integrity": "sha512-zo3MIHGOkPOfoRXitsgHLjEXmlDaD/5KU1Uzuc9GNiZPhSqVxVRtxuPaSBZDsYZ9qV88AjtMtWW7ww98loJ9KA==", + "dev": true, + "dependencies": { + "@babel/helper-string-parser": "^7.22.5", + "@babel/helper-validator-identifier": "^7.22.5", + "to-fast-properties": "^2.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-string-parser": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/helper-string-parser/-/helper-string-parser-7.22.5.tgz", + "integrity": "sha512-mM4COjgZox8U+JcXQwPijIZLElkgEpO5rsERVDJTc2qfCDfERyob6k5WegS14SX18IIjv+XD+GrqNumY5JRCDw==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-validator-identifier": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.22.5.tgz", + "integrity": "sha512-aJXu+6lErq8ltp+JhkJUfk1MTGyuA4v7f3pA+BJ5HLfNC6nAQ0Cpi9uOquUj8Hehg0aUiHzWQbOVJGao6ztBAQ==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/highlight": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.22.5.tgz", + "integrity": "sha512-BSKlD1hgnedS5XRnGOljZawtag7H1yPfQp0tdNJCHoH6AZ+Pcm9VvkrK59/Yy593Ypg0zMxH2BxD1VPYUQ7UIw==", + "dev": true, + "dependencies": { + "@babel/helper-validator-identifier": "^7.22.5", + "chalk": "^2.0.0", + "js-tokens": "^4.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/highlight/node_modules/ansi-styles": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", + "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dev": true, + "dependencies": { + "color-convert": "^1.9.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/highlight/node_modules/chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dev": true, + "dependencies": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/highlight/node_modules/color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dev": true, + "dependencies": { + "color-name": "1.1.3" + } + }, + "node_modules/@babel/highlight/node_modules/color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==", + "dev": true + }, + "node_modules/@babel/highlight/node_modules/escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "dev": true, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/@babel/highlight/node_modules/has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/highlight/node_modules/supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "dependencies": { + "has-flag": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/parser": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.22.5.tgz", + "integrity": "sha512-DFZMC9LJUG9PLOclRC32G63UXwzqS2koQC8dkx+PLdmt1xSePYpbT/NbsrJy8Q/muXz7o/h/d4A7Fuyixm559Q==", + "dev": true, + "bin": { + "parser": "bin/babel-parser.js" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@babel/template": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.22.5.tgz", + "integrity": "sha512-X7yV7eiwAxdj9k94NEylvbVHLiVG1nvzCV2EAowhxLTwODV1jl9UzZ48leOC0sH7OnuHrIkllaBgneUykIcZaw==", + "dev": true, + "dependencies": { + "@babel/code-frame": "^7.22.5", + "@babel/parser": "^7.22.5", + "@babel/types": "^7.22.5" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/template/node_modules/@babel/types": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.22.5.tgz", + "integrity": "sha512-zo3MIHGOkPOfoRXitsgHLjEXmlDaD/5KU1Uzuc9GNiZPhSqVxVRtxuPaSBZDsYZ9qV88AjtMtWW7ww98loJ9KA==", + "dev": true, + "dependencies": { + "@babel/helper-string-parser": "^7.22.5", + "@babel/helper-validator-identifier": "^7.22.5", + "to-fast-properties": "^2.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/traverse": { + "version": "7.17.3", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.17.3.tgz", + "integrity": "sha512-5irClVky7TxRWIRtxlh2WPUUOLhcPN06AGgaQSB8AEwuyEBgJVuJ5imdHm5zxk8w0QS5T+tDfnDxAlhWjpb7cw==", + "dev": true, + "dependencies": { + "@babel/code-frame": "^7.16.7", + "@babel/generator": "^7.17.3", + "@babel/helper-environment-visitor": "^7.16.7", + "@babel/helper-function-name": "^7.16.7", + "@babel/helper-hoist-variables": "^7.16.7", + "@babel/helper-split-export-declaration": "^7.16.7", + "@babel/parser": "^7.17.3", + "@babel/types": "^7.17.0", + "debug": "^4.1.0", + "globals": "^11.1.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/traverse/node_modules/globals": { + "version": "11.12.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz", + "integrity": "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/types": { + "version": "7.17.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.17.0.tgz", + "integrity": "sha512-TmKSNO4D5rzhL5bjWFcVHHLETzfQ/AmbKpKPOSjlP0WoHZ6L911fgoOKY4Alp/emzG4cHJdyN49zpgkbXFEHHw==", + "dev": true, + "dependencies": { + "@babel/helper-validator-identifier": "^7.16.7", + "to-fast-properties": "^2.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, "node_modules/@codemirror/autocomplete": { "version": "6.8.1", "resolved": "https://registry.npmjs.org/@codemirror/autocomplete/-/autocomplete-6.8.1.tgz", @@ -892,6 +1202,29 @@ "troika-three-text": "^0.46.4" } }, + "node_modules/@trivago/prettier-plugin-sort-imports": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/@trivago/prettier-plugin-sort-imports/-/prettier-plugin-sort-imports-4.1.1.tgz", + "integrity": "sha512-dQ2r2uzNr1x6pJsuh/8x0IRA3CBUB+pWEW3J/7N98axqt7SQSm+2fy0FLNXvXGg77xEDC7KHxJlHfLYyi7PDcw==", + "dev": true, + "dependencies": { + "@babel/generator": "7.17.7", + "@babel/parser": "^7.20.5", + "@babel/traverse": "7.17.3", + "@babel/types": "7.17.0", + "javascript-natural-sort": "0.7.1", + "lodash": "^4.17.21" + }, + "peerDependencies": { + "@vue/compiler-sfc": "3.x", + "prettier": "2.x" + }, + "peerDependenciesMeta": { + "@vue/compiler-sfc": { + "optional": true + } + } + }, "node_modules/@tweenjs/tween.js": { "version": "18.6.4", "resolved": "https://registry.npmjs.org/@tweenjs/tween.js/-/tween.js-18.6.4.tgz", @@ -2501,6 +2834,12 @@ "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", "dev": true }, + "node_modules/javascript-natural-sort": { + "version": "0.7.1", + "resolved": "https://registry.npmjs.org/javascript-natural-sort/-/javascript-natural-sort-0.7.1.tgz", + "integrity": "sha512-nO6jcEfZWQXDhOiBtG2KvKyEptz7RVbpGP4vTD2hLBdmNQSsCiicO2Ioinv6UI4y9ukqnBpy+XZ9H6uLNgJTlw==", + "dev": true + }, "node_modules/jiti": { "version": "1.18.2", "resolved": "https://registry.npmjs.org/jiti/-/jiti-1.18.2.tgz", @@ -2518,6 +2857,12 @@ "node": ">= 0.6.0" } }, + "node_modules/js-tokens": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", + "dev": true + }, "node_modules/js-yaml": { "version": "4.1.0", "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", @@ -2530,6 +2875,18 @@ "js-yaml": "bin/js-yaml.js" } }, + "node_modules/jsesc": { + "version": "2.5.2", + "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz", + "integrity": "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==", + "dev": true, + "bin": { + "jsesc": "bin/jsesc" + }, + "engines": { + "node": ">=4" + } + }, "node_modules/json-schema-traverse": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", @@ -4020,6 +4377,15 @@ "node": ">=14.0.0" } }, + "node_modules/to-fast-properties": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-2.0.0.tgz", + "integrity": "sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==", + "dev": true, + "engines": { + "node": ">=4" + } + }, "node_modules/to-regex-range": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", diff --git a/package.json b/package.json index 6082984..5716619 100644 --- a/package.json +++ b/package.json @@ -1,53 +1,54 @@ { - "name": "land-of-svelte", - "version": "0.0.1", - "private": true, - "scripts": { - "dev": "vite dev", - "build": "vite build", - "preview": "vite preview", - "test": "playwright test", - "check": "svelte-kit sync && svelte-check --tsconfig ./tsconfig.json", - "check:watch": "svelte-kit sync && svelte-check --tsconfig ./tsconfig.json --watch", - "test:unit": "vitest", - "lint": "prettier --plugin-search-dir ./src --check . && eslint .", - "lint:fix": "prettier --plugin-search-dir ./src --check . && eslint --fix .", - "format": "prettier --plugin-search-dir ./src --write .", - "all": "npm run format && npm run lint:fix" - }, - "devDependencies": { - "@playwright/test": "^1.28.1", - "@sveltejs/adapter-auto": "^2.0.0", - "@sveltejs/adapter-static": "^2.0.2", - "@sveltejs/kit": "^1.5.0", - "@threlte/core": "^6.0.0-next.8", - "@threlte/extras": "^5.0.0-next.13", - "@types/fast-astar": "^1.0.0", - "@types/three": "^0.152.1", - "@typescript-eslint/eslint-plugin": "^5.45.0", - "@typescript-eslint/parser": "^5.45.0", - "autoprefixer": "^10.4.14", - "eslint": "^8.28.0", - "eslint-config-prettier": "^8.5.0", - "eslint-plugin-svelte": "^2.26.0", - "fast-astar": "^1.0.6", - "postcss": "^8.4.23", - "postcss-load-config": "^4.0.1", - "prettier": "^2.8.0", - "prettier-plugin-svelte": "^2.8.1", - "svelte": "^3.54.0", - "svelte-check": "^3.0.1", - "svelte-cubed": "^0.2.1", - "svelte-preprocess": "^5.0.3", - "tailwindcss": "^3.3.1", - "three": "^0.152.2", - "tslib": "^2.4.1", - "typescript": "^5.0.0", - "vite": "^4.3.0", - "vitest": "^0.25.3" - }, - "type": "module", - "dependencies": { - "svelte-jsoneditor": "^0.17.7" - } + "name": "land-of-svelte", + "version": "0.0.1", + "private": true, + "scripts": { + "dev": "vite dev", + "build": "vite build", + "preview": "vite preview", + "test": "playwright test", + "check": "svelte-kit sync && svelte-check --tsconfig ./tsconfig.json", + "check:watch": "svelte-kit sync && svelte-check --tsconfig ./tsconfig.json --watch", + "test:unit": "vitest", + "lint": "prettier --plugin-search-dir ./src --check . && eslint .", + "lint:fix": "prettier --plugin-search-dir ./src --check . && eslint --fix .", + "format": "prettier --plugin-search-dir ./src --write .", + "all": "npm run format && npm run lint:fix" + }, + "devDependencies": { + "@playwright/test": "^1.28.1", + "@sveltejs/adapter-auto": "^2.0.0", + "@sveltejs/adapter-static": "^2.0.2", + "@sveltejs/kit": "^1.5.0", + "@threlte/core": "^6.0.0-next.8", + "@threlte/extras": "^5.0.0-next.13", + "@trivago/prettier-plugin-sort-imports": "^4.1.1", + "@types/fast-astar": "^1.0.0", + "@types/three": "^0.152.1", + "@typescript-eslint/eslint-plugin": "^5.45.0", + "@typescript-eslint/parser": "^5.45.0", + "autoprefixer": "^10.4.14", + "eslint": "^8.28.0", + "eslint-config-prettier": "^8.5.0", + "eslint-plugin-svelte": "^2.26.0", + "fast-astar": "^1.0.6", + "postcss": "^8.4.23", + "postcss-load-config": "^4.0.1", + "prettier": "^2.8.0", + "prettier-plugin-svelte": "^2.8.1", + "svelte": "^3.54.0", + "svelte-check": "^3.0.1", + "svelte-cubed": "^0.2.1", + "svelte-preprocess": "^5.0.3", + "tailwindcss": "^3.3.1", + "three": "^0.152.2", + "tslib": "^2.4.1", + "typescript": "^5.0.0", + "vite": "^4.3.0", + "vitest": "^0.25.3" + }, + "type": "module", + "dependencies": { + "svelte-jsoneditor": "^0.17.7" + } } diff --git a/playwright.config.ts b/playwright.config.ts index 1c5d7a1..62187d0 100644 --- a/playwright.config.ts +++ b/playwright.config.ts @@ -1,12 +1,12 @@ import type { PlaywrightTestConfig } from '@playwright/test'; const config: PlaywrightTestConfig = { - webServer: { - command: 'npm run build && npm run preview', - port: 4173 - }, - testDir: 'tests', - testMatch: /(.+\.)?(test|spec)\.[jt]s/ + webServer: { + command: 'npm run build && npm run preview', + port: 4173 + }, + testDir: 'tests', + testMatch: /(.+\.)?(test|spec)\.[jt]s/ }; export default config; diff --git a/postcss.config.cjs b/postcss.config.cjs index fe10e55..042ad89 100644 --- a/postcss.config.cjs +++ b/postcss.config.cjs @@ -2,12 +2,12 @@ const tailwindcss = require('tailwindcss'); const autoprefixer = require('autoprefixer'); const config = { - plugins: [ - //Some plugins, like tailwindcss/nesting, need to run before Tailwind, - tailwindcss(), - //But others, like autoprefixer, need to run after, - autoprefixer - ] + plugins: [ + //Some plugins, like tailwindcss/nesting, need to run before Tailwind, + tailwindcss(), + //But others, like autoprefixer, need to run after, + autoprefixer + ] }; module.exports = config; diff --git a/src/app.d.ts b/src/app.d.ts index d443b43..a513627 100644 --- a/src/app.d.ts +++ b/src/app.d.ts @@ -1,5 +1,5 @@ declare namespace svelteHTML { - interface HTMLAttributes { - 'on:clickoutside'?: CompositionEventHandler; - } + interface HTMLAttributes { + 'on:clickoutside'?: CompositionEventHandler; + } } diff --git a/src/app.html b/src/app.html index 5f9f1f5..32add11 100644 --- a/src/app.html +++ b/src/app.html @@ -1,21 +1,21 @@ - - Land of Svelte - - - - - %sveltekit.head% - - -
%sveltekit.body%
- + + Land of Svelte + + + + + %sveltekit.head% + + +
%sveltekit.body%
+ diff --git a/src/index.d.ts b/src/index.d.ts index b342284..ef035f7 100644 --- a/src/index.d.ts +++ b/src/index.d.ts @@ -5,148 +5,148 @@ export type Position2d = [number, number]; export type Map2d = number[][]; export type GameState = ( - | { - state: 'main' | 'control' | 'editor'; - running: 'newGame' | 'continue'; - } - | { - state: 'running' | 'inventory' | 'container'; - running: 'continue' | 'gameOver'; - } + | { + state: 'main' | 'control' | 'editor'; + running: 'newGame' | 'continue'; + } + | { + state: 'running' | 'inventory' | 'container'; + running: 'continue' | 'gameOver'; + } ) & { - isLoading: boolean; + isLoading: boolean; }; export interface Store { - game: GameState; - levels: Level[]; - currentLevelNumber: number; - screen: { - shaking: boolean; - dirty: boolean; - }; + game: GameState; + levels: Level[]; + currentLevelNumber: number; + screen: { + shaking: boolean; + dirty: boolean; + }; } export interface LevelProp { - width: number; - height: number; - floor: string; - ceiling: string; - collisionMap: Map2d; - textureMap: string[][]; - lights: Light[]; - scripts: Script[]; + width: number; + height: number; + floor: string; + ceiling: string; + collisionMap: Map2d; + textureMap: string[][]; + lights: Light[]; + scripts: Script[]; } export type DoodadName = 'door' | 'button' | 'ladder' | 'not-found'; export type Doodad = { - id: number; - type: DoodadName; - collision?: boolean; - texture: string[]; - color?: ColorRepresentation; - z?: number; + id: number; + type: DoodadName; + collision?: boolean; + texture: string[]; + color?: ColorRepresentation; + z?: number; } & OrientedPosition; export type NpcName = 'man' | 'not-found'; export type Npc = { - id: number; - type: 'npc'; - name: string; - collision?: boolean; - texture: string[]; - color?: number; + id: number; + type: 'npc'; + name: string; + collision?: boolean; + texture: string[]; + color?: number; } & OrientedPosition; export type AIName = 'orc' | 'gobelin' | 'not-found'; export type AIMode = 'idle' | 'attack-on-sight'; export type AI = { - id: number; - type: 'ai'; - name: string; - mode: AIMode; - collision?: boolean; - texture: string[]; - color?: number; - stats: Stats; - loot?: ItemName; - xp: number; + id: number; + type: 'ai'; + name: string; + mode: AIMode; + collision?: boolean; + texture: string[]; + color?: number; + stats: Stats; + loot?: ItemName; + xp: number; } & OrientedPosition; export type Panel = { - id: number; - type: 'panel'; - collision?: boolean; - texture: string[]; - color?: ColorRepresentation; - content: string[]; + id: number; + type: 'panel'; + collision?: boolean; + texture: string[]; + color?: ColorRepresentation; + content: string[]; } & OrientedPosition; export type Loot = { - id: number; - type: 'loot'; - name: ItemName; - texture: string[]; - collision?: boolean; - color?: ColorRepresentation; + id: number; + type: 'loot'; + name: ItemName; + texture: string[]; + collision?: boolean; + color?: ColorRepresentation; } & OrientedPosition; export type Container = { - id: number; - type: 'container'; - name: string; - texture: string[]; - collision?: boolean; - content: ItemName[]; + id: number; + type: 'container'; + name: string; + texture: string[]; + collision?: boolean; + content: ItemName[]; } & OrientedPosition; export type Script = Doodad | AI | Npc | Loot | Panel | Container; export interface OrientedPosition { - x: number; - y: number; - t: number; + x: number; + y: number; + t: number; } export interface Stats { - hp: number; - maxHp: number; - ac: number; - hit: number; - pDefense: number; - pAttack: number; + hp: number; + maxHp: number; + ac: number; + hit: number; + pDefense: number; + pAttack: number; } export interface Inventory { - mainHand: Item | null; - offHand: Item | null; - armor: Item | null; - bag: Item[]; + mainHand: Item | null; + offHand: Item | null; + armor: Item | null; + bag: Item[]; } type ItemName = 'sword' | 'shield' | 'armor' | 'key' | 'not-found'; export interface Item { - name: ItemName; - texture: string; - slot: 'mainHand' | 'offHand' | 'armor' | 'none'; - stats: Stats; - cooldown: number; - lastAttackTimestamp: number; + name: ItemName; + texture: string; + slot: 'mainHand' | 'offHand' | 'armor' | 'none'; + stats: Stats; + cooldown: number; + lastAttackTimestamp: number; } export interface UI { - weaponCooldownPercent: number; + weaponCooldownPercent: number; } export type Light = { id: number } & OrientedPosition; export type Tile = { - collision: boolean; - light?: Light; - texture: string; - script?: Script; + collision: boolean; + light?: Light; + texture: string; + script?: Script; } & OrientedPosition; diff --git a/src/index.test.ts b/src/index.test.ts index e07cbbd..701fbe0 100644 --- a/src/index.test.ts +++ b/src/index.test.ts @@ -1,7 +1,7 @@ import { describe, it, expect } from 'vitest'; describe('sum test', () => { - it('adds 1 + 2 to equal 3', () => { - expect(1 + 2).toBe(3); - }); + it('adds 1 + 2 to equal 3', () => { + expect(1 + 2).toBe(3); + }); }); diff --git a/src/lib/AI.ts b/src/lib/AI.ts index 1035ce6..3b502c1 100644 --- a/src/lib/AI.ts +++ b/src/lib/AI.ts @@ -7,142 +7,142 @@ import { logs } from '$stores/logs'; import type { Level } from './Level'; export const makeAI = function ( - aiName: AIName, - id: number, - x: number, - y: number, - loot: ItemName | undefined = undefined + aiName: AIName, + id: number, + x: number, + y: number, + loot: ItemName | undefined = undefined ): AI { - if (aiName === 'orc') { - return { - id: id, - type: 'ai', - name: aiName, - mode: 'attack-on-sight', - collision: true, - texture: ['orc-1'], - x: x, - y: y, - t: 0, - stats: { - hp: 5, - maxHp: 5, - ac: 0, - hit: 0, - pDefense: 0, - pAttack: 1 - }, - xp: 3, - loot: loot - }; - } + if (aiName === 'orc') { + return { + id: id, + type: 'ai', + name: aiName, + mode: 'attack-on-sight', + collision: true, + texture: ['orc-1'], + x: x, + y: y, + t: 0, + stats: { + hp: 5, + maxHp: 5, + ac: 0, + hit: 0, + pDefense: 0, + pAttack: 1 + }, + xp: 3, + loot: loot + }; + } - if (aiName === 'gobelin') { - return { - id: id, - type: 'ai', - name: aiName, - mode: 'attack-on-sight', - collision: true, - texture: [`${aiName}-idle`], - x: x, - y: y, - t: 0, - stats: { - hp: 3, - maxHp: 3, - ac: 0, - hit: 0, - pDefense: 0, - pAttack: 1 - }, - xp: 3, - loot: loot - }; - } + if (aiName === 'gobelin') { + return { + id: id, + type: 'ai', + name: aiName, + mode: 'attack-on-sight', + collision: true, + texture: [`${aiName}-idle`], + x: x, + y: y, + t: 0, + stats: { + hp: 3, + maxHp: 3, + ac: 0, + hit: 0, + pDefense: 0, + pAttack: 1 + }, + xp: 3, + loot: loot + }; + } - return { - id: 0, - type: 'ai', - name: 'not-found', - mode: 'idle', - collision: true, - texture: ['not-found'], - x: x, - y: y, - t: 0, - stats: { - hp: 1, - maxHp: 1, - ac: 0, - hit: 0, - pDefense: 0, - pAttack: 0 - }, - xp: 0 - }; + return { + id: 0, + type: 'ai', + name: 'not-found', + mode: 'idle', + collision: true, + texture: ['not-found'], + x: x, + y: y, + t: 0, + stats: { + hp: 1, + maxHp: 1, + ac: 0, + hit: 0, + pDefense: 0, + pAttack: 0 + }, + xp: 0 + }; }; export const advanceAi = (store: Store, level: Level) => (ai: AI) => { - if (ai.mode === 'idle') { - return; - } + if (ai.mode === 'idle') { + return; + } - // ai.mode === 'aggro' - const position = get(player).position; - const stats = get(player).stats; + // ai.mode === 'aggro' + const position = get(player).position; + const stats = get(player).stats; - const grid = makeAstar(level); - const nextPosition = grid.search([ai.x, ai.y], [position.x, position.y], { - rightAngle: true - }); + const grid = makeAstar(level); + const nextPosition = grid.search([ai.x, ai.y], [position.x, position.y], { + rightAngle: true + }); - // IDLE - if (!nextPosition || nextPosition.length >= 7) { - ai.texture = [`${ai.name}-idle`]; - level.replaceScript(ai); - return; - } + // IDLE + if (!nextPosition || nextPosition.length >= 7) { + ai.texture = [`${ai.name}-idle`]; + level.replaceScript(ai); + return; + } - // FOLLOW - if (nextPosition.length > 2) { - ai.x = nextPosition[1][0]; - ai.y = nextPosition[1][1]; - ai.texture = [`${ai.name}-aggro`]; + // FOLLOW + if (nextPosition.length > 2) { + ai.x = nextPosition[1][0]; + ai.y = nextPosition[1][1]; + ai.texture = [`${ai.name}-aggro`]; - level.replaceScript(ai); - return; - } + level.replaceScript(ai); + return; + } - // ATTACK - const newPlayerStats = fight( - ai.stats, - stats, - () => { - logs.update((logs) => { - logs.push(`You dodged a hit`); - return logs; - }); - }, - (damage) => { - logs.update((logs) => { - logs.push(`You took ${damage} dmg`); - return logs; - }); - store.screen.shaking = true; - store.screen.dirty = true; - }, - () => { - logs.update((logs) => { - logs.push('Death!'); - return logs; - }); - store.game.running = 'gameOver'; - } - ); + // ATTACK + const newPlayerStats = fight( + ai.stats, + stats, + () => { + logs.update((logs) => { + logs.push(`You dodged a hit`); + return logs; + }); + }, + (damage) => { + logs.update((logs) => { + logs.push(`You took ${damage} dmg`); + return logs; + }); + store.screen.shaking = true; + store.screen.dirty = true; + }, + () => { + logs.update((logs) => { + logs.push('Death!'); + return logs; + }); + store.game.running = 'gameOver'; + } + ); - player.update((player) => { - player.stats = newPlayerStats; - return player; - }); + player.update((player) => { + player.stats = newPlayerStats; + return player; + }); }; diff --git a/src/lib/Doodad.ts b/src/lib/Doodad.ts index 5cc4831..56f45c1 100644 --- a/src/lib/Doodad.ts +++ b/src/lib/Doodad.ts @@ -1,30 +1,30 @@ import type { Doodad, DoodadName } from '..'; export const makeDoodad = function ( - doodadName: DoodadName, - id: number, - x: number, - y: number + doodadName: DoodadName, + id: number, + x: number, + y: number ): Doodad { - if (doodadName === 'door') { - return { - id, - type: 'door', - collision: true, - texture: ['door-0'], - x, - y, - t: 0 - }; - } + if (doodadName === 'door') { + return { + id, + type: 'door', + collision: true, + texture: ['door-0'], + x, + y, + t: 0 + }; + } - return { - id, - type: 'not-found', - collision: true, - texture: ['not-found'], - x, - y, - t: 0 - }; + return { + id, + type: 'not-found', + collision: true, + texture: ['not-found'], + x, + y, + t: 0 + }; }; diff --git a/src/lib/Item.ts b/src/lib/Item.ts index 28f5ef7..6946a1d 100644 --- a/src/lib/Item.ts +++ b/src/lib/Item.ts @@ -1,91 +1,91 @@ import type { Item, ItemName } from '..'; export const makeItem = function (itemName: ItemName): Item { - if (itemName === 'sword') { - return { - name: 'sword', - texture: 'sword-0', - slot: 'mainHand', - stats: { - hp: 0, - maxHp: 0, - ac: 0, - hit: 0, - pAttack: 1, - pDefense: 0 - }, - cooldown: 1, - lastAttackTimestamp: 0 - }; - } + if (itemName === 'sword') { + return { + name: 'sword', + texture: 'sword-0', + slot: 'mainHand', + stats: { + hp: 0, + maxHp: 0, + ac: 0, + hit: 0, + pAttack: 1, + pDefense: 0 + }, + cooldown: 1, + lastAttackTimestamp: 0 + }; + } - if (itemName === 'armor') { - return { - name: 'armor', - texture: 'armor-0', - slot: 'armor', - stats: { - hp: 0, - maxHp: 0, - ac: 2, - hit: 0, - pAttack: 0, - pDefense: 0 - }, - cooldown: 0, - lastAttackTimestamp: 0 - }; - } + if (itemName === 'armor') { + return { + name: 'armor', + texture: 'armor-0', + slot: 'armor', + stats: { + hp: 0, + maxHp: 0, + ac: 2, + hit: 0, + pAttack: 0, + pDefense: 0 + }, + cooldown: 0, + lastAttackTimestamp: 0 + }; + } - if (itemName === 'shield') { - return { - name: 'shield', - texture: 'shield-0', - slot: 'offHand', - stats: { - hp: 0, - maxHp: 0, - ac: 2, - hit: 0, - pAttack: 0, - pDefense: 0 - }, - cooldown: 0, - lastAttackTimestamp: 0 - }; - } + if (itemName === 'shield') { + return { + name: 'shield', + texture: 'shield-0', + slot: 'offHand', + stats: { + hp: 0, + maxHp: 0, + ac: 2, + hit: 0, + pAttack: 0, + pDefense: 0 + }, + cooldown: 0, + lastAttackTimestamp: 0 + }; + } - if (itemName === 'key') { - return { - name: 'key', - texture: 'key-0', - slot: 'none', - stats: { - hp: 0, - maxHp: 0, - ac: 0, - hit: 0, - pAttack: 0, - pDefense: 0 - }, - cooldown: 0, - lastAttackTimestamp: 0 - }; - } + if (itemName === 'key') { + return { + name: 'key', + texture: 'key-0', + slot: 'none', + stats: { + hp: 0, + maxHp: 0, + ac: 0, + hit: 0, + pAttack: 0, + pDefense: 0 + }, + cooldown: 0, + lastAttackTimestamp: 0 + }; + } - return { - name: 'not-found', - texture: 'not-found-0', - slot: 'armor', - stats: { - hp: 0, - maxHp: 0, - ac: 0, - hit: 0, - pAttack: 0, - pDefense: 0 - }, - cooldown: 0, - lastAttackTimestamp: 0 - }; + return { + name: 'not-found', + texture: 'not-found-0', + slot: 'armor', + stats: { + hp: 0, + maxHp: 0, + ac: 0, + hit: 0, + pAttack: 0, + pDefense: 0 + }, + cooldown: 0, + lastAttackTimestamp: 0 + }; }; diff --git a/src/lib/Level.ts b/src/lib/Level.ts index 0c3c3bd..fe0018f 100644 --- a/src/lib/Level.ts +++ b/src/lib/Level.ts @@ -1,216 +1,216 @@ import type { - AI, - Script, - LevelProp, - Map2d, - Store, - Loot, - OrientedPosition, - Light, - AIName, - DoodadName, - NpcName + AI, + Script, + LevelProp, + Map2d, + Store, + Loot, + OrientedPosition, + Light, + AIName, + DoodadName, + NpcName } from '..'; import { advanceAi, makeAI } from './AI'; import { makeDoodad } from './Doodad'; import { makeNpc } from './Npc'; export class Level { - width: number; - height: number; - floor: string; - ceiling: string; - collisionMap: Map2d; - textureMap: string[][]; - lights: Light[]; - scripts: Script[]; - - constructor(level: LevelProp) { - this.width = level.width; - this.height = level.height; - this.floor = level.floor; - this.ceiling = level.ceiling; - this.collisionMap = level.collisionMap; - this.textureMap = level.textureMap; - this.lights = level.lights; - this.scripts = level.scripts; - } - - resize(width: number, height: number): Level { - const level = new Level(this); - - level.width = width; - level.height = height; - - level.collisionMap = []; - level.textureMap = []; - - for (let x = 0; x < width; x++) { - if (!level.collisionMap[x]) { - level.collisionMap[x] = []; - } - - if (!level.textureMap[x]) { - level.textureMap[x] = []; - } - - for (let y = 0; y < height; y++) { - if (!level.collisionMap[x][y]) { - if (!this.collisionMap[x]?.[y]) { - level.collisionMap[x][y] = 0; - } else { - level.collisionMap[x][y] = this.collisionMap[x][y]; - } - } - - if (!level.textureMap[x][y]) { - if (!this.textureMap[x]?.[y]) { - level.textureMap[x][y] = 'wall-0'; - } else { - level.textureMap[x][y] = this.textureMap[x][y]; - } - } - } - } - - return level; - } - - getAis(): AI[] { - return this.scripts.filter((item) => { - return item.type === 'ai'; - }) as AI[]; - } - - getAiAt(x: number, y: number): AI | undefined { - return this.getAis().find((ai: AI) => { - return ai.x === x && ai.y === y; - }); - } - - addAiAt(x: number, y: number, aiName: AIName) { - const id = Math.max(...this.scripts.map((script) => script.id), 0) + 1; - this.scripts = [...this.scripts, makeAI(aiName, id, x, y)]; - } - - removeAiAt(x: number, y: number): void { - const loot = this.getAiAt(x, y)?.loot; - - if (loot) { - this.scripts.push({ - id: this.scripts.length, - type: 'loot', - name: loot, - collision: false, - texture: [`${loot}-0`], - x, - y, - t: 0 - }); - } - - this.scripts = this.scripts.filter((script: Script) => { - return !(script.x === x && script.y === y && script.type === 'ai'); - }); - } - - getLightAt(x: number, y: number): Light | undefined { - return this.lights.find((light: Light) => { - return light.x === x && light.y === y; - }); - } - - addLightAt(x: number, y: number): void { - const id = Math.max(...this.lights.map((light) => light.id), 0) + 1; - this.lights = [ - ...this.lights, - { - id, - x, - y, - t: 0 - } - ]; - } - - removeLightAt(x: number, y: number): void { - this.lights = this.lights.filter((light: Light) => { - return !(light.x === x && light.y === y); - }); - } - - getScriptAt(x: number, y: number): Script | undefined { - return this.scripts.find((script: Script) => { - return script.x === x && script.y === y; - }); - } - - removeScriptAt(x: number, y: number): void { - this.scripts = this.scripts.filter((script: Script) => { - return !(script.x === x && script.y === y); - }); - } - - addNpcAt(x: number, y: number, npcName: NpcName) { - const id = Math.max(...this.scripts.map((script) => script.id), 0) + 1; - this.scripts = [...this.scripts, makeNpc(npcName, id, x, y)]; - } - - addDoodadAt(x: number, y: number, doodadName: DoodadName): void { - const id = Math.max(...this.scripts.map((script) => script.id), 0) + 1; - this.scripts = [...this.scripts, makeDoodad(doodadName, id, x, y)]; - } - - getLoots(): Loot[] { - return this.scripts.filter((item) => { - return item.type === 'loot'; - }) as Loot[]; - } - - getWalls(): OrientedPosition[] { - const walls = []; - for (let i = 0; i < this.width; i++) { - for (let j = 0; j < this.height; j++) { - if (this.collisionMap[i][j] == 1) { - walls.push({ - x: i, - y: j, - t: 0 - }); - } - } - } - return walls; - } - - advance(store: Store): Store { - this.getAis().map(advanceAi(store, this)); - - store.levels[store.currentLevelNumber] = this; - - return store; - } - - getScript(scriptId: number): Script | null { - const scripts = this.scripts; - - let scriptFound = null; - scripts.forEach((script: Script) => { - if (script.id === scriptId) { - scriptFound = script; - } - }); - - return scriptFound; - } - - replaceScript(script: Script) { - this.scripts = this.scripts.map((oldScript) => { - if (oldScript.id === script.id) { - return script; - } - - return oldScript; - }); - } + width: number; + height: number; + floor: string; + ceiling: string; + collisionMap: Map2d; + textureMap: string[][]; + lights: Light[]; + scripts: Script[]; + + constructor(level: LevelProp) { + this.width = level.width; + this.height = level.height; + this.floor = level.floor; + this.ceiling = level.ceiling; + this.collisionMap = level.collisionMap; + this.textureMap = level.textureMap; + this.lights = level.lights; + this.scripts = level.scripts; + } + + resize(width: number, height: number): Level { + const level = new Level(this); + + level.width = width; + level.height = height; + + level.collisionMap = []; + level.textureMap = []; + + for (let x = 0; x < width; x++) { + if (!level.collisionMap[x]) { + level.collisionMap[x] = []; + } + + if (!level.textureMap[x]) { + level.textureMap[x] = []; + } + + for (let y = 0; y < height; y++) { + if (!level.collisionMap[x][y]) { + if (!this.collisionMap[x]?.[y]) { + level.collisionMap[x][y] = 0; + } else { + level.collisionMap[x][y] = this.collisionMap[x][y]; + } + } + + if (!level.textureMap[x][y]) { + if (!this.textureMap[x]?.[y]) { + level.textureMap[x][y] = 'wall-0'; + } else { + level.textureMap[x][y] = this.textureMap[x][y]; + } + } + } + } + + return level; + } + + getAis(): AI[] { + return this.scripts.filter((item) => { + return item.type === 'ai'; + }) as AI[]; + } + + getAiAt(x: number, y: number): AI | undefined { + return this.getAis().find((ai: AI) => { + return ai.x === x && ai.y === y; + }); + } + + addAiAt(x: number, y: number, aiName: AIName) { + const id = Math.max(...this.scripts.map((script) => script.id), 0) + 1; + this.scripts = [...this.scripts, makeAI(aiName, id, x, y)]; + } + + removeAiAt(x: number, y: number): void { + const loot = this.getAiAt(x, y)?.loot; + + if (loot) { + this.scripts.push({ + id: this.scripts.length, + type: 'loot', + name: loot, + collision: false, + texture: [`${loot}-0`], + x, + y, + t: 0 + }); + } + + this.scripts = this.scripts.filter((script: Script) => { + return !(script.x === x && script.y === y && script.type === 'ai'); + }); + } + + getLightAt(x: number, y: number): Light | undefined { + return this.lights.find((light: Light) => { + return light.x === x && light.y === y; + }); + } + + addLightAt(x: number, y: number): void { + const id = Math.max(...this.lights.map((light) => light.id), 0) + 1; + this.lights = [ + ...this.lights, + { + id, + x, + y, + t: 0 + } + ]; + } + + removeLightAt(x: number, y: number): void { + this.lights = this.lights.filter((light: Light) => { + return !(light.x === x && light.y === y); + }); + } + + getScriptAt(x: number, y: number): Script | undefined { + return this.scripts.find((script: Script) => { + return script.x === x && script.y === y; + }); + } + + removeScriptAt(x: number, y: number): void { + this.scripts = this.scripts.filter((script: Script) => { + return !(script.x === x && script.y === y); + }); + } + + addNpcAt(x: number, y: number, npcName: NpcName) { + const id = Math.max(...this.scripts.map((script) => script.id), 0) + 1; + this.scripts = [...this.scripts, makeNpc(npcName, id, x, y)]; + } + + addDoodadAt(x: number, y: number, doodadName: DoodadName): void { + const id = Math.max(...this.scripts.map((script) => script.id), 0) + 1; + this.scripts = [...this.scripts, makeDoodad(doodadName, id, x, y)]; + } + + getLoots(): Loot[] { + return this.scripts.filter((item) => { + return item.type === 'loot'; + }) as Loot[]; + } + + getWalls(): OrientedPosition[] { + const walls = []; + for (let i = 0; i < this.width; i++) { + for (let j = 0; j < this.height; j++) { + if (this.collisionMap[i][j] == 1) { + walls.push({ + x: i, + y: j, + t: 0 + }); + } + } + } + return walls; + } + + advance(store: Store): Store { + this.getAis().map(advanceAi(store, this)); + + store.levels[store.currentLevelNumber] = this; + + return store; + } + + getScript(scriptId: number): Script | null { + const scripts = this.scripts; + + let scriptFound = null; + scripts.forEach((script: Script) => { + if (script.id === scriptId) { + scriptFound = script; + } + }); + + return scriptFound; + } + + replaceScript(script: Script) { + this.scripts = this.scripts.map((oldScript) => { + if (oldScript.id === script.id) { + return script; + } + + return oldScript; + }); + } } diff --git a/src/lib/Npc.ts b/src/lib/Npc.ts index 98004d0..67bc04e 100644 --- a/src/lib/Npc.ts +++ b/src/lib/Npc.ts @@ -1,27 +1,27 @@ import type { Npc, NpcName } from '..'; export const makeNpc = function (npcName: NpcName, id: number, x: number, y: number): Npc { - if (npcName === 'man') { - return { - id: id, - type: 'npc', - name: npcName, - collision: true, - texture: ['npc-1'], - x: x, - y: y, - t: 0 - }; - } + if (npcName === 'man') { + return { + id: id, + type: 'npc', + name: npcName, + collision: true, + texture: ['npc-1'], + x: x, + y: y, + t: 0 + }; + } - return { - id: id, - type: 'npc', - name: 'not-found', - collision: true, - texture: ['npc-1'], - x: x, - y: y, - t: 0 - }; + return { + id: id, + type: 'npc', + name: 'not-found', + collision: true, + texture: ['npc-1'], + x: x, + y: y, + t: 0 + }; }; diff --git a/src/lib/Player.ts b/src/lib/Player.ts index 6b300bd..22026bb 100644 --- a/src/lib/Player.ts +++ b/src/lib/Player.ts @@ -6,219 +6,219 @@ import { store } from '$stores/store'; import { player } from '$stores/player'; export class Player { - xp: number; - level: number; - position: OrientedPosition; - stats: Stats; - inventory: Inventory; - - constructor( - position: OrientedPosition, - stats: Stats, - inventory: Inventory, - xp: number, - level: number - ) { - this.position = position; - this.stats = stats; - this.inventory = inventory; - this.xp = xp; - this.level = level; - } - - moveForward(level: Level) { - const offsetX = Math.round(+Math.sin(this.position.t)); - const offsetY = Math.round(-Math.cos(this.position.t)); - - if (this.hasCollision(level, this.position.x + offsetX, this.position.y + offsetY)) { - return; - } - - this.position.x += offsetX; - this.position.y += offsetY; - } - - moveBackward(level: Level) { - const offsetX = Math.round(-Math.sin(this.position.t)); - const offsetY = Math.round(+Math.cos(this.position.t)); - - if (this.hasCollision(level, this.position.x + offsetX, this.position.y + offsetY)) { - return; - } - - this.position.x += offsetX; - this.position.y += offsetY; - } - - moveLeft(level: Level) { - const offsetX = Math.round(-Math.cos(this.position.t)); - const offsetY = Math.round(-Math.sin(this.position.t)); - - if (this.hasCollision(level, this.position.x + offsetX, this.position.y + offsetY)) { - return; - } - - this.position.x += offsetX; - this.position.y += offsetY; - } - - moveRight(level: Level) { - const offsetX = Math.round(+Math.cos(this.position.t)); - const offsetY = Math.round(+Math.sin(this.position.t)); - if (this.hasCollision(level, this.position.x + offsetX, this.position.y + offsetY)) { - return; - } - - this.position.x += offsetX; - this.position.y += offsetY; - } - - rotateLeft() { - this.position.t -= Math.PI / 2; - } - - rotateRight() { - this.position.t += Math.PI / 2; - } - - hasCollision(level: Level, x: number, y: number): boolean { - if (level.collisionMap[x][y]) { - return true; - } - - let collide = false; - level.scripts.forEach((script) => { - if (script.collision && script.x == x && script.y == y) { - collide = true; - } - }); - - return collide; - } - - attack(): void { - const offsetX = Math.round(+Math.sin(this.position.t)); - const offsetY = Math.round(-Math.cos(this.position.t)); - - store.update((store) => { - const weapon = this.inventory.mainHand; - - if (!weapon) { - return store; - } - - if (Date.now() - weapon.lastAttackTimestamp < weapon.cooldown * 1e3) { - return store; - } - - weapon.lastAttackTimestamp = Date.now(); - - const ai = store.levels[store.currentLevelNumber].getAiAt( - this.position.x + offsetX, - this.position.y + offsetY - ); - - if (!ai) { - return store; - } - - const newAiStats = fight( - this.getStats(), - ai.stats, - () => { - logs.update((logs) => { - logs.push(`You missed a hit`); - return logs; - }); - }, - (damage) => { - logs.update((logs) => { - logs.push(`You hit for ${damage} dmg`); - return logs; - }); - ai.color = 0xff0000; - store.screen.dirty = true; - }, - () => { - logs.update((logs) => { - logs.push(`You killed a ${ai.name}`); - return logs; - }); - player.update((player) => { - player.xp += ai.xp; - return player; - }); - } - ); - - ai.stats = newAiStats; - - if (ai.stats.hp === 0) { - store.levels[store.currentLevelNumber].removeAiAt( - this.position.x + offsetX, - this.position.y + offsetY - ); - } - - return store; - }); - } - - getStats(): Stats { - return [this.inventory.mainHand, this.inventory.offHand, this.inventory.armor].reduce( - function (stats, item: Item | null) { - if (item) { - stats.hp += item.stats.hp; - stats.maxHp += item.stats.maxHp; - stats.ac += item.stats.ac; - stats.hit += item.stats.hit; - stats.pAttack += item.stats.pAttack; - stats.pDefense += item.stats.pDefense; - } - - return stats; - }, - { ...this.stats } - ); - } - - equip(item: Item, itemIndex: number): Inventory { - let oldItem = null; - - if (item.slot === 'none') { - return this.inventory; - } - - if (item.slot === 'mainHand') { - oldItem = this.inventory.mainHand; - } - if (item.slot === 'offHand') { - oldItem = this.inventory.offHand; - } - if (item.slot === 'armor') { - oldItem = this.inventory.armor; - } - - const inventory = { - mainHand: item.slot === 'mainHand' ? item : this.inventory.mainHand, - offHand: item.slot === 'offHand' ? item : this.inventory.offHand, - armor: item.slot === 'armor' ? item : this.inventory.armor, - bag: [...this.inventory.bag, oldItem].filter(Boolean) as Item[] - }; - - inventory.bag.splice(itemIndex, 1); - - return inventory; - } - - unequip(item: Item): Inventory { - const inventory = { - mainHand: item.slot === 'mainHand' ? null : this.inventory.mainHand, - offHand: item.slot === 'offHand' ? null : this.inventory.offHand, - armor: item.slot === 'armor' ? null : this.inventory.armor, - bag: [...this.inventory.bag, item] - }; - - return inventory; - } + xp: number; + level: number; + position: OrientedPosition; + stats: Stats; + inventory: Inventory; + + constructor( + position: OrientedPosition, + stats: Stats, + inventory: Inventory, + xp: number, + level: number + ) { + this.position = position; + this.stats = stats; + this.inventory = inventory; + this.xp = xp; + this.level = level; + } + + moveForward(level: Level) { + const offsetX = Math.round(+Math.sin(this.position.t)); + const offsetY = Math.round(-Math.cos(this.position.t)); + + if (this.hasCollision(level, this.position.x + offsetX, this.position.y + offsetY)) { + return; + } + + this.position.x += offsetX; + this.position.y += offsetY; + } + + moveBackward(level: Level) { + const offsetX = Math.round(-Math.sin(this.position.t)); + const offsetY = Math.round(+Math.cos(this.position.t)); + + if (this.hasCollision(level, this.position.x + offsetX, this.position.y + offsetY)) { + return; + } + + this.position.x += offsetX; + this.position.y += offsetY; + } + + moveLeft(level: Level) { + const offsetX = Math.round(-Math.cos(this.position.t)); + const offsetY = Math.round(-Math.sin(this.position.t)); + + if (this.hasCollision(level, this.position.x + offsetX, this.position.y + offsetY)) { + return; + } + + this.position.x += offsetX; + this.position.y += offsetY; + } + + moveRight(level: Level) { + const offsetX = Math.round(+Math.cos(this.position.t)); + const offsetY = Math.round(+Math.sin(this.position.t)); + if (this.hasCollision(level, this.position.x + offsetX, this.position.y + offsetY)) { + return; + } + + this.position.x += offsetX; + this.position.y += offsetY; + } + + rotateLeft() { + this.position.t -= Math.PI / 2; + } + + rotateRight() { + this.position.t += Math.PI / 2; + } + + hasCollision(level: Level, x: number, y: number): boolean { + if (level.collisionMap[x][y]) { + return true; + } + + let collide = false; + level.scripts.forEach((script) => { + if (script.collision && script.x == x && script.y == y) { + collide = true; + } + }); + + return collide; + } + + attack(): void { + const offsetX = Math.round(+Math.sin(this.position.t)); + const offsetY = Math.round(-Math.cos(this.position.t)); + + store.update((store) => { + const weapon = this.inventory.mainHand; + + if (!weapon) { + return store; + } + + if (Date.now() - weapon.lastAttackTimestamp < weapon.cooldown * 1e3) { + return store; + } + + weapon.lastAttackTimestamp = Date.now(); + + const ai = store.levels[store.currentLevelNumber].getAiAt( + this.position.x + offsetX, + this.position.y + offsetY + ); + + if (!ai) { + return store; + } + + const newAiStats = fight( + this.getStats(), + ai.stats, + () => { + logs.update((logs) => { + logs.push(`You missed a hit`); + return logs; + }); + }, + (damage) => { + logs.update((logs) => { + logs.push(`You hit for ${damage} dmg`); + return logs; + }); + ai.color = 0xff0000; + store.screen.dirty = true; + }, + () => { + logs.update((logs) => { + logs.push(`You killed a ${ai.name}`); + return logs; + }); + player.update((player) => { + player.xp += ai.xp; + return player; + }); + } + ); + + ai.stats = newAiStats; + + if (ai.stats.hp === 0) { + store.levels[store.currentLevelNumber].removeAiAt( + this.position.x + offsetX, + this.position.y + offsetY + ); + } + + return store; + }); + } + + getStats(): Stats { + return [this.inventory.mainHand, this.inventory.offHand, this.inventory.armor].reduce( + function (stats, item: Item | null) { + if (item) { + stats.hp += item.stats.hp; + stats.maxHp += item.stats.maxHp; + stats.ac += item.stats.ac; + stats.hit += item.stats.hit; + stats.pAttack += item.stats.pAttack; + stats.pDefense += item.stats.pDefense; + } + + return stats; + }, + { ...this.stats } + ); + } + + equip(item: Item, itemIndex: number): Inventory { + let oldItem = null; + + if (item.slot === 'none') { + return this.inventory; + } + + if (item.slot === 'mainHand') { + oldItem = this.inventory.mainHand; + } + if (item.slot === 'offHand') { + oldItem = this.inventory.offHand; + } + if (item.slot === 'armor') { + oldItem = this.inventory.armor; + } + + const inventory = { + mainHand: item.slot === 'mainHand' ? item : this.inventory.mainHand, + offHand: item.slot === 'offHand' ? item : this.inventory.offHand, + armor: item.slot === 'armor' ? item : this.inventory.armor, + bag: [...this.inventory.bag, oldItem].filter(Boolean) as Item[] + }; + + inventory.bag.splice(itemIndex, 1); + + return inventory; + } + + unequip(item: Item): Inventory { + const inventory = { + mainHand: item.slot === 'mainHand' ? null : this.inventory.mainHand, + offHand: item.slot === 'offHand' ? null : this.inventory.offHand, + armor: item.slot === 'armor' ? null : this.inventory.armor, + bag: [...this.inventory.bag, item] + }; + + return inventory; + } } diff --git a/src/lib/animation.ts b/src/lib/animation.ts index aa74b7b..d3e188d 100644 --- a/src/lib/animation.ts +++ b/src/lib/animation.ts @@ -1,116 +1,116 @@ type AnimationDirection = 'forward' | 'backward'; export const animate = (cb: (t: number) => void, duration: number) => { - let t = 0; - const start = Date.now(); - - const step = () => { - requestAnimationFrame(() => { - t = (Date.now() - start) / 1e3 / duration; - cb(Math.min(t, 1)); - if (t < duration) { - step(); - } - }); - }; - - step(); + let t = 0; + const start = Date.now(); + + const step = () => { + requestAnimationFrame(() => { + t = (Date.now() - start) / 1e3 / duration; + cb(Math.min(t, 1)); + if (t < duration) { + step(); + } + }); + }; + + step(); }; export const animateOnce = (cb: (t: number) => void, duration: number) => { - let called = false; - - return () => { - if (called) { - return; - } - - called = true; - - let t = 0; - const start = Date.now(); - - const step = () => { - requestAnimationFrame(() => { - t = (Date.now() - start) / 1e3 / duration; - cb(Math.min(t, 1)); - if (t < duration) { - step(); - } - }); - }; - - step(); - }; + let called = false; + + return () => { + if (called) { + return; + } + + called = true; + + let t = 0; + const start = Date.now(); + + const step = () => { + requestAnimationFrame(() => { + t = (Date.now() - start) / 1e3 / duration; + cb(Math.min(t, 1)); + if (t < duration) { + step(); + } + }); + }; + + step(); + }; }; export const animateToggle = (cb: (t: number) => void, duration: number) => { - let running = false; - - return () => { - if (running) { - return; - } - - running = true; - - let t = 0; - const start = Date.now(); - - const step = () => { - requestAnimationFrame(() => { - t = (Date.now() - start) / 1e3 / duration; - cb(Math.min(t, 1)); - if (t < duration) { - step(); - } - - if (t > duration) { - running = false; - } - }); - }; - - step(); - }; + let running = false; + + return () => { + if (running) { + return; + } + + running = true; + + let t = 0; + const start = Date.now(); + + const step = () => { + requestAnimationFrame(() => { + t = (Date.now() - start) / 1e3 / duration; + cb(Math.min(t, 1)); + if (t < duration) { + step(); + } + + if (t > duration) { + running = false; + } + }); + }; + + step(); + }; }; export const animateToggleReverse = (cb: (t: number) => void, duration: number) => { - let running = false; - let direction: AnimationDirection = 'forward'; - - return () => { - if (running) { - return; - } - - running = true; - - let t = 0; - const start = Date.now(); - - const step = () => { - requestAnimationFrame(() => { - if (direction == 'forward') { - t = (Date.now() - start) / 1e3 / duration; - } - if (direction == 'backward') { - t = 1 - (Date.now() - start) / 1e3 / duration; - } - - cb(Math.max(0, Math.min(t, 1))); - - if (t > 0 && t < duration) { - step(); - } - - if (t > duration || t <= 0) { - running = false; - direction = direction == 'forward' ? 'backward' : 'forward'; - } - }); - }; - - step(); - }; + let running = false; + let direction: AnimationDirection = 'forward'; + + return () => { + if (running) { + return; + } + + running = true; + + let t = 0; + const start = Date.now(); + + const step = () => { + requestAnimationFrame(() => { + if (direction == 'forward') { + t = (Date.now() - start) / 1e3 / duration; + } + if (direction == 'backward') { + t = 1 - (Date.now() - start) / 1e3 / duration; + } + + cb(Math.max(0, Math.min(t, 1))); + + if (t > 0 && t < duration) { + step(); + } + + if (t > duration || t <= 0) { + running = false; + direction = direction == 'forward' ? 'backward' : 'forward'; + } + }); + }; + + step(); + }; }; diff --git a/src/lib/camera.ts b/src/lib/camera.ts index da64b27..f19bdb5 100644 --- a/src/lib/camera.ts +++ b/src/lib/camera.ts @@ -2,10 +2,10 @@ import type { Writable } from 'svelte/store'; import type { OrientedPosition } from '..'; export const updateCamera = (camera: Writable, position: OrientedPosition): void => { - camera.update((camera) => { - camera.position.x = position.x - Math.sin(position.t) * 0.5; - camera.position.z = position.y + Math.cos(position.t) * 0.5; - camera.lookAt(position.x + Math.sin(position.t), 0, position.y - Math.cos(position.t)); - return camera; - }); + camera.update((camera) => { + camera.position.x = position.x - Math.sin(position.t) * 0.5; + camera.position.z = position.y + Math.cos(position.t) * 0.5; + camera.lookAt(position.x + Math.sin(position.t), 0, position.y - Math.cos(position.t)); + return camera; + }); }; diff --git a/src/lib/color.ts b/src/lib/color.ts index acdefa0..af0d539 100644 --- a/src/lib/color.ts +++ b/src/lib/color.ts @@ -7,16 +7,16 @@ const cache: ColorCache = {}; const undefinedColor = new THREE.Color(); export const colorCache = function (value: string | number | undefined): THREE.Color | undefined { - if (!value) { - return undefinedColor; - } + if (!value) { + return undefinedColor; + } - if (cache[value] != undefined) { - return cache[value]; - } + if (cache[value] != undefined) { + return cache[value]; + } - const colorRepresentation = new THREE.Color(value); - cache[value] = colorRepresentation; + const colorRepresentation = new THREE.Color(value); + cache[value] = colorRepresentation; - return colorRepresentation; + return colorRepresentation; }; diff --git a/src/lib/dice.ts b/src/lib/dice.ts index a18a289..db41bbd 100644 --- a/src/lib/dice.ts +++ b/src/lib/dice.ts @@ -1,19 +1,19 @@ export const dice = function (strings: TemplateStringsArray): number { - if (!strings.raw[0]) { - throw new Error('Empty dice'); - } + if (!strings.raw[0]) { + throw new Error('Empty dice'); + } - const raw = strings.raw[0]; + const raw = strings.raw[0]; - const matches = raw.match(/(\d+)+d(\d*)(\+(\d*))?/); + const matches = raw.match(/(\d+)+d(\d*)(\+(\d*))?/); - if (!matches) { - throw new Error(`Invalid match for ${raw}`); - } + if (!matches) { + throw new Error(`Invalid match for ${raw}`); + } - const multiple = Number(matches[1]); - const faces = 1 + ~~(Math.random() * Number(matches[2])); - const bonus = matches[4] ? Number(matches[4]) : 0; + const multiple = Number(matches[1]); + const faces = 1 + ~~(Math.random() * Number(matches[2])); + const bonus = matches[4] ? Number(matches[4]) : 0; - return multiple * faces + bonus; + return multiple * faces + bonus; }; diff --git a/src/lib/fight.ts b/src/lib/fight.ts index 7655875..25750e0 100644 --- a/src/lib/fight.ts +++ b/src/lib/fight.ts @@ -2,31 +2,31 @@ import type { Stats } from '..'; import { dice } from './dice'; export const fight = function ( - emitter: Stats, - receiver: Stats, - onMiss: () => void, - onDamage: (damage: number) => void, - onDeath: () => void + emitter: Stats, + receiver: Stats, + onMiss: () => void, + onDamage: (damage: number) => void, + onDeath: () => void ): Stats { - const newStats: Stats = { ...receiver }; + const newStats: Stats = { ...receiver }; - const hit = emitter.hit - receiver.ac + dice`1d6`; + const hit = emitter.hit - receiver.ac + dice`1d6`; - if (hit <= 0) { - onMiss(); - return newStats; - } + if (hit <= 0) { + onMiss(); + return newStats; + } - const damage = emitter.pAttack - receiver.pDefense; + const damage = emitter.pAttack - receiver.pDefense; - if (damage > 0) { - newStats.hp -= damage; - onDamage(damage); - } + if (damage > 0) { + newStats.hp -= damage; + onDamage(damage); + } - if (newStats.hp <= 0) { - onDeath(); - } + if (newStats.hp <= 0) { + onDeath(); + } - return newStats; + return newStats; }; diff --git a/src/lib/game.ts b/src/lib/game.ts index f2c13d9..a1e7cdd 100644 --- a/src/lib/game.ts +++ b/src/lib/game.ts @@ -4,63 +4,63 @@ import { useFrame } from '@threlte/core'; import { get } from 'svelte/store'; const advanceFrame = (t: number) => { - if (get(store).game.state !== 'running') { - return; - } + if (get(store).game.state !== 'running') { + return; + } - player.update((player) => { - return player; - }); + player.update((player) => { + return player; + }); - if (!get(store).screen.dirty && get(currentLevel).getLoots().length === 0) { - return; - } + if (!get(store).screen.dirty && get(currentLevel).getLoots().length === 0) { + return; + } - store.update((store) => { - // clear animation - store.screen.dirty = false; - store.screen.shaking = false; - store.levels[store.currentLevelNumber].getAis().map((ai) => { - ai.color = 0xffffff; - }); + store.update((store) => { + // clear animation + store.screen.dirty = false; + store.screen.shaking = false; + store.levels[store.currentLevelNumber].getAis().map((ai) => { + ai.color = 0xffffff; + }); - store.levels[store.currentLevelNumber].getLoots().map((loot) => { - loot.t = t * 1e-3; - }); + store.levels[store.currentLevelNumber].getLoots().map((loot) => { + loot.t = t * 1e-3; + }); - return store; - }); + return store; + }); }; const advanceGame = () => { - if (get(store).game.state !== 'running' || get(store).game.running === 'gameOver') { - return; - } + if (get(store).game.state !== 'running' || get(store).game.running === 'gameOver') { + return; + } - store.update((store) => { - const $currentLevel = store.levels[store.currentLevelNumber]; - store = $currentLevel.advance(store); - return store; - }); + store.update((store) => { + const $currentLevel = store.levels[store.currentLevelNumber]; + store = $currentLevel.advance(store); + return store; + }); }; export const gameTick = () => { - let t = 0; - let start = Date.now(); - const tickDuration = 1000; + let t = 0; + let start = Date.now(); + const tickDuration = 1000; - useFrame( - () => { - t = Date.now() - start; - advanceFrame(Date.now()); + useFrame( + () => { + t = Date.now() - start; + advanceFrame(Date.now()); - if (t > tickDuration) { - start = Date.now(); - advanceGame(); - } - }, - { - invalidate: false - } - ); + if (t > tickDuration) { + start = Date.now(); + advanceGame(); + } + }, + { + invalidate: false + } + ); }; diff --git a/src/lib/grid.ts b/src/lib/grid.ts index 25effe7..26dd6d8 100644 --- a/src/lib/grid.ts +++ b/src/lib/grid.ts @@ -2,22 +2,22 @@ import { Grid, Astar } from 'fast-astar'; import type { Level } from './Level'; export const makeAstar = (currentLevel: Level) => { - const grid = new Grid({ - col: currentLevel.width, - row: currentLevel.height - }); + const grid = new Grid({ + col: currentLevel.width, + row: currentLevel.height + }); - for (let i = 0; i < currentLevel.width; i++) { - for (let j = 0; j < currentLevel.height; j++) { - if (currentLevel.collisionMap[i][j]) { - grid.set([i, j], 'value', 1); - } - } - } + for (let i = 0; i < currentLevel.width; i++) { + for (let j = 0; j < currentLevel.height; j++) { + if (currentLevel.collisionMap[i][j]) { + grid.set([i, j], 'value', 1); + } + } + } - currentLevel.scripts.map((script) => { - grid.set([script.x, script.y], 'value', Number(script.collision) as 0 | 1); - }); + currentLevel.scripts.map((script) => { + grid.set([script.x, script.y], 'value', Number(script.collision) as 0 | 1); + }); - return new Astar(grid); + return new Astar(grid); }; diff --git a/src/lib/helpers.ts b/src/lib/helpers.ts index 18620cd..79becac 100644 --- a/src/lib/helpers.ts +++ b/src/lib/helpers.ts @@ -1,34 +1,34 @@ import type { Level } from './Level'; export const getClosestWall = function (level: Level, x: number, y: number) { - if (level.collisionMap[x + 1] && level.collisionMap[x + 1][y]) { - return 0; - } - if (level.collisionMap[x] && level.collisionMap[x][y + 1]) { - return Math.PI / 2; - } - if (level.collisionMap[x - 1] && level.collisionMap[x - 1][y]) { - return Math.PI; - } - if (level.collisionMap[x] && level.collisionMap[x][y - 1]) { - return Math.PI / 2 + Math.PI; - } + if (level.collisionMap[x + 1] && level.collisionMap[x + 1][y]) { + return 0; + } + if (level.collisionMap[x] && level.collisionMap[x][y + 1]) { + return Math.PI / 2; + } + if (level.collisionMap[x - 1] && level.collisionMap[x - 1][y]) { + return Math.PI; + } + if (level.collisionMap[x] && level.collisionMap[x][y - 1]) { + return Math.PI / 2 + Math.PI; + } - return 0; + return 0; }; export function clickOutside(node: HTMLElement) { - const handleClick = (event: Event) => { - if (!node.contains(event.target) && !event.defaultPrevented) { - node.dispatchEvent(new CustomEvent('clickoutside', node)); - } - }; + const handleClick = (event: Event) => { + if (!node.contains(event.target) && !event.defaultPrevented) { + node.dispatchEvent(new CustomEvent('clickoutside', node)); + } + }; - document.addEventListener('click', handleClick, true); + document.addEventListener('click', handleClick, true); - return { - destroy() { - document.removeEventListener('click', handleClick, true); - } - }; + return { + destroy() { + document.removeEventListener('click', handleClick, true); + } + }; } diff --git a/src/lib/maps/level-0.json b/src/lib/maps/level-0.json index 6b078a0..d871c7b 100644 --- a/src/lib/maps/level-0.json +++ b/src/lib/maps/level-0.json @@ -1,262 +1,262 @@ { - "width": 9, - "height": 12, - "floor": "floor-0", - "ceiling": "floor-1", - "collisionMap": [ - [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1], - [1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1], - [1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1], - [1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1], - [1, 1, 0, 1, 1, 0, 0, 0, 1, 1, 1, 1], - [1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1], - [1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1], - [1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1], - [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1] - ], - "textureMap": [ - [ - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-4", - "wall-0", - "wall-4", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-4", - "wall-4", - "wall-0" - ], - [ - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0" - ] - ], - "lights": [ - { - "id": 1, - "x": 2, - "y": 1 - }, - { - "id": 4, - "x": 2, - "y": 10, - "t": 0 - }, - { - "id": 5, - "x": 1, - "y": 6, - "t": 0 - }, - { - "id": 6, - "x": 6, - "y": 1, - "t": 0 - }, - { - "id": 7, - "x": 7, - "y": 9, - "t": 0 - } - ], - "scripts": [ - { - "id": 0, - "type": "door", - "collision": true, - "texture": ["door-0"], - "x": 2, - "y": 8 - }, - { - "id": 1, - "type": "button", - "collision": false, - "texture": [], - "color": "333333", - "x": 1, - "y": 9, - "t": 4.7123 - }, - { - "id": 2, - "type": "ladder", - "collision": false, - "texture": ["ladder-0", "ladder-1", "ladder-1", "ladder-1", "ladder-1", "ladder-1"], - "x": 1, - "y": 2 - }, - { - "id": 3, - "type": "ai", - "name": "gobelin", - "collision": true, - "texture": ["gobelin-idle"], - "x": 6, - "y": 2, - "t": 0, - "stats": { - "hp": 3, - "maxHp": 3, - "ac": 0, - "hit": 0, - "pDefense": 0, - "pAttack": 1 - }, - "xp": 3, - "loot": "key" - }, - { - "id": 4, - "type": "door", - "collision": true, - "texture": ["door-0"], - "x": 4, - "y": 2 - }, - { - "id": 5, - "type": "panel", - "collision": false, - "texture": ["panel-1", "panel-1", "panel-1", "panel-1", "panel-0", "panel-1"], - "x": 3, - "y": 9, - "t": 4.7123, - "content": ["Tips: Some items are clickable"] - }, - { - "id": 6, - "type": "container", - "name": "treasure chest", - "collision": true, - "texture": ["chest-1", "chest-1", "chest-1", "chest-1", "chest-0", "chest-1"], - "x": 6, - "y": 10, - "t": 1.5, - "content": ["sword"] - }, - { - "id": 7, - "type": "door", - "collision": true, - "texture": ["door-0"], - "x": 6, - "y": 4, - "t": 0 - } - ] + "width": 9, + "height": 12, + "floor": "floor-0", + "ceiling": "floor-1", + "collisionMap": [ + [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1], + [1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1], + [1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1], + [1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1], + [1, 1, 0, 1, 1, 0, 0, 0, 1, 1, 1, 1], + [1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1], + [1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1], + [1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1], + [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1] + ], + "textureMap": [ + [ + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-4", + "wall-0", + "wall-4", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-4", + "wall-4", + "wall-0" + ], + [ + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0" + ] + ], + "lights": [ + { + "id": 1, + "x": 2, + "y": 1 + }, + { + "id": 4, + "x": 2, + "y": 10, + "t": 0 + }, + { + "id": 5, + "x": 1, + "y": 6, + "t": 0 + }, + { + "id": 6, + "x": 6, + "y": 1, + "t": 0 + }, + { + "id": 7, + "x": 7, + "y": 9, + "t": 0 + } + ], + "scripts": [ + { + "id": 0, + "type": "door", + "collision": true, + "texture": ["door-0"], + "x": 2, + "y": 8 + }, + { + "id": 1, + "type": "button", + "collision": false, + "texture": [], + "color": "333333", + "x": 1, + "y": 9, + "t": 4.7123 + }, + { + "id": 2, + "type": "ladder", + "collision": false, + "texture": ["ladder-0", "ladder-1", "ladder-1", "ladder-1", "ladder-1", "ladder-1"], + "x": 1, + "y": 2 + }, + { + "id": 3, + "type": "ai", + "name": "gobelin", + "collision": true, + "texture": ["gobelin-idle"], + "x": 6, + "y": 2, + "t": 0, + "stats": { + "hp": 3, + "maxHp": 3, + "ac": 0, + "hit": 0, + "pDefense": 0, + "pAttack": 1 + }, + "xp": 3, + "loot": "key" + }, + { + "id": 4, + "type": "door", + "collision": true, + "texture": ["door-0"], + "x": 4, + "y": 2 + }, + { + "id": 5, + "type": "panel", + "collision": false, + "texture": ["panel-1", "panel-1", "panel-1", "panel-1", "panel-0", "panel-1"], + "x": 3, + "y": 9, + "t": 4.7123, + "content": ["Tips: Some items are clickable"] + }, + { + "id": 6, + "type": "container", + "name": "treasure chest", + "collision": true, + "texture": ["chest-1", "chest-1", "chest-1", "chest-1", "chest-0", "chest-1"], + "x": 6, + "y": 10, + "t": 1.5, + "content": ["sword"] + }, + { + "id": 7, + "type": "door", + "collision": true, + "texture": ["door-0"], + "x": 6, + "y": 4, + "t": 0 + } + ] } diff --git a/src/lib/maps/level-1.json b/src/lib/maps/level-1.json index 69a9179..64fd9eb 100644 --- a/src/lib/maps/level-1.json +++ b/src/lib/maps/level-1.json @@ -1,177 +1,177 @@ { - "width": 7, - "height": 12, - "floor": "floor-0", - "ceiling": "floor-1", - "collisionMap": [ - [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1], - [1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1], - [1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1], - [1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1], - [1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1], - [1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0], - [0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0] - ], - "textureMap": [ - [ - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-4", - "wall-0", - "wall-4", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-4", - "wall-0", - "wall-4", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-4", - "wall-4", - "wall-4", - "wall-0" - ], - [ - "wall-0", - "wall-4", - "wall-0", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0" - ], - [ - "wall-0", - "wall-4", - "wall-4", - "wall-4", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0", - "wall-0" - ] - ], - "lights": [ - { - "id": 0, - "x": 2, - "y": 1 - }, - { - "id": 1, - "x": 1, - "y": 6 - }, - { - "id": 3, - "x": 2, - "y": 10 - }, - { - "id": 4, - "x": 5, - "y": 2, - "t": 0 - } - ], - "scripts": [ - { - "id": 0, - "type": "ladder", - "collision": false, - "texture": ["ladder-1", "ladder-1", "ladder-1", "ladder-1", "ladder-1", "ladder-0"], - "x": 1, - "y": 2 - }, - { - "id": 1, - "type": "loot", - "name": "armor", - "collision": false, - "texture": ["armor-0"], - "x": 4, - "y": 5 - }, - { - "id": 2, - "type": "ai", - "name": "npc", - "mode": "idle", - "collision": true, - "texture": ["npc-1"], - "x": 5, - "y": 2, - "t": 0, - "stats": { - "hp": 20, - "maxHp": 20, - "ac": 20, - "hit": 0, - "pDefense": 20, - "pAttack": 0 - }, - "xp": 0 - } - ] + "width": 7, + "height": 12, + "floor": "floor-0", + "ceiling": "floor-1", + "collisionMap": [ + [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1], + [1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1], + [1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1], + [1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1], + [1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1], + [1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0], + [0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0] + ], + "textureMap": [ + [ + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-4", + "wall-0", + "wall-4", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-4", + "wall-0", + "wall-4", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-4", + "wall-4", + "wall-4", + "wall-0" + ], + [ + "wall-0", + "wall-4", + "wall-0", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0" + ], + [ + "wall-0", + "wall-4", + "wall-4", + "wall-4", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0", + "wall-0" + ] + ], + "lights": [ + { + "id": 0, + "x": 2, + "y": 1 + }, + { + "id": 1, + "x": 1, + "y": 6 + }, + { + "id": 3, + "x": 2, + "y": 10 + }, + { + "id": 4, + "x": 5, + "y": 2, + "t": 0 + } + ], + "scripts": [ + { + "id": 0, + "type": "ladder", + "collision": false, + "texture": ["ladder-1", "ladder-1", "ladder-1", "ladder-1", "ladder-1", "ladder-0"], + "x": 1, + "y": 2 + }, + { + "id": 1, + "type": "loot", + "name": "armor", + "collision": false, + "texture": ["armor-0"], + "x": 4, + "y": 5 + }, + { + "id": 2, + "type": "ai", + "name": "npc", + "mode": "idle", + "collision": true, + "texture": ["npc-1"], + "x": 5, + "y": 2, + "t": 0, + "stats": { + "hp": 20, + "maxHp": 20, + "ac": 20, + "hit": 0, + "pDefense": 20, + "pAttack": 0 + }, + "xp": 0 + } + ] } diff --git a/src/lib/scripts.ts b/src/lib/scripts.ts index 605a8d6..4a1966b 100644 --- a/src/lib/scripts.ts +++ b/src/lib/scripts.ts @@ -6,93 +6,93 @@ import { animateOnce, animateToggleReverse } from './animation'; import { store } from '$stores/store'; export const scripts = [ - [ - { - scriptId: 1, - predicate: () => true, - doClick: animateToggleReverse((t) => { - store.update((store) => { - const script = store.levels[0].getScript(0) as Doodad; - script.z = t * 1.01; - script.collision = true; - if (script.z > 1) { - script.collision = false; - } - store.levels[0].replaceScript(script); - return store; - }); - }, 1) - }, - { - scriptId: 4, - predicate: (): boolean => { - return get(player).inventory.bag.filter((item) => item.name === 'key').length > 0; - }, - doClick: animateOnce((t) => { - store.update((store) => { - const script = store.levels[0].getScript(4) as Doodad; - script.z = t * 1.01; - script.collision = true; - if (script.z > 1) { - script.collision = false; - player.update((player) => { - player.inventory.bag = player.inventory.bag.filter( - (item) => item.name !== 'key' - ); - return player; - }); - } - store.levels[0].replaceScript(script); - return store; - }); - }, 1) - }, - { - x: 1, - y: 2, - doWalk: () => { - store.update((store) => { - store.currentLevelNumber = 1; - return store; - }); - player.update((player) => { - player.position.t = Math.PI / 2; - return player; - }); - } - }, - { - x: 6, - y: 9, - predicate: () => true, - doWalk: animateOnce((t) => { - store.update((store) => { - const script = store.levels[0].getScript(7) as Doodad; - script.z = t * 1.01; - script.collision = true; - if (script.z > 1) { - script.collision = false; - } - store.levels[0].replaceScript(script); - return store; - }); - }, 1) - } - ], - [ - { - x: 1, - y: 2, - doWalk: () => { - store.update((store) => { - store.currentLevelNumber = 0; - return store; - }); - player.update((player) => { - player.position.t = Math.PI / 2; - return player; - }); - } - } - ] + [ + { + scriptId: 1, + predicate: () => true, + doClick: animateToggleReverse((t) => { + store.update((store) => { + const script = store.levels[0].getScript(0) as Doodad; + script.z = t * 1.01; + script.collision = true; + if (script.z > 1) { + script.collision = false; + } + store.levels[0].replaceScript(script); + return store; + }); + }, 1) + }, + { + scriptId: 4, + predicate: (): boolean => { + return get(player).inventory.bag.filter((item) => item.name === 'key').length > 0; + }, + doClick: animateOnce((t) => { + store.update((store) => { + const script = store.levels[0].getScript(4) as Doodad; + script.z = t * 1.01; + script.collision = true; + if (script.z > 1) { + script.collision = false; + player.update((player) => { + player.inventory.bag = player.inventory.bag.filter( + (item) => item.name !== 'key' + ); + return player; + }); + } + store.levels[0].replaceScript(script); + return store; + }); + }, 1) + }, + { + x: 1, + y: 2, + doWalk: () => { + store.update((store) => { + store.currentLevelNumber = 1; + return store; + }); + player.update((player) => { + player.position.t = Math.PI / 2; + return player; + }); + } + }, + { + x: 6, + y: 9, + predicate: () => true, + doWalk: animateOnce((t) => { + store.update((store) => { + const script = store.levels[0].getScript(7) as Doodad; + script.z = t * 1.01; + script.collision = true; + if (script.z > 1) { + script.collision = false; + } + store.levels[0].replaceScript(script); + return store; + }); + }, 1) + } + ], + [ + { + x: 1, + y: 2, + doWalk: () => { + store.update((store) => { + store.currentLevelNumber = 0; + return store; + }); + player.update((player) => { + player.position.t = Math.PI / 2; + return player; + }); + } + } + ] ]; diff --git a/src/stores/dialogs.ts b/src/stores/dialogs.ts index c554050..b570364 100644 --- a/src/stores/dialogs.ts +++ b/src/stores/dialogs.ts @@ -1,41 +1,41 @@ import { writable } from 'svelte/store'; interface Dialog { - title: string; - content: string; - dialogChoices: DialogChoice[]; + title: string; + content: string; + dialogChoices: DialogChoice[]; } interface DialogChoice { - content: string; - doAction?: () => void; + content: string; + doAction?: () => void; } const testDialog: Dialog = { - title: 'NPC Name ?', - content: 'Welcome adventurer, blabla', - dialogChoices: [] + title: 'NPC Name ?', + content: 'Welcome adventurer, blabla', + dialogChoices: [] }; const testDialog2: Dialog = { - title: 'NPC Name ?', - content: 'Welcome adventurer, blabla', - dialogChoices: [ - { - content: 'proceed', - doAction: () => { - console.log('ok'); - // to next step - } - }, - { - content: 'wait', - doAction: () => { - console.log('ok'); - // close dialog - } - } - ] + title: 'NPC Name ?', + content: 'Welcome adventurer, blabla', + dialogChoices: [ + { + content: 'proceed', + doAction: () => { + console.log('ok'); + // to next step + } + }, + { + content: 'wait', + doAction: () => { + console.log('ok'); + // close dialog + } + } + ] }; const level0Dialogs: Dialog[] = []; diff --git a/src/stores/editor.ts b/src/stores/editor.ts index 7bc826a..9adbb20 100644 --- a/src/stores/editor.ts +++ b/src/stores/editor.ts @@ -3,14 +3,14 @@ import { store } from './store'; import type { AIName, DoodadName, NpcName } from '..'; export type ToolName = - | 'texture' - | 'collision+' - | 'collision-' - | 'light' - | 'ai' - | 'npc' - | 'doodad' - | null; + | 'texture' + | 'collision+' + | 'collision-' + | 'light' + | 'ai' + | 'npc' + | 'doodad' + | null; export const activatedTool = writable(null); @@ -27,8 +27,8 @@ export const currentDoodad = writable('door'); export const currentLevelNumber = writable(0); export const currentLevel = derived( - [store, currentLevelNumber], - function ([store, currentLevelNumber]) { - return store.levels[currentLevelNumber]; - } + [store, currentLevelNumber], + function ([store, currentLevelNumber]) { + return store.levels[currentLevelNumber]; + } ); diff --git a/src/stores/keyboard.ts b/src/stores/keyboard.ts index 7dc72a4..b7fdfd6 100644 --- a/src/stores/keyboard.ts +++ b/src/stores/keyboard.ts @@ -1,23 +1,23 @@ import { writable } from 'svelte/store'; interface Keyboard { - forward: string; - backward: string; - left: string; - right: string; - rotateLeft: string; - rotateRight: string; - inventory: string; + forward: string; + backward: string; + left: string; + right: string; + rotateLeft: string; + rotateRight: string; + inventory: string; } export type Action = keyof Keyboard; export const keyboard = writable({ - forward: 'KeyW', - left: 'KeyA', - backward: 'KeyS', - right: 'KeyD', - rotateLeft: 'KeyQ', - rotateRight: 'KeyE', - inventory: 'KeyI' + forward: 'KeyW', + left: 'KeyA', + backward: 'KeyS', + right: 'KeyD', + rotateLeft: 'KeyQ', + rotateRight: 'KeyE', + inventory: 'KeyI' }); diff --git a/src/stores/logs.ts b/src/stores/logs.ts index bcdf5a7..9f1bad9 100644 --- a/src/stores/logs.ts +++ b/src/stores/logs.ts @@ -3,5 +3,5 @@ import { derived, writable } from 'svelte/store'; export const logs = writable(['Welcome to "Land of Svelte"']); export const lastLogs = derived(logs, (logs) => { - return logs.slice(-3); + return logs.slice(-3); }); diff --git a/src/stores/player.ts b/src/stores/player.ts index e93f793..7e2a039 100644 --- a/src/stores/player.ts +++ b/src/stores/player.ts @@ -2,23 +2,23 @@ import { Player } from '$lib/Player'; import { writable } from 'svelte/store'; const initialPlayer = new Player( - { x: 2, y: 10, t: 0 }, - { - hp: 10, - maxHp: 10, - ac: 3, - hit: 0, - pDefense: 0, - pAttack: 0 - }, - { - mainHand: null, - offHand: null, - armor: null, - bag: [] - }, - 0, - 1 + { x: 2, y: 10, t: 0 }, + { + hp: 10, + maxHp: 10, + ac: 3, + hit: 0, + pDefense: 0, + pAttack: 0 + }, + { + mainHand: null, + offHand: null, + armor: null, + bag: [] + }, + 0, + 1 ); export const player = writable(initialPlayer); diff --git a/src/stores/store.ts b/src/stores/store.ts index 462e57b..883c919 100644 --- a/src/stores/store.ts +++ b/src/stores/store.ts @@ -9,62 +9,62 @@ import type { LevelProp, Store } from '..'; type Route = 'main' | 'control' | 'editor' | 'running' | 'inventory' | 'container'; const initialStoreState: Store = { - game: { - state: 'main', - running: 'newGame', - isLoading: true - }, - levels: [new Level(level0 as LevelProp), new Level(level1 as LevelProp)], - currentLevelNumber: 0, - screen: { - shaking: false, - dirty: false - } + game: { + state: 'main', + running: 'newGame', + isLoading: true + }, + levels: [new Level(level0 as LevelProp), new Level(level1 as LevelProp)], + currentLevelNumber: 0, + screen: { + shaking: false, + dirty: false + } }; const createStore = () => { - const { subscribe, set, update } = writable(initialStoreState); + const { subscribe, set, update } = writable(initialStoreState); - const stack: Route[] = ['main']; + const stack: Route[] = ['main']; - const navigateTo = (target: Route): void => { - if (target === stack[stack.length - 1]) { - return; - } + const navigateTo = (target: Route): void => { + if (target === stack[stack.length - 1]) { + return; + } - stack.push(target); + stack.push(target); - update((store) => { - store.game.state = target; - return store; - }); - }; + update((store) => { + store.game.state = target; + return store; + }); + }; - const back = (): void => { - if (stack.length <= 1) { - return; - } + const back = (): void => { + if (stack.length <= 1) { + return; + } - stack.pop(); - const target = stack[stack.length - 1]; + stack.pop(); + const target = stack[stack.length - 1]; - update((store) => { - store.game.state = target; - return store; - }); - }; + update((store) => { + store.game.state = target; + return store; + }); + }; - return { - subscribe, - set, - update, - navigateTo, - back - }; + return { + subscribe, + set, + update, + navigateTo, + back + }; }; export const store = createStore(); export const currentLevel = derived(store, (store) => { - return store.levels[store.currentLevelNumber]; + return store.levels[store.currentLevelNumber]; }); diff --git a/src/stores/textures.ts b/src/stores/textures.ts index 809f9ca..bfed316 100644 --- a/src/stores/textures.ts +++ b/src/stores/textures.ts @@ -3,17 +3,17 @@ import { writable } from 'svelte/store'; type TextureMap = Record; const createTextures = () => { - const { subscribe, set, update } = writable({}); + const { subscribe, set, update } = writable({}); - return { - subscribe, - set, - setTexture: (name: string, texture: THREE.Texture) => - update((textures) => { - textures[name] = texture; - return textures; - }) - }; + return { + subscribe, + set, + setTexture: (name: string, texture: THREE.Texture) => + update((textures) => { + textures[name] = texture; + return textures; + }) + }; }; export const textures = createTextures(); diff --git a/src/stores/ui.ts b/src/stores/ui.ts index cd56822..b2852fb 100644 --- a/src/stores/ui.ts +++ b/src/stores/ui.ts @@ -3,16 +3,16 @@ import { player } from './player'; import type { UI } from '..'; export const ui = derived(player, function (player): UI { - const weapon = player.inventory.mainHand; + const weapon = player.inventory.mainHand; - if (weapon === null || weapon.lastAttackTimestamp === 0) { - return { - weaponCooldownPercent: 100 - }; - } + if (weapon === null || weapon.lastAttackTimestamp === 0) { + return { + weaponCooldownPercent: 100 + }; + } - return { - weaponCooldownPercent: - ((Date.now() - weapon.lastAttackTimestamp) / (weapon.cooldown * 1e3)) * 100 - }; + return { + weaponCooldownPercent: + ((Date.now() - weapon.lastAttackTimestamp) / (weapon.cooldown * 1e3)) * 100 + }; }); diff --git a/svelte.config.js b/svelte.config.js index 87ffda5..c97751a 100644 --- a/svelte.config.js +++ b/svelte.config.js @@ -4,24 +4,24 @@ import { vitePreprocess } from '@sveltejs/kit/vite'; /** @type {import('@sveltejs/kit').Config} */ const config = { - // Consult https://kit.svelte.dev/docs/integrations#preprocessors - // for more information about preprocessors - preprocess: [ - vitePreprocess(), - preprocess({ - postcss: true - }) - ], + // Consult https://kit.svelte.dev/docs/integrations#preprocessors + // for more information about preprocessors + preprocess: [ + vitePreprocess(), + preprocess({ + postcss: true + }) + ], - kit: { - // adapter-auto only supports some environments, see https://kit.svelte.dev/docs/adapter-auto for a list. - // If your environment is not supported or you settled on a specific environment, switch out the adapter. - // See https://kit.svelte.dev/docs/adapters for more information about adapters. - adapter: adapter(), - alias: { - '$stores/*': 'src/stores/*' - } - } + kit: { + // adapter-auto only supports some environments, see https://kit.svelte.dev/docs/adapter-auto for a list. + // If your environment is not supported or you settled on a specific environment, switch out the adapter. + // See https://kit.svelte.dev/docs/adapters for more information about adapters. + adapter: adapter(), + alias: { + '$stores/*': 'src/stores/*' + } + } }; export default config; diff --git a/tailwind.config.cjs b/tailwind.config.cjs index a2629b6..aac8bac 100644 --- a/tailwind.config.cjs +++ b/tailwind.config.cjs @@ -1,12 +1,12 @@ /** @type {import('tailwindcss').Config}*/ const config = { - content: ['./src/**/*.{html,js,svelte,ts}'], + content: ['./src/**/*.{html,js,svelte,ts}'], - theme: { - extend: {} - }, + theme: { + extend: {} + }, - plugins: [] + plugins: [] }; module.exports = config; diff --git a/tests/test.ts b/tests/test.ts index 5816be4..f9f3162 100644 --- a/tests/test.ts +++ b/tests/test.ts @@ -1,6 +1,6 @@ import { expect, test } from '@playwright/test'; test('index page has expected h1', async ({ page }) => { - await page.goto('/'); - await expect(page.getByRole('heading', { name: 'Welcome to SvelteKit' })).toBeVisible(); + await page.goto('/'); + await expect(page.getByRole('heading', { name: 'Welcome to SvelteKit' })).toBeVisible(); }); diff --git a/tsconfig.json b/tsconfig.json index 6ae0c8c..70401cc 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -1,17 +1,17 @@ { - "extends": "./.svelte-kit/tsconfig.json", - "compilerOptions": { - "allowJs": true, - "checkJs": true, - "esModuleInterop": true, - "forceConsistentCasingInFileNames": true, - "resolveJsonModule": true, - "skipLibCheck": true, - "sourceMap": true, - "strict": true - } - // Path aliases are handled by https://kit.svelte.dev/docs/configuration#alias - // - // If you want to overwrite includes/excludes, make sure to copy over the relevant includes/excludes - // from the referenced tsconfig.json - TypeScript does not merge them in + "extends": "./.svelte-kit/tsconfig.json", + "compilerOptions": { + "allowJs": true, + "checkJs": true, + "esModuleInterop": true, + "forceConsistentCasingInFileNames": true, + "resolveJsonModule": true, + "skipLibCheck": true, + "sourceMap": true, + "strict": true + } + // Path aliases are handled by https://kit.svelte.dev/docs/configuration#alias + // + // If you want to overwrite includes/excludes, make sure to copy over the relevant includes/excludes + // from the referenced tsconfig.json - TypeScript does not merge them in } diff --git a/vite.config.ts b/vite.config.ts index d946c52..25d22ae 100644 --- a/vite.config.ts +++ b/vite.config.ts @@ -2,11 +2,11 @@ import { sveltekit } from '@sveltejs/kit/vite'; import { defineConfig } from 'vitest/config'; export default defineConfig({ - plugins: [sveltekit()], - test: { - include: ['src/**/*.{test,spec}.{js,ts}'] - }, - ssr: { - noExternal: ['three'] - } + plugins: [sveltekit()], + test: { + include: ['src/**/*.{test,spec}.{js,ts}'] + }, + ssr: { + noExternal: ['three'] + } });