diff --git a/.eslintrc.json b/.eslintrc.json index b71322f7..44e6bd97 100644 --- a/.eslintrc.json +++ b/.eslintrc.json @@ -55,6 +55,8 @@ } ], "@typescript-eslint/no-empty-function": "error", + "@typescript-eslint/consistent-type-imports": "error", + "@typescript-eslint/consistent-type-exports": "error", "curly": "error", "dot-notation": "error", "no-caller": "error", diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 34b61972..3f14258d 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -16,9 +16,46 @@ on: workflow_call: jobs: + lint: + runs-on: [ubuntu-latest] + env: + CI: true + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-node@v4 + with: + node-version-file: '.nvmrc' + registry-url: 'https://registry.npmjs.org' + cache: npm + - run: npm ci + - name: Check formatting + run: npm run format + - name: Lint + run: npm run lint + build: runs-on: [ubuntu-latest] + env: + CI: true + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-node@v4 + with: + node-version-file: '.nvmrc' + registry-url: 'https://registry.npmjs.org' + cache: npm + - run: npm ci + - name: Build + run: npm run core && npm run build:esm + tests: + strategy: + fail-fast: false + matrix: + runner: [ubuntu-latest, windows-2025] + runs-on: ${{ matrix.runner }} + env: + CI: true steps: - uses: actions/checkout@v4 with: @@ -30,8 +67,17 @@ jobs: registry-url: 'https://registry.npmjs.org' cache: npm - run: npm ci - - run: npm run linux:ci + - uses: browser-actions/setup-chrome@v1 + with: + chrome-version: 133.0.6943.98 + # - name: Install Playwright browsers + # run: npx playwright install --with-deps + + - name: Tests + run: npm run test:ci -- --coverage=${{ matrix.runner == 'ubuntu-latest' }} + - name: Coveralls + if: ${{ matrix.runner == 'ubuntu-latest'}} uses: coverallsapp/github-action@v2.3.6 with: github-token: ${{ secrets.GITHUB_TOKEN }} diff --git a/.gitignore b/.gitignore index 16ec6d16..2c81dae9 100644 --- a/.gitignore +++ b/.gitignore @@ -52,3 +52,6 @@ obj/ *.suo *.map *.orig + +# Test outputs +__screenshots__ \ No newline at end of file diff --git a/karma.conf.browsers.js b/karma.conf.browsers.js index d18d166b..1ca89f5c 100644 --- a/karma.conf.browsers.js +++ b/karma.conf.browsers.js @@ -27,7 +27,7 @@ module.exports = (config) => { '/src/' : '/base/src/' }, files: [ - 'src/browsersupport/BrowserSupportSpec.ts', + 'src/spec/karma/BrowserSupportSpec.ts', ], mime: { 'text/x-typescript': ['ts', 'tsx'] }, preprocessors: { diff --git a/karma.conf.js b/karma.conf.js index 4c97d47e..a8c09f0f 100644 --- a/karma.conf.js +++ b/karma.conf.js @@ -107,20 +107,20 @@ module.exports = (config) => { '/src/': '/base/src/' }, files: [ - 'src/spec/_boot.ts', - { pattern: 'src/spec/images/**/*.mp3', included: false, served: true }, - { pattern: 'src/spec/images/**/*.ogg', included: false, served: true }, - { pattern: 'src/spec/images/**/*.svg', included: false, served: true }, - { pattern: 'src/spec/images/**/*.png', included: false, served: true }, - { pattern: 'src/spec/images/**/*.gif', included: false, served: true }, - { pattern: 'src/spec/images/**/*.txt', included: false, served: true }, - { pattern: 'src/spec/images/**/*.css', included: false, served: true }, - { pattern: 'src/spec/images/**/*.woff2', included: false, served: true }, - { pattern: 'src/spec/fonts/**/*.ttf', included: false, served: true } + 'src/spec/karma/_boot.ts', + { pattern: 'src/spec/assets/**/*.mp3', included: false, served: true }, + { pattern: 'src/spec/assets/**/*.ogg', included: false, served: true }, + { pattern: 'src/spec/assets/**/*.svg', included: false, served: true }, + { pattern: 'src/spec/assets/**/*.png', included: false, served: true }, + { pattern: 'src/spec/assets/**/*.gif', included: false, served: true }, + { pattern: 'src/spec/assets/**/*.txt', included: false, served: true }, + { pattern: 'src/spec/assets/**/*.css', included: false, served: true }, + { pattern: 'src/spec/assets/**/*.woff2', included: false, served: true }, + { pattern: 'src/spec/assets/fonts/**/*.ttf', included: false, served: true } ], mime: { 'text/x-typescript': ['ts', 'tsx'] }, preprocessors: { - './src/spec/_boot.ts': ['webpack'] + './src/spec/karma/_boot.ts': ['webpack'] }, webpack: { mode: 'none', diff --git a/package-lock.json b/package-lock.json index 8af25122..032503d4 100644 --- a/package-lock.json +++ b/package-lock.json @@ -25,6 +25,8 @@ "@types/webpack-env": "1.18.8", "@typescript-eslint/eslint-plugin": "7.18.0", "@typescript-eslint/parser": "7.18.0", + "@vitest/browser": "3.1.2", + "@vitest/coverage-istanbul": "3.1.2", "babel-loader": "9.2.1", "concurrently": "9.1.2", "copy-webpack-plugin": "12.0.2", @@ -53,6 +55,8 @@ "karma-summary-reporter": "3.1.1", "karma-webpack": "5.0.1", "lint-staged": "15.5.1", + "pixelmatch": "5.3.0", + "playwright": "1.50.1", "prettier": "3.2.5", "puppeteer": "15.5.0", "raw-loader": "4.0.2", @@ -70,6 +74,8 @@ "typedoc": "0.25.13", "typescript": "5.6.3", "url-loader": "4.1.1", + "vite": "6.2.0", + "vitest": "3.1.2", "webpack": "5.99.7", "webpack-cli": "5.1.4" } @@ -1953,6 +1959,23 @@ "node": ">=16" } }, + "node_modules/@esbuild/aix-ppc64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.25.0.tgz", + "integrity": "sha512-O7vun9Sf8DFjH2UtqK8Ku3LkquL9SZL8OLY1T5NZkA34+wG3OQF7cl4Ql8vdNzM6fzBbYfLaiRLIOZ+2FOCgBQ==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "aix" + ], + "engines": { + "node": ">=18" + } + }, "node_modules/@esbuild/android-arm": { "version": "0.18.20", "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.18.20.tgz", @@ -2225,6 +2248,23 @@ "node": ">=12" } }, + "node_modules/@esbuild/netbsd-arm64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-arm64/-/netbsd-arm64-0.25.0.tgz", + "integrity": "sha512-RuG4PSMPFfrkH6UwCAqBzauBWTygTvb1nxWasEJooGSJ/NwRw7b2HOwyRTQIU97Hq37l3npXoZGYMy3b3xYvPw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=18" + } + }, "node_modules/@esbuild/netbsd-x64": { "version": "0.18.20", "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.18.20.tgz", @@ -2242,6 +2282,23 @@ "node": ">=12" } }, + "node_modules/@esbuild/openbsd-arm64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-arm64/-/openbsd-arm64-0.25.0.tgz", + "integrity": "sha512-21sUNbq2r84YE+SJDfaQRvdgznTD8Xc0oc3p3iW/a1EVWeNj/SdUCbm5U0itZPQYRuRTW20fPMWMpcrciH2EJw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=18" + } + }, "node_modules/@esbuild/openbsd-x64": { "version": "0.18.20", "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.18.20.tgz", @@ -3088,6 +3145,13 @@ "node": ">=14" } }, + "node_modules/@polka/url": { + "version": "1.0.0-next.28", + "resolved": "https://registry.npmjs.org/@polka/url/-/url-1.0.0-next.28.tgz", + "integrity": "sha512-8LduaNlMZGwdZ6qWrKlfa+2M4gahzFkprZiAt2TF8uS0qQgBizKXpXURqvTJ4WtmupWxaLqjRb2UCTe72mu+Aw==", + "dev": true, + "license": "MIT" + }, "node_modules/@radix-ui/number": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/@radix-ui/number/-/number-1.0.1.tgz", @@ -4362,6 +4426,272 @@ "@babel/runtime": "^7.13.10" } }, + "node_modules/@rollup/rollup-android-arm-eabi": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.34.9.tgz", + "integrity": "sha512-qZdlImWXur0CFakn2BJ2znJOdqYZKiedEPEVNTBrpfPjc/YuTGcaYZcdmNFTkUj3DU0ZM/AElcM8Ybww3xVLzA==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@rollup/rollup-android-arm64": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.34.9.tgz", + "integrity": "sha512-4KW7P53h6HtJf5Y608T1ISKvNIYLWRKMvfnG0c44M6In4DQVU58HZFEVhWINDZKp7FZps98G3gxwC1sb0wXUUg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@rollup/rollup-darwin-arm64": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.34.9.tgz", + "integrity": "sha512-0CY3/K54slrzLDjOA7TOjN1NuLKERBgk9nY5V34mhmuu673YNb+7ghaDUs6N0ujXR7fz5XaS5Aa6d2TNxZd0OQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@rollup/rollup-darwin-x64": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.34.9.tgz", + "integrity": "sha512-eOojSEAi/acnsJVYRxnMkPFqcxSMFfrw7r2iD9Q32SGkb/Q9FpUY1UlAu1DH9T7j++gZ0lHjnm4OyH2vCI7l7Q==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@rollup/rollup-freebsd-arm64": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.34.9.tgz", + "integrity": "sha512-2lzjQPJbN5UnHm7bHIUKFMulGTQwdvOkouJDpPysJS+QFBGDJqcfh+CxxtG23Ik/9tEvnebQiylYoazFMAgrYw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ] + }, + "node_modules/@rollup/rollup-freebsd-x64": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.34.9.tgz", + "integrity": "sha512-SLl0hi2Ah2H7xQYd6Qaiu01kFPzQ+hqvdYSoOtHYg/zCIFs6t8sV95kaoqjzjFwuYQLtOI0RZre/Ke0nPaQV+g==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ] + }, + "node_modules/@rollup/rollup-linux-arm-gnueabihf": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.34.9.tgz", + "integrity": "sha512-88I+D3TeKItrw+Y/2ud4Tw0+3CxQ2kLgu3QvrogZ0OfkmX/DEppehus7L3TS2Q4lpB+hYyxhkQiYPJ6Mf5/dPg==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm-musleabihf": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.34.9.tgz", + "integrity": "sha512-3qyfWljSFHi9zH0KgtEPG4cBXHDFhwD8kwg6xLfHQ0IWuH9crp005GfoUUh/6w9/FWGBwEHg3lxK1iHRN1MFlA==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm64-gnu": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.34.9.tgz", + "integrity": "sha512-6TZjPHjKZUQKmVKMUowF3ewHxctrRR09eYyvT5eFv8w/fXarEra83A2mHTVJLA5xU91aCNOUnM+DWFMSbQ0Nxw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm64-musl": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.34.9.tgz", + "integrity": "sha512-LD2fytxZJZ6xzOKnMbIpgzFOuIKlxVOpiMAXawsAZ2mHBPEYOnLRK5TTEsID6z4eM23DuO88X0Tq1mErHMVq0A==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-loongarch64-gnu": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loongarch64-gnu/-/rollup-linux-loongarch64-gnu-4.34.9.tgz", + "integrity": "sha512-dRAgTfDsn0TE0HI6cmo13hemKpVHOEyeciGtvlBTkpx/F65kTvShtY/EVyZEIfxFkV5JJTuQ9tP5HGBS0hfxIg==", + "cpu": [ + "loong64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-powerpc64le-gnu": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-powerpc64le-gnu/-/rollup-linux-powerpc64le-gnu-4.34.9.tgz", + "integrity": "sha512-PHcNOAEhkoMSQtMf+rJofwisZqaU8iQ8EaSps58f5HYll9EAY5BSErCZ8qBDMVbq88h4UxaNPlbrKqfWP8RfJA==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-riscv64-gnu": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.34.9.tgz", + "integrity": "sha512-Z2i0Uy5G96KBYKjeQFKbbsB54xFOL5/y1P5wNBsbXB8yE+At3oh0DVMjQVzCJRJSfReiB2tX8T6HUFZ2k8iaKg==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-s390x-gnu": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.34.9.tgz", + "integrity": "sha512-U+5SwTMoeYXoDzJX5dhDTxRltSrIax8KWwfaaYcynuJw8mT33W7oOgz0a+AaXtGuvhzTr2tVKh5UO8GVANTxyQ==", + "cpu": [ + "s390x" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-x64-gnu": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.34.9.tgz", + "integrity": "sha512-FwBHNSOjUTQLP4MG7y6rR6qbGw4MFeQnIBrMe161QGaQoBQLqSUEKlHIiVgF3g/mb3lxlxzJOpIBhaP+C+KP2A==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-x64-musl": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.34.9.tgz", + "integrity": "sha512-cYRpV4650z2I3/s6+5/LONkjIz8MBeqrk+vPXV10ORBnshpn8S32bPqQ2Utv39jCiDcO2eJTuSlPXpnvmaIgRA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-win32-arm64-msvc": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.34.9.tgz", + "integrity": "sha512-z4mQK9dAN6byRA/vsSgQiPeuO63wdiDxZ9yg9iyX2QTzKuQM7T4xlBoeUP/J8uiFkqxkcWndWi+W7bXdPbt27Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-ia32-msvc": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.34.9.tgz", + "integrity": "sha512-KB48mPtaoHy1AwDNkAJfHXvHp24H0ryZog28spEs0V48l3H1fr4i37tiyHsgKZJnCmvxsbATdZGBpbmxTE3a9w==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-x64-msvc": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.34.9.tgz", + "integrity": "sha512-AyleYRPU7+rgkMWbEh71fQlrzRfeP6SyMnRf9XX4fCdDPAJumdSBqYEcWPMzVQ4ScAl7E4oFfK0GUVn77xSwbw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, "node_modules/@sinclair/typebox": { "version": "0.27.8", "resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.27.8.tgz", @@ -5840,6 +6170,47 @@ "@swc/counter": "^0.1.3" } }, + "node_modules/@testing-library/dom": { + "version": "10.4.0", + "resolved": "https://registry.npmjs.org/@testing-library/dom/-/dom-10.4.0.tgz", + "integrity": "sha512-pemlzrSESWbdAloYml3bAJMEfNh1Z7EduzqPKprCH5S341frlpYnUEW0H72dLxa6IsYr+mPno20GiSm+h9dEdQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@babel/code-frame": "^7.10.4", + "@babel/runtime": "^7.12.5", + "@types/aria-query": "^5.0.1", + "aria-query": "5.3.0", + "chalk": "^4.1.0", + "dom-accessibility-api": "^0.5.9", + "lz-string": "^1.5.0", + "pretty-format": "^27.0.2" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/@testing-library/user-event": { + "version": "14.6.1", + "resolved": "https://registry.npmjs.org/@testing-library/user-event/-/user-event-14.6.1.tgz", + "integrity": "sha512-vq7fv0rnt+QTXgPxr5Hjc210p6YKq2kmdziLgnsZGgLJ9e6VAShx1pACLuRjd/AS/sr7phAR58OIIpf0LlmQNw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12", + "npm": ">=6" + }, + "peerDependencies": { + "@testing-library/dom": ">=7.21.4" + } + }, + "node_modules/@types/aria-query": { + "version": "5.0.4", + "resolved": "https://registry.npmjs.org/@types/aria-query/-/aria-query-5.0.4.tgz", + "integrity": "sha512-rfT93uj5s0PRL7EzccGMs3brplhcrghnDoV26NqKhCAS1hVo+WdNsPvE/yb6ilfr5hi2MEk6d5EWJTKdxg8jVw==", + "dev": true, + "license": "MIT" + }, "node_modules/@types/babel__core": { "version": "7.20.5", "resolved": "https://registry.npmjs.org/@types/babel__core/-/babel__core-7.20.5.tgz", @@ -6512,23 +6883,298 @@ "dev": true, "license": "ISC" }, - "node_modules/@webassemblyjs/ast": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.14.1.tgz", - "integrity": "sha512-nuBEDgQfm1ccRp/8bCQrx1frohyufl4JlbMMZ4P1wpeOfDhF6FQkxZJ1b/e+PLwr6X1Nhw6OLme5usuBWYBvuQ==", + "node_modules/@vitest/browser": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@vitest/browser/-/browser-3.1.2.tgz", + "integrity": "sha512-dwL6hQg3NSDP3Z4xzIZL0xHq/AkQAPQ4StFpWVlY2zbRJtK3Y2YqdFZ7YmZjszTETN1BDQZRn/QOrcP+c8ATgg==", "dev": true, "license": "MIT", "dependencies": { - "@webassemblyjs/helper-numbers": "1.13.2", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2" + "@testing-library/dom": "^10.4.0", + "@testing-library/user-event": "^14.6.1", + "@vitest/mocker": "3.1.2", + "@vitest/utils": "3.1.2", + "magic-string": "^0.30.17", + "sirv": "^3.0.1", + "tinyrainbow": "^2.0.0", + "ws": "^8.18.1" + }, + "funding": { + "url": "https://opencollective.com/vitest" + }, + "peerDependencies": { + "playwright": "*", + "vitest": "3.1.2", + "webdriverio": "^7.0.0 || ^8.0.0 || ^9.0.0" + }, + "peerDependenciesMeta": { + "playwright": { + "optional": true + }, + "safaridriver": { + "optional": true + }, + "webdriverio": { + "optional": true + } } }, - "node_modules/@webassemblyjs/floating-point-hex-parser": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.13.2.tgz", - "integrity": "sha512-6oXyTOzbKxGH4steLbLNOu71Oj+C8Lg34n6CqRvqfS2O71BxY6ByfMDRhBytzknj9yGUPVJ1qIKhRlAwO1AovA==", + "node_modules/@vitest/browser/node_modules/ws": { + "version": "8.18.1", + "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.1.tgz", + "integrity": "sha512-RKW2aJZMXeMxVpnZ6bck+RswznaxmzdULiBr6KY7XkTnW8uvt0iT9H5DkHUChXrc+uurzwa0rVI16n/Xzjdz1w==", "dev": true, - "license": "MIT" + "license": "MIT", + "engines": { + "node": ">=10.0.0" + }, + "peerDependencies": { + "bufferutil": "^4.0.1", + "utf-8-validate": ">=5.0.2" + }, + "peerDependenciesMeta": { + "bufferutil": { + "optional": true + }, + "utf-8-validate": { + "optional": true + } + } + }, + "node_modules/@vitest/coverage-istanbul": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@vitest/coverage-istanbul/-/coverage-istanbul-3.1.2.tgz", + "integrity": "sha512-PXjSd4g7SxlC9WJ00jbMMFJob+LcjXUYow5vpXuZe/acjhlEQgCaf6npm+W9Mg/ahiFKtIAHI+P8A9n2JfZilg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@istanbuljs/schema": "^0.1.3", + "debug": "^4.4.0", + "istanbul-lib-coverage": "^3.2.2", + "istanbul-lib-instrument": "^6.0.3", + "istanbul-lib-report": "^3.0.1", + "istanbul-lib-source-maps": "^5.0.6", + "istanbul-reports": "^3.1.7", + "magicast": "^0.3.5", + "test-exclude": "^7.0.1", + "tinyrainbow": "^2.0.0" + }, + "funding": { + "url": "https://opencollective.com/vitest" + }, + "peerDependencies": { + "vitest": "3.1.2" + } + }, + "node_modules/@vitest/coverage-istanbul/node_modules/debug": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", + "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/@vitest/coverage-istanbul/node_modules/istanbul-lib-instrument": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-6.0.3.tgz", + "integrity": "sha512-Vtgk7L/R2JHyyGW07spoFlB8/lpjiOLTjMdms6AFMraYt3BaJauod/NGrfnVG/y4Ix1JEuMRPDPEj2ua+zz1/Q==", + "dev": true, + "license": "BSD-3-Clause", + "dependencies": { + "@babel/core": "^7.23.9", + "@babel/parser": "^7.23.9", + "@istanbuljs/schema": "^0.1.3", + "istanbul-lib-coverage": "^3.2.0", + "semver": "^7.5.4" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@vitest/coverage-istanbul/node_modules/istanbul-lib-source-maps": { + "version": "5.0.6", + "resolved": "https://registry.npmjs.org/istanbul-lib-source-maps/-/istanbul-lib-source-maps-5.0.6.tgz", + "integrity": "sha512-yg2d+Em4KizZC5niWhQaIomgf5WlL4vOOjZ5xGCmF8SnPE/mDWWXgvRExdcpCgh9lLRRa1/fSYp2ymmbJ1pI+A==", + "dev": true, + "license": "BSD-3-Clause", + "dependencies": { + "@jridgewell/trace-mapping": "^0.3.23", + "debug": "^4.1.1", + "istanbul-lib-coverage": "^3.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@vitest/coverage-istanbul/node_modules/test-exclude": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/test-exclude/-/test-exclude-7.0.1.tgz", + "integrity": "sha512-pFYqmTw68LXVjeWJMST4+borgQP2AyMNbg1BpZh9LbyhUeNkeaPF9gzfPGUAnSMV3qPYdWUwDIjjCLiSDOl7vg==", + "dev": true, + "license": "ISC", + "dependencies": { + "@istanbuljs/schema": "^0.1.2", + "glob": "^10.4.1", + "minimatch": "^9.0.4" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/@vitest/expect": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@vitest/expect/-/expect-3.1.2.tgz", + "integrity": "sha512-O8hJgr+zREopCAqWl3uCVaOdqJwZ9qaDwUP7vy3Xigad0phZe9APxKhPcDNqYYi0rX5oMvwJMSCAXY2afqeTSA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@vitest/spy": "3.1.2", + "@vitest/utils": "3.1.2", + "chai": "^5.2.0", + "tinyrainbow": "^2.0.0" + }, + "funding": { + "url": "https://opencollective.com/vitest" + } + }, + "node_modules/@vitest/mocker": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@vitest/mocker/-/mocker-3.1.2.tgz", + "integrity": "sha512-kOtd6K2lc7SQ0mBqYv/wdGedlqPdM/B38paPY+OwJ1XiNi44w3Fpog82UfOibmHaV9Wod18A09I9SCKLyDMqgw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@vitest/spy": "3.1.2", + "estree-walker": "^3.0.3", + "magic-string": "^0.30.17" + }, + "funding": { + "url": "https://opencollective.com/vitest" + }, + "peerDependencies": { + "msw": "^2.4.9", + "vite": "^5.0.0 || ^6.0.0" + }, + "peerDependenciesMeta": { + "msw": { + "optional": true + }, + "vite": { + "optional": true + } + } + }, + "node_modules/@vitest/pretty-format": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@vitest/pretty-format/-/pretty-format-3.1.2.tgz", + "integrity": "sha512-R0xAiHuWeDjTSB3kQ3OQpT8Rx3yhdOAIm/JM4axXxnG7Q/fS8XUwggv/A4xzbQA+drYRjzkMnpYnOGAc4oeq8w==", + "dev": true, + "license": "MIT", + "dependencies": { + "tinyrainbow": "^2.0.0" + }, + "funding": { + "url": "https://opencollective.com/vitest" + } + }, + "node_modules/@vitest/runner": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@vitest/runner/-/runner-3.1.2.tgz", + "integrity": "sha512-bhLib9l4xb4sUMPXnThbnhX2Yi8OutBMA8Yahxa7yavQsFDtwY/jrUZwpKp2XH9DhRFJIeytlyGpXCqZ65nR+g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@vitest/utils": "3.1.2", + "pathe": "^2.0.3" + }, + "funding": { + "url": "https://opencollective.com/vitest" + } + }, + "node_modules/@vitest/runner/node_modules/pathe": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/pathe/-/pathe-2.0.3.tgz", + "integrity": "sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==", + "dev": true, + "license": "MIT" + }, + "node_modules/@vitest/snapshot": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@vitest/snapshot/-/snapshot-3.1.2.tgz", + "integrity": "sha512-Q1qkpazSF/p4ApZg1vfZSQ5Yw6OCQxVMVrLjslbLFA1hMDrT2uxtqMaw8Tc/jy5DLka1sNs1Y7rBcftMiaSH/Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "@vitest/pretty-format": "3.1.2", + "magic-string": "^0.30.17", + "pathe": "^2.0.3" + }, + "funding": { + "url": "https://opencollective.com/vitest" + } + }, + "node_modules/@vitest/snapshot/node_modules/pathe": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/pathe/-/pathe-2.0.3.tgz", + "integrity": "sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==", + "dev": true, + "license": "MIT" + }, + "node_modules/@vitest/spy": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@vitest/spy/-/spy-3.1.2.tgz", + "integrity": "sha512-OEc5fSXMws6sHVe4kOFyDSj/+4MSwst0ib4un0DlcYgQvRuYQ0+M2HyqGaauUMnjq87tmUaMNDxKQx7wNfVqPA==", + "dev": true, + "license": "MIT", + "dependencies": { + "tinyspy": "^3.0.2" + }, + "funding": { + "url": "https://opencollective.com/vitest" + } + }, + "node_modules/@vitest/utils": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@vitest/utils/-/utils-3.1.2.tgz", + "integrity": "sha512-5GGd0ytZ7BH3H6JTj9Kw7Prn1Nbg0wZVrIvou+UWxm54d+WoXXgAgjFJ8wn3LdagWLFSEfpPeyYrByZaGEZHLg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@vitest/pretty-format": "3.1.2", + "loupe": "^3.1.3", + "tinyrainbow": "^2.0.0" + }, + "funding": { + "url": "https://opencollective.com/vitest" + } + }, + "node_modules/@webassemblyjs/ast": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.14.1.tgz", + "integrity": "sha512-nuBEDgQfm1ccRp/8bCQrx1frohyufl4JlbMMZ4P1wpeOfDhF6FQkxZJ1b/e+PLwr6X1Nhw6OLme5usuBWYBvuQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@webassemblyjs/helper-numbers": "1.13.2", + "@webassemblyjs/helper-wasm-bytecode": "1.13.2" + } + }, + "node_modules/@webassemblyjs/floating-point-hex-parser": { + "version": "1.13.2", + "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.13.2.tgz", + "integrity": "sha512-6oXyTOzbKxGH4steLbLNOu71Oj+C8Lg34n6CqRvqfS2O71BxY6ByfMDRhBytzknj9yGUPVJ1qIKhRlAwO1AovA==", + "dev": true, + "license": "MIT" }, "node_modules/@webassemblyjs/helper-api-error": { "version": "1.13.2", @@ -7146,6 +7792,16 @@ "node": ">=10" } }, + "node_modules/aria-query": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.3.0.tgz", + "integrity": "sha512-b0P0sZPKtyu8HkeRAfCq0IfURZK+SuwMjY1UXGBU27wpAiTwQAIlq56IbIO+ytk/JjS1fMR14ee5WBBfKi5J6A==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "dequal": "^2.0.3" + } + }, "node_modules/array-flatten": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", @@ -7204,6 +7860,16 @@ "node": ">=0.8" } }, + "node_modules/assertion-error": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/assertion-error/-/assertion-error-2.0.1.tgz", + "integrity": "sha512-Izi8RQcffqCeNVgFigKli1ssklIbpHnCYc6AknXGYoB6grJqyeby7jv12JUQgmTAnIDnbck1uxksT4dzN3PWBA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12" + } + }, "node_modules/ast-types": { "version": "0.16.1", "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.16.1.tgz", @@ -8184,6 +8850,16 @@ "node": ">= 0.8" } }, + "node_modules/cac": { + "version": "6.7.14", + "resolved": "https://registry.npmjs.org/cac/-/cac-6.7.14.tgz", + "integrity": "sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=8" + } + }, "node_modules/call-bind": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz", @@ -8273,6 +8949,23 @@ "dev": true, "license": "Apache-2.0" }, + "node_modules/chai": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/chai/-/chai-5.2.0.tgz", + "integrity": "sha512-mCuXncKXk5iCLhfhwTc0izo0gtEmpz5CtG2y8GiOINBlMVS6v8TMRc5TaLWKS6692m9+dVVfzgeVxR5UxWHTYw==", + "dev": true, + "license": "MIT", + "dependencies": { + "assertion-error": "^2.0.1", + "check-error": "^2.1.1", + "deep-eql": "^5.0.1", + "loupe": "^3.1.0", + "pathval": "^2.0.0" + }, + "engines": { + "node": ">=12" + } + }, "node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8306,6 +8999,16 @@ "url": "https://github.com/chalk/chalk-template?sponsor=1" } }, + "node_modules/check-error": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/check-error/-/check-error-2.1.1.tgz", + "integrity": "sha512-OAlb+T7V4Op9OwdkjmguYRqncdlx5JiofwOAUkmTF+jNdHwzTaTs4sRAGpzLF3oOz5xAyDGrPgeIDFQmDOTiJw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 16" + } + }, "node_modules/chokidar": { "version": "3.6.0", "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.6.0.tgz", @@ -9499,6 +10202,16 @@ "node": ">=10" } }, + "node_modules/cosmiconfig/node_modules/yaml": { + "version": "1.10.2", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz", + "integrity": "sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==", + "dev": true, + "license": "ISC", + "engines": { + "node": ">= 6" + } + }, "node_modules/coveralls": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/coveralls/-/coveralls-3.1.1.tgz", @@ -9728,6 +10441,16 @@ } } }, + "node_modules/deep-eql": { + "version": "5.0.2", + "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-5.0.2.tgz", + "integrity": "sha512-h5k/5U50IJJFpzfL6nO9jaaumfjO/f2NjK/oYB2Djzm4p9L+3T9qWpZqZ2hAbLPuuYq9wrU08WQyBTL5GbPk5Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/deep-extend": { "version": "0.6.0", "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", @@ -10169,6 +10892,13 @@ "node": ">=6.0.0" } }, + "node_modules/dom-accessibility-api": { + "version": "0.5.16", + "resolved": "https://registry.npmjs.org/dom-accessibility-api/-/dom-accessibility-api-0.5.16.tgz", + "integrity": "sha512-X7BJ2yElsnOJ30pZF4uIIDfBEVgF4XEBxL9Bxhy6dnrm5hkzqmsWHGTiHqRiITNhMyFLyAiWndIJP7Z1NTteDg==", + "dev": true, + "license": "MIT" + }, "node_modules/dom-converter": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/dom-converter/-/dom-converter-0.2.0.tgz", @@ -10591,9 +11321,9 @@ } }, "node_modules/es-module-lexer": { - "version": "1.5.4", - "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-1.5.4.tgz", - "integrity": "sha512-MVNK56NiMrOwitFB7cqDwq0CQutbw+0BvLshJSse0MUNU+y1FC3bUS/AQg7oUng+/wKrrki7JfmwtVHkVfPLlw==", + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-1.6.0.tgz", + "integrity": "sha512-qqnD1yMU6tk/jnaMosogGySTZP8YtUgAffA9nMN+E/rjxcfRQ6IEk7IiozUjgxKoFHBGjTLnrHB/YC45r/59EQ==", "dev": true, "license": "MIT" }, @@ -11243,6 +11973,16 @@ "node": ">=4.0" } }, + "node_modules/estree-walker": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-3.0.3.tgz", + "integrity": "sha512-7RUKfXgSMMkzt6ZuXmqapOurLGPPfgj6l9uRZ7lRGolvk0y2yocc35LdcxKC5PQZdn2DMqioAQ2NoWcrTKmm6g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/estree": "^1.0.0" + } + }, "node_modules/esutils": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", @@ -11341,6 +12081,16 @@ "url": "https://github.com/sindresorhus/execa?sponsor=1" } }, + "node_modules/expect-type": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/expect-type/-/expect-type-1.2.1.tgz", + "integrity": "sha512-/kP8CAwxzLVEeFrMm4kMmy4CCDlpipyA7MYLVrdJIkV0fYF0UaigQHRsxHiuY/GEea+bh4KSv3TIlgr+2UL6bw==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">=12.0.0" + } + }, "node_modules/express": { "version": "4.21.2", "resolved": "https://registry.npmjs.org/express/-/express-4.21.2.tgz", @@ -15222,6 +15972,13 @@ "loose-envify": "cli.js" } }, + "node_modules/loupe": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/loupe/-/loupe-3.1.3.tgz", + "integrity": "sha512-kkIp7XSkP78ZxJEsSxW3712C6teJVoeHHwgo9zJ380de7IYyJ2ISlxojcH2pC5OFLewESmnRi/+XCDIEEVyoug==", + "dev": true, + "license": "MIT" + }, "node_modules/lower-case": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/lower-case/-/lower-case-2.0.2.tgz", @@ -15249,16 +16006,38 @@ "dev": true, "license": "MIT" }, + "node_modules/lz-string": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/lz-string/-/lz-string-1.5.0.tgz", + "integrity": "sha512-h5bgJWpxJNswbU7qCrV0tIKQCaS3blPDrqKWx+QxzuzL1zGUzij9XCWLrSLsJPu5t+eWA/ycetzYAO5IOMcWAQ==", + "dev": true, + "license": "MIT", + "bin": { + "lz-string": "bin/bin.js" + } + }, "node_modules/magic-string": { - "version": "0.30.14", - "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.30.14.tgz", - "integrity": "sha512-5c99P1WKTed11ZC0HMJOj6CDIue6F8ySu+bJL+85q1zBEIY8IklrJ1eiKC2NDRh3Ct3FcvmJPyQHb9erXMTJNw==", + "version": "0.30.17", + "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.30.17.tgz", + "integrity": "sha512-sNPKHvyjVf7gyjwS4xGTaW/mCnF8wnjtifKBEhxfZ7E/S8tQ0rssrwGNn6q8JH/ohItJfSQp9mBtQYuTlH5QnA==", "dev": true, "license": "MIT", "dependencies": { "@jridgewell/sourcemap-codec": "^1.5.0" } }, + "node_modules/magicast": { + "version": "0.3.5", + "resolved": "https://registry.npmjs.org/magicast/-/magicast-0.3.5.tgz", + "integrity": "sha512-L0WhttDl+2BOsybvEOLK7fW3UA0OQ0IQ2d6Zl2x/a6vVRs3bAY0ECOSHHeL5jD+SbOpOCUEi0y1DgHEn9Qn1AQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@babel/parser": "^7.25.4", + "@babel/types": "^7.25.4", + "source-map-js": "^1.2.0" + } + }, "node_modules/make-dir": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz", @@ -15608,12 +16387,22 @@ "ufo": "^1.5.4" } }, - "node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", + "node_modules/mrmime": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/mrmime/-/mrmime-2.0.1.tgz", + "integrity": "sha512-Y3wQdFg2Va6etvQ5I82yUhGdsKrcYox6p7FfL1LbK2J4V01F9TGlepTIhnK24t7koZibmg82KGglhA1XK5IsLQ==", "dev": true, - "license": "MIT" + "license": "MIT", + "engines": { + "node": ">=10" + } + }, + "node_modules/ms": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", + "dev": true, + "license": "MIT" }, "node_modules/nanoid": { "version": "3.3.8", @@ -16395,6 +17184,16 @@ "dev": true, "license": "MIT" }, + "node_modules/pathval": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/pathval/-/pathval-2.0.0.tgz", + "integrity": "sha512-vE7JKRyES09KiunauX7nd2Q9/L7lhok4smP9RZTDeD4MVs72Dp2qNFVz39Nz5a0FVEW0BJR6C0DYrq6unoziZA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 14.16" + } + }, "node_modules/pause-stream": { "version": "0.0.11", "resolved": "https://registry.npmjs.org/pause-stream/-/pause-stream-0.0.11.tgz", @@ -16525,6 +17324,53 @@ "pathe": "^1.1.2" } }, + "node_modules/playwright": { + "version": "1.50.1", + "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.50.1.tgz", + "integrity": "sha512-G8rwsOQJ63XG6BbKj2w5rHeavFjy5zynBA9zsJMMtBoe/Uf757oG12NXz6e6OirF7RCrTVAKFXbLmn1RbL7Qaw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "playwright-core": "1.50.1" + }, + "bin": { + "playwright": "cli.js" + }, + "engines": { + "node": ">=18" + }, + "optionalDependencies": { + "fsevents": "2.3.2" + } + }, + "node_modules/playwright-core": { + "version": "1.50.1", + "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.50.1.tgz", + "integrity": "sha512-ra9fsNWayuYumt+NiM069M6OkcRb1FZSK8bgi66AtpFoWkg2+y0bJSNmkFrWhMbEBbVKC/EruAHH3g0zmtwGmQ==", + "dev": true, + "license": "Apache-2.0", + "bin": { + "playwright-core": "cli.js" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/playwright/node_modules/fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, "node_modules/pngjs": { "version": "6.0.0", "resolved": "https://registry.npmjs.org/pngjs/-/pngjs-6.0.0.tgz", @@ -16559,9 +17405,9 @@ } }, "node_modules/postcss": { - "version": "8.4.49", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.49.tgz", - "integrity": "sha512-OCVPnIObs4N29kxTjzLfUryOkvZEq+pf8jTF0lg8E7uETuWHA+v7j3c/xJmiqpX450191LlmZfUKkXxkTry7nA==", + "version": "8.5.3", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.3.tgz", + "integrity": "sha512-dle9A3yYxlBSrt8Fu+IpjGT8SY8hN0mlaA6GY8t0P5PjIOZemULz/E2Bnm/2dcUOena75OTNkHI76uZBNUUq3A==", "dev": true, "funding": [ { @@ -16579,7 +17425,7 @@ ], "license": "MIT", "dependencies": { - "nanoid": "^3.3.7", + "nanoid": "^3.3.8", "picocolors": "^1.1.1", "source-map-js": "^1.2.1" }, @@ -16708,6 +17554,34 @@ "renderkid": "^3.0.0" } }, + "node_modules/pretty-format": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-27.5.1.tgz", + "integrity": "sha512-Qb1gy5OrP5+zDf2Bvnzdl3jsTf1qXVMazbvCoKhtKqVs4/YK4ozX4gKQJJVyNe+cajNPn0KoC0MC3FUmaHWEmQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "ansi-regex": "^5.0.1", + "ansi-styles": "^5.0.0", + "react-is": "^17.0.1" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/pretty-format/node_modules/ansi-styles": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", + "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, "node_modules/pretty-hrtime": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/pretty-hrtime/-/pretty-hrtime-1.0.3.tgz", @@ -17451,6 +18325,13 @@ "react": "^18.3.1" } }, + "node_modules/react-is": { + "version": "17.0.2", + "resolved": "https://registry.npmjs.org/react-is/-/react-is-17.0.2.tgz", + "integrity": "sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w==", + "dev": true, + "license": "MIT" + }, "node_modules/react-remove-scroll": { "version": "2.5.5", "resolved": "https://registry.npmjs.org/react-remove-scroll/-/react-remove-scroll-2.5.5.tgz", @@ -18214,6 +19095,45 @@ "url": "https://github.com/sponsors/isaacs" } }, + "node_modules/rollup": { + "version": "4.34.9", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.34.9.tgz", + "integrity": "sha512-nF5XYqWWp9hx/LrpC8sZvvvmq0TeTjQgaZHYmAgwysT9nh8sWnZhBnM8ZyVbbJFIQBLwHDNoMqsBZBbUo4U8sQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/estree": "1.0.6" + }, + "bin": { + "rollup": "dist/bin/rollup" + }, + "engines": { + "node": ">=18.0.0", + "npm": ">=8.0.0" + }, + "optionalDependencies": { + "@rollup/rollup-android-arm-eabi": "4.34.9", + "@rollup/rollup-android-arm64": "4.34.9", + "@rollup/rollup-darwin-arm64": "4.34.9", + "@rollup/rollup-darwin-x64": "4.34.9", + "@rollup/rollup-freebsd-arm64": "4.34.9", + "@rollup/rollup-freebsd-x64": "4.34.9", + "@rollup/rollup-linux-arm-gnueabihf": "4.34.9", + "@rollup/rollup-linux-arm-musleabihf": "4.34.9", + "@rollup/rollup-linux-arm64-gnu": "4.34.9", + "@rollup/rollup-linux-arm64-musl": "4.34.9", + "@rollup/rollup-linux-loongarch64-gnu": "4.34.9", + "@rollup/rollup-linux-powerpc64le-gnu": "4.34.9", + "@rollup/rollup-linux-riscv64-gnu": "4.34.9", + "@rollup/rollup-linux-s390x-gnu": "4.34.9", + "@rollup/rollup-linux-x64-gnu": "4.34.9", + "@rollup/rollup-linux-x64-musl": "4.34.9", + "@rollup/rollup-win32-arm64-msvc": "4.34.9", + "@rollup/rollup-win32-ia32-msvc": "4.34.9", + "@rollup/rollup-win32-x64-msvc": "4.34.9", + "fsevents": "~2.3.2" + } + }, "node_modules/run-parallel": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", @@ -18714,6 +19634,13 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/siginfo": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/siginfo/-/siginfo-2.0.0.tgz", + "integrity": "sha512-ybx0WO1/8bSBLEWXZvEd7gMW3Sn3JFlW3TvX1nREbDLRNQNaeNN8WK0meBwPdAaOI7TtRRRJn/Es1zhrrCHu7g==", + "dev": true, + "license": "ISC" + }, "node_modules/signal-exit": { "version": "4.1.0", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-4.1.0.tgz", @@ -18727,6 +19654,21 @@ "url": "https://github.com/sponsors/isaacs" } }, + "node_modules/sirv": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/sirv/-/sirv-3.0.1.tgz", + "integrity": "sha512-FoqMu0NCGBLCcAkS1qA+XJIQTR6/JHfQXl+uGteNCQ76T91DMUjPa9xfmeqMY3z80nLSg9yQmNjK0Px6RWsH/A==", + "dev": true, + "license": "MIT", + "dependencies": { + "@polka/url": "^1.0.0-next.24", + "mrmime": "^2.0.0", + "totalist": "^3.0.0" + }, + "engines": { + "node": ">=18" + } + }, "node_modules/sisteransi": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/sisteransi/-/sisteransi-1.0.5.tgz", @@ -18975,6 +19917,13 @@ "node": ">=0.10.0" } }, + "node_modules/stackback": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/stackback/-/stackback-0.0.2.tgz", + "integrity": "sha512-1XMJE5fQo1jGH6Y/7ebnwPOBEkIEnT4QF32d5R1+VXdXveM0IBMJt8zfaxX1P3QhVwrYe+576+jkANtSS2mBbw==", + "dev": true, + "license": "MIT" + }, "node_modules/statuses": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", @@ -18985,6 +19934,13 @@ "node": ">= 0.8" } }, + "node_modules/std-env": { + "version": "3.9.0", + "resolved": "https://registry.npmjs.org/std-env/-/std-env-3.9.0.tgz", + "integrity": "sha512-UGvjygr6F6tpH7o2qyqR6QYpwraIjKSdtzyBdyytFOHmPZY917kwdwLG0RbOjWOnKmnm3PeHjaoLLMie7kPLQw==", + "dev": true, + "license": "MIT" + }, "node_modules/store2": { "version": "2.14.3", "resolved": "https://registry.npmjs.org/store2/-/store2-2.14.3.tgz", @@ -19916,6 +20872,95 @@ "dev": true, "license": "MIT" }, + "node_modules/tinybench": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/tinybench/-/tinybench-2.9.0.tgz", + "integrity": "sha512-0+DUvqWMValLmha6lr4kD8iAMK1HzV0/aKnCtWb9v9641TnP/MFb7Pc2bxoxQjTXAErryXVgUOfv2YqNllqGeg==", + "dev": true, + "license": "MIT" + }, + "node_modules/tinyexec": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/tinyexec/-/tinyexec-0.3.2.tgz", + "integrity": "sha512-KQQR9yN7R5+OSwaK0XQoj22pwHoTlgYqmUscPYoknOoWCWfj/5/ABTMRi69FrKU5ffPVh5QcFikpWJI/P1ocHA==", + "dev": true, + "license": "MIT" + }, + "node_modules/tinyglobby": { + "version": "0.2.13", + "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.13.tgz", + "integrity": "sha512-mEwzpUgrLySlveBwEVDMKk5B57bhLPYovRfPAXD5gA/98Opn0rCDj3GtLwFvCvH5RK9uPCExUROW5NjDwvqkxw==", + "dev": true, + "license": "MIT", + "dependencies": { + "fdir": "^6.4.4", + "picomatch": "^4.0.2" + }, + "engines": { + "node": ">=12.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/SuperchupuDev" + } + }, + "node_modules/tinyglobby/node_modules/fdir": { + "version": "6.4.4", + "resolved": "https://registry.npmjs.org/fdir/-/fdir-6.4.4.tgz", + "integrity": "sha512-1NZP+GK4GfuAv3PqKvxQRDMjdSRZjnkq7KfhlNrCNNlZ0ygQFpebfrnfnq/W7fpUnAv9aGWmY1zKx7FYL3gwhg==", + "dev": true, + "license": "MIT", + "peerDependencies": { + "picomatch": "^3 || ^4" + }, + "peerDependenciesMeta": { + "picomatch": { + "optional": true + } + } + }, + "node_modules/tinyglobby/node_modules/picomatch": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.2.tgz", + "integrity": "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, + "node_modules/tinypool": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/tinypool/-/tinypool-1.0.2.tgz", + "integrity": "sha512-al6n+QEANGFOMf/dmUMsuS5/r9B06uwlyNjZZql/zv8J7ybHCgoihBNORZCY2mzUuAnomQa2JdhyHKzZxPCrFA==", + "dev": true, + "license": "MIT", + "engines": { + "node": "^18.0.0 || >=20.0.0" + } + }, + "node_modules/tinyrainbow": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/tinyrainbow/-/tinyrainbow-2.0.0.tgz", + "integrity": "sha512-op4nsTR47R6p0vMUUoYl/a+ljLFVtlfaXkLQmqfLR1qHma1h/ysYk4hEXZ880bf2CYgTskvTa/e196Vd5dDQXw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/tinyspy": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/tinyspy/-/tinyspy-3.0.2.tgz", + "integrity": "sha512-n1cw8k1k0x4pgA2+9XrOkFydTerNcJ1zWCO5Nn9scWHTD+5tp8dghT2x1uduQePZTZgd3Tupf+x9BxJjeJi77Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=14.0.0" + } + }, "node_modules/tmp": { "version": "0.2.3", "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.3.tgz", @@ -19973,6 +21018,16 @@ "node": ">=0.6" } }, + "node_modules/totalist": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/totalist/-/totalist-3.0.1.tgz", + "integrity": "sha512-sf4i37nQ2LBx4m3wB74y+ubopq6W/dIzXg0FDGjsYnZHVa1Da8FH853wlL2gtUhg+xJXjfk3kUZS3BRoQeoQBQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/tough-cookie": { "version": "2.5.0", "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.5.0.tgz", @@ -20726,57 +21781,688 @@ "dev": true, "license": "MIT" }, - "node_modules/void-elements": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/void-elements/-/void-elements-2.0.1.tgz", - "integrity": "sha512-qZKX4RnBzH2ugr8Lxa7x+0V6XD9Sb/ouARtiasEQCHB1EVU4NXtmHsDDrx1dO4ne5fc3J6EW05BP1Dl0z0iung==", + "node_modules/vite": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/vite/-/vite-6.2.0.tgz", + "integrity": "sha512-7dPxoo+WsT/64rDcwoOjk76XHj+TqNTIvHKcuMQ1k4/SeHDaQt5GFAeLYzrimZrMpn/O6DtdI03WUjdxuPM0oQ==", "dev": true, "license": "MIT", + "dependencies": { + "esbuild": "^0.25.0", + "postcss": "^8.5.3", + "rollup": "^4.30.1" + }, + "bin": { + "vite": "bin/vite.js" + }, "engines": { - "node": ">=0.10.0" + "node": "^18.0.0 || ^20.0.0 || >=22.0.0" + }, + "funding": { + "url": "https://github.com/vitejs/vite?sponsor=1" + }, + "optionalDependencies": { + "fsevents": "~2.3.3" + }, + "peerDependencies": { + "@types/node": "^18.0.0 || ^20.0.0 || >=22.0.0", + "jiti": ">=1.21.0", + "less": "*", + "lightningcss": "^1.21.0", + "sass": "*", + "sass-embedded": "*", + "stylus": "*", + "sugarss": "*", + "terser": "^5.16.0", + "tsx": "^4.8.1", + "yaml": "^2.4.2" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + }, + "jiti": { + "optional": true + }, + "less": { + "optional": true + }, + "lightningcss": { + "optional": true + }, + "sass": { + "optional": true + }, + "sass-embedded": { + "optional": true + }, + "stylus": { + "optional": true + }, + "sugarss": { + "optional": true + }, + "terser": { + "optional": true + }, + "tsx": { + "optional": true + }, + "yaml": { + "optional": true + } } }, - "node_modules/vscode-oniguruma": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/vscode-oniguruma/-/vscode-oniguruma-1.7.0.tgz", - "integrity": "sha512-L9WMGRfrjOhgHSdOYgCt/yRMsXzLDJSL7BPrOZt73gU0iWO4mpqzqQzOz5srxqTvMBaR0XZTSrVWo4j55Rc6cA==", - "dev": true, - "license": "MIT" - }, - "node_modules/vscode-textmate": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/vscode-textmate/-/vscode-textmate-8.0.0.tgz", - "integrity": "sha512-AFbieoL7a5LMqcnOF04ji+rpXadgOXnZsxQr//r83kLPr7biP7am3g9zbaZIaBGwBRWeSvoMD4mgPdX3e4NWBg==", - "dev": true, - "license": "MIT" - }, - "node_modules/walker": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/walker/-/walker-1.0.8.tgz", - "integrity": "sha512-ts/8E8l5b7kY0vlWLewOkDXMmPdLcVV4GmOQLyxuSswIJsweeFZtAsMF7k1Nszz+TYBQrlYRmzOnr398y1JemQ==", + "node_modules/vite-node": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/vite-node/-/vite-node-3.1.2.tgz", + "integrity": "sha512-/8iMryv46J3aK13iUXsei5G/A3CUlW4665THCPS+K8xAaqrVWiGB4RfXMQXCLjpK9P2eK//BczrVkn5JLAk6DA==", "dev": true, - "license": "Apache-2.0", + "license": "MIT", "dependencies": { - "makeerror": "1.0.12" + "cac": "^6.7.14", + "debug": "^4.4.0", + "es-module-lexer": "^1.6.0", + "pathe": "^2.0.3", + "vite": "^5.0.0 || ^6.0.0" + }, + "bin": { + "vite-node": "vite-node.mjs" + }, + "engines": { + "node": "^18.0.0 || ^20.0.0 || >=22.0.0" + }, + "funding": { + "url": "https://opencollective.com/vitest" } }, - "node_modules/watchpack": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.2.tgz", - "integrity": "sha512-TnbFSbcOCcDgjZ4piURLCbJ3nJhznVh9kw6F6iokjiFPl8ONxe9A6nMDVXDiNbrSfLILs6vB07F7wLBrwPYzJw==", + "node_modules/vite-node/node_modules/debug": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", + "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", "dev": true, "license": "MIT", "dependencies": { - "glob-to-regexp": "^0.4.1", - "graceful-fs": "^4.1.2" + "ms": "^2.1.3" }, "engines": { - "node": ">=10.13.0" + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } } }, - "node_modules/wcwidth": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/wcwidth/-/wcwidth-1.0.1.tgz", + "node_modules/vite-node/node_modules/pathe": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/pathe/-/pathe-2.0.3.tgz", + "integrity": "sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==", + "dev": true, + "license": "MIT" + }, + "node_modules/vite/node_modules/@esbuild/android-arm": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.25.0.tgz", + "integrity": "sha512-PTyWCYYiU0+1eJKmw21lWtC+d08JDZPQ5g+kFyxP0V+es6VPPSUhM6zk8iImp2jbV6GwjX4pap0JFbUQN65X1g==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/android-arm64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.25.0.tgz", + "integrity": "sha512-grvv8WncGjDSyUBjN9yHXNt+cq0snxXbDxy5pJtzMKGmmpPxeAmAhWxXI+01lU5rwZomDgD3kJwulEnhTRUd6g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/android-x64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.25.0.tgz", + "integrity": "sha512-m/ix7SfKG5buCnxasr52+LI78SQ+wgdENi9CqyCXwjVR2X4Jkz+BpC3le3AoBPYTC9NHklwngVXvbJ9/Akhrfg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/darwin-arm64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.25.0.tgz", + "integrity": "sha512-mVwdUb5SRkPayVadIOI78K7aAnPamoeFR2bT5nszFUZ9P8UpK4ratOdYbZZXYSqPKMHfS1wdHCJk1P1EZpRdvw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/darwin-x64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.25.0.tgz", + "integrity": "sha512-DgDaYsPWFTS4S3nWpFcMn/33ZZwAAeAFKNHNa1QN0rI4pUjgqf0f7ONmXf6d22tqTY+H9FNdgeaAa+YIFUn2Rg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/freebsd-arm64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.25.0.tgz", + "integrity": "sha512-VN4ocxy6dxefN1MepBx/iD1dH5K8qNtNe227I0mnTRjry8tj5MRk4zprLEdG8WPyAPb93/e4pSgi1SoHdgOa4w==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/freebsd-x64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.25.0.tgz", + "integrity": "sha512-mrSgt7lCh07FY+hDD1TxiTyIHyttn6vnjesnPoVDNmDfOmggTLXRv8Id5fNZey1gl/V2dyVK1VXXqVsQIiAk+A==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/linux-arm": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.25.0.tgz", + "integrity": "sha512-vkB3IYj2IDo3g9xX7HqhPYxVkNQe8qTK55fraQyTzTX/fxaDtXiEnavv9geOsonh2Fd2RMB+i5cbhu2zMNWJwg==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/linux-arm64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.25.0.tgz", + "integrity": "sha512-9QAQjTWNDM/Vk2bgBl17yWuZxZNQIF0OUUuPZRKoDtqF2k4EtYbpyiG5/Dk7nqeK6kIJWPYldkOcBqjXjrUlmg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/linux-ia32": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.25.0.tgz", + "integrity": "sha512-43ET5bHbphBegyeqLb7I1eYn2P/JYGNmzzdidq/w0T8E2SsYL1U6un2NFROFRg1JZLTzdCoRomg8Rvf9M6W6Gg==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/linux-loong64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.25.0.tgz", + "integrity": "sha512-fC95c/xyNFueMhClxJmeRIj2yrSMdDfmqJnyOY4ZqsALkDrrKJfIg5NTMSzVBr5YW1jf+l7/cndBfP3MSDpoHw==", + "cpu": [ + "loong64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/linux-mips64el": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.25.0.tgz", + "integrity": "sha512-nkAMFju7KDW73T1DdH7glcyIptm95a7Le8irTQNO/qtkoyypZAnjchQgooFUDQhNAy4iu08N79W4T4pMBwhPwQ==", + "cpu": [ + "mips64el" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/linux-ppc64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.25.0.tgz", + "integrity": "sha512-NhyOejdhRGS8Iwv+KKR2zTq2PpysF9XqY+Zk77vQHqNbo/PwZCzB5/h7VGuREZm1fixhs4Q/qWRSi5zmAiO4Fw==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/linux-riscv64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.25.0.tgz", + "integrity": "sha512-5S/rbP5OY+GHLC5qXp1y/Mx//e92L1YDqkiBbO9TQOvuFXM+iDqUNG5XopAnXoRH3FjIUDkeGcY1cgNvnXp/kA==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/linux-s390x": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.25.0.tgz", + "integrity": "sha512-XM2BFsEBz0Fw37V0zU4CXfcfuACMrppsMFKdYY2WuTS3yi8O1nFOhil/xhKTmE1nPmVyvQJjJivgDT+xh8pXJA==", + "cpu": [ + "s390x" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/linux-x64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.25.0.tgz", + "integrity": "sha512-9yl91rHw/cpwMCNytUDxwj2XjFpxML0y9HAOH9pNVQDpQrBxHy01Dx+vaMu0N1CKa/RzBD2hB4u//nfc+Sd3Cw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/netbsd-x64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.25.0.tgz", + "integrity": "sha512-jl+qisSB5jk01N5f7sPCsBENCOlPiS/xptD5yxOx2oqQfyourJwIKLRA2yqWdifj3owQZCL2sn6o08dBzZGQzA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/openbsd-x64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.25.0.tgz", + "integrity": "sha512-2gwwriSMPcCFRlPlKx3zLQhfN/2WjJ2NSlg5TKLQOJdV0mSxIcYNTMhk3H3ulL/cak+Xj0lY1Ym9ysDV1igceg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/sunos-x64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.25.0.tgz", + "integrity": "sha512-bxI7ThgLzPrPz484/S9jLlvUAHYMzy6I0XiU1ZMeAEOBcS0VePBFxh1JjTQt3Xiat5b6Oh4x7UC7IwKQKIJRIg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "sunos" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/win32-arm64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.25.0.tgz", + "integrity": "sha512-ZUAc2YK6JW89xTbXvftxdnYy3m4iHIkDtK3CLce8wg8M2L+YZhIvO1DKpxrd0Yr59AeNNkTiic9YLf6FTtXWMw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/win32-ia32": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.25.0.tgz", + "integrity": "sha512-eSNxISBu8XweVEWG31/JzjkIGbGIJN/TrRoiSVZwZ6pkC6VX4Im/WV2cz559/TXLcYbcrDN8JtKgd9DJVIo8GA==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/@esbuild/win32-x64": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.25.0.tgz", + "integrity": "sha512-ZENoHJBxA20C2zFzh6AI4fT6RraMzjYw4xKWemRTRmRVtN9c5DcH9r/f2ihEkMjOW5eGgrwCslG/+Y/3bL+DHQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/vite/node_modules/esbuild": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.25.0.tgz", + "integrity": "sha512-BXq5mqc8ltbaN34cDqWuYKyNhX8D/Z0J1xdtdQ8UcIIIyJyz+ZMKUt58tF3SrZ85jcfN/PZYhjR5uDQAYNVbuw==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "bin": { + "esbuild": "bin/esbuild" + }, + "engines": { + "node": ">=18" + }, + "optionalDependencies": { + "@esbuild/aix-ppc64": "0.25.0", + "@esbuild/android-arm": "0.25.0", + "@esbuild/android-arm64": "0.25.0", + "@esbuild/android-x64": "0.25.0", + "@esbuild/darwin-arm64": "0.25.0", + "@esbuild/darwin-x64": "0.25.0", + "@esbuild/freebsd-arm64": "0.25.0", + "@esbuild/freebsd-x64": "0.25.0", + "@esbuild/linux-arm": "0.25.0", + "@esbuild/linux-arm64": "0.25.0", + "@esbuild/linux-ia32": "0.25.0", + "@esbuild/linux-loong64": "0.25.0", + "@esbuild/linux-mips64el": "0.25.0", + "@esbuild/linux-ppc64": "0.25.0", + "@esbuild/linux-riscv64": "0.25.0", + "@esbuild/linux-s390x": "0.25.0", + "@esbuild/linux-x64": "0.25.0", + "@esbuild/netbsd-arm64": "0.25.0", + "@esbuild/netbsd-x64": "0.25.0", + "@esbuild/openbsd-arm64": "0.25.0", + "@esbuild/openbsd-x64": "0.25.0", + "@esbuild/sunos-x64": "0.25.0", + "@esbuild/win32-arm64": "0.25.0", + "@esbuild/win32-ia32": "0.25.0", + "@esbuild/win32-x64": "0.25.0" + } + }, + "node_modules/vitest": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/vitest/-/vitest-3.1.2.tgz", + "integrity": "sha512-WaxpJe092ID1C0mr+LH9MmNrhfzi8I65EX/NRU/Ld016KqQNRgxSOlGNP1hHN+a/F8L15Mh8klwaF77zR3GeDQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@vitest/expect": "3.1.2", + "@vitest/mocker": "3.1.2", + "@vitest/pretty-format": "^3.1.2", + "@vitest/runner": "3.1.2", + "@vitest/snapshot": "3.1.2", + "@vitest/spy": "3.1.2", + "@vitest/utils": "3.1.2", + "chai": "^5.2.0", + "debug": "^4.4.0", + "expect-type": "^1.2.1", + "magic-string": "^0.30.17", + "pathe": "^2.0.3", + "std-env": "^3.9.0", + "tinybench": "^2.9.0", + "tinyexec": "^0.3.2", + "tinyglobby": "^0.2.13", + "tinypool": "^1.0.2", + "tinyrainbow": "^2.0.0", + "vite": "^5.0.0 || ^6.0.0", + "vite-node": "3.1.2", + "why-is-node-running": "^2.3.0" + }, + "bin": { + "vitest": "vitest.mjs" + }, + "engines": { + "node": "^18.0.0 || ^20.0.0 || >=22.0.0" + }, + "funding": { + "url": "https://opencollective.com/vitest" + }, + "peerDependencies": { + "@edge-runtime/vm": "*", + "@types/debug": "^4.1.12", + "@types/node": "^18.0.0 || ^20.0.0 || >=22.0.0", + "@vitest/browser": "3.1.2", + "@vitest/ui": "3.1.2", + "happy-dom": "*", + "jsdom": "*" + }, + "peerDependenciesMeta": { + "@edge-runtime/vm": { + "optional": true + }, + "@types/debug": { + "optional": true + }, + "@types/node": { + "optional": true + }, + "@vitest/browser": { + "optional": true + }, + "@vitest/ui": { + "optional": true + }, + "happy-dom": { + "optional": true + }, + "jsdom": { + "optional": true + } + } + }, + "node_modules/vitest/node_modules/debug": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", + "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/vitest/node_modules/pathe": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/pathe/-/pathe-2.0.3.tgz", + "integrity": "sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==", + "dev": true, + "license": "MIT" + }, + "node_modules/void-elements": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/void-elements/-/void-elements-2.0.1.tgz", + "integrity": "sha512-qZKX4RnBzH2ugr8Lxa7x+0V6XD9Sb/ouARtiasEQCHB1EVU4NXtmHsDDrx1dO4ne5fc3J6EW05BP1Dl0z0iung==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/vscode-oniguruma": { + "version": "1.7.0", + "resolved": "https://registry.npmjs.org/vscode-oniguruma/-/vscode-oniguruma-1.7.0.tgz", + "integrity": "sha512-L9WMGRfrjOhgHSdOYgCt/yRMsXzLDJSL7BPrOZt73gU0iWO4mpqzqQzOz5srxqTvMBaR0XZTSrVWo4j55Rc6cA==", + "dev": true, + "license": "MIT" + }, + "node_modules/vscode-textmate": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/vscode-textmate/-/vscode-textmate-8.0.0.tgz", + "integrity": "sha512-AFbieoL7a5LMqcnOF04ji+rpXadgOXnZsxQr//r83kLPr7biP7am3g9zbaZIaBGwBRWeSvoMD4mgPdX3e4NWBg==", + "dev": true, + "license": "MIT" + }, + "node_modules/walker": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/walker/-/walker-1.0.8.tgz", + "integrity": "sha512-ts/8E8l5b7kY0vlWLewOkDXMmPdLcVV4GmOQLyxuSswIJsweeFZtAsMF7k1Nszz+TYBQrlYRmzOnr398y1JemQ==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "makeerror": "1.0.12" + } + }, + "node_modules/watchpack": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.2.tgz", + "integrity": "sha512-TnbFSbcOCcDgjZ4piURLCbJ3nJhznVh9kw6F6iokjiFPl8ONxe9A6nMDVXDiNbrSfLILs6vB07F7wLBrwPYzJw==", + "dev": true, + "license": "MIT", + "dependencies": { + "glob-to-regexp": "^0.4.1", + "graceful-fs": "^4.1.2" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/wcwidth": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/wcwidth/-/wcwidth-1.0.1.tgz", "integrity": "sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg==", "dev": true, "license": "MIT", @@ -21049,6 +22735,23 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/why-is-node-running": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/why-is-node-running/-/why-is-node-running-2.3.0.tgz", + "integrity": "sha512-hUrmaWBdVDcxvYqnyh09zunKzROWjbZTiNy8dBEjkS7ehEDQibXJ7XvlmtbwuTclUiIyN+CyXQD4Vmko8fNm8w==", + "dev": true, + "license": "MIT", + "dependencies": { + "siginfo": "^2.0.0", + "stackback": "0.0.2" + }, + "bin": { + "why-is-node-running": "cli.js" + }, + "engines": { + "node": ">=8" + } + }, "node_modules/widest-line": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-4.0.1.tgz", @@ -21278,13 +22981,18 @@ "license": "ISC" }, "node_modules/yaml": { - "version": "1.10.2", - "resolved": "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz", - "integrity": "sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==", + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.7.0.tgz", + "integrity": "sha512-+hSoy/QHluxmC9kCIJyL/uyFmLmc+e5CFR5Wa+bpIhIj85LVb9ZH2nVnqrHoSvKogwODv0ClqZkmiSSaIH5LTA==", "dev": true, "license": "ISC", + "optional": true, + "peer": true, + "bin": { + "yaml": "bin.mjs" + }, "engines": { - "node": ">= 6" + "node": ">= 14" } }, "node_modules/yargs": { diff --git a/package.json b/package.json index d1b9e7bb..916b92fc 100644 --- a/package.json +++ b/package.json @@ -42,7 +42,7 @@ ], "scripts": { "all": "npm run format && npm run lint && npm run core && npm run build:esm && npm run test && npm run legacy-visual", - "all:ci": "npm run format && npm run lint && npm run core && npm run build:esm && npm run test:ci && npm run legacy-visual", + "all:ci": "npm run format && npm run lint && npm run test:ci && npm run core && npm run build:esm && npm run legacy-visual", "clean": "rimraf .tsbuildinfo ./build/dist ./build ./src/spec/*.js ./src/spec/*.map", "linux:ci": "npm run clean && npm run all:ci && npm run coveralls && npm run apidocs", "appveyor": "npm run all:ci && npm run nuget 0.0.1", @@ -65,6 +65,7 @@ "format:fix": "npm run format -- --write", "lint": "npm run eslint", "lint:fix": "npm run eslint -- --fix", + "type-check": "cd src/engine && tsc --noEmit", "eslint": "eslint .", "visual": "storybook dev", "build-storybook": "storybook build -o build-storybook", @@ -72,10 +73,12 @@ "sandbox:build": "tsc --project ./sandbox", "sandbox": "serve ./sandbox -l 3001 -n", "legacy-visual": "npm run sandbox:copy && npm run sandbox:build", - "test": "karma start", - "test:ci": "karma start --browsers=ChromeHeadless_with_audio", - "test:watch": "karma start --auto-watch --single-run=false", - "coveralls": "echo 'Temporarily Remove Coveralls Due To Outage'", + "test": "vitest", + "test:watch": "npm run test -- --watch", + "test:ci": "npm run test:chromium -- --silent", + "test:chromium": "vitest --browser chromium", + "test:firefox": "vitest --browser firefox", + "test:webkit": "vitest --browser webkit", "apidocs": "node scripts/apidocs.js", "release": "cross-env release=true npm run all", "prepare": "husky" @@ -97,6 +100,8 @@ "@types/webpack-env": "1.18.8", "@typescript-eslint/eslint-plugin": "7.18.0", "@typescript-eslint/parser": "7.18.0", + "@vitest/browser": "3.1.2", + "@vitest/coverage-istanbul": "3.1.2", "babel-loader": "9.2.1", "concurrently": "9.1.2", "copy-webpack-plugin": "12.0.2", @@ -125,6 +130,8 @@ "karma-summary-reporter": "3.1.1", "karma-webpack": "5.0.1", "lint-staged": "15.5.1", + "pixelmatch": "5.3.0", + "playwright": "1.50.1", "prettier": "3.2.5", "puppeteer": "15.5.0", "raw-loader": "4.0.2", @@ -142,6 +149,8 @@ "typedoc": "0.25.13", "typescript": "5.6.3", "url-loader": "4.1.1", + "vite": "6.2.0", + "vitest": "3.1.2", "webpack": "5.99.7", "webpack-cli": "5.1.4" }, diff --git a/src/engine/Actions/Action.ts b/src/engine/Actions/Action.ts index 484145e5..154b1fcf 100644 --- a/src/engine/Actions/Action.ts +++ b/src/engine/Actions/Action.ts @@ -1,4 +1,4 @@ -import { Entity } from '../EntityComponentSystem/Entity'; +import type { Entity } from '../EntityComponentSystem/Entity'; /** * Used for implementing actions for the {@apilink ActionContext | `Action API`}. diff --git a/src/engine/Actions/Action/ActionSequence.ts b/src/engine/Actions/Action/ActionSequence.ts index 11909122..522fe61b 100644 --- a/src/engine/Actions/Action/ActionSequence.ts +++ b/src/engine/Actions/Action/ActionSequence.ts @@ -1,7 +1,8 @@ -import { Entity } from '../../EntityComponentSystem'; -import { Action, nextActionId } from '../Action'; +import type { Entity } from '../../EntityComponentSystem'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; import { ActionContext } from '../ActionContext'; -import { ActionQueue } from '../ActionQueue'; +import type { ActionQueue } from '../ActionQueue'; /** * Action that can represent a sequence of actions, this can be useful in conjunction with diff --git a/src/engine/Actions/Action/Blink.ts b/src/engine/Actions/Action/Blink.ts index 357eaf2c..30257e52 100644 --- a/src/engine/Actions/Action/Blink.ts +++ b/src/engine/Actions/Action/Blink.ts @@ -1,6 +1,7 @@ import { GraphicsComponent } from '../../Graphics/GraphicsComponent'; -import { Entity } from '../../EntityComponentSystem/Entity'; -import { Action, nextActionId } from '../Action'; +import type { Entity } from '../../EntityComponentSystem/Entity'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; export class Blink implements Action { id = nextActionId(); diff --git a/src/engine/Actions/Action/CallMethod.ts b/src/engine/Actions/Action/CallMethod.ts index 7aa996af..b099a8a6 100644 --- a/src/engine/Actions/Action/CallMethod.ts +++ b/src/engine/Actions/Action/CallMethod.ts @@ -1,4 +1,5 @@ -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; export class CallMethod implements Action { id = nextActionId(); diff --git a/src/engine/Actions/Action/CurveBy.ts b/src/engine/Actions/Action/CurveBy.ts index f7555c15..1a119e7b 100644 --- a/src/engine/Actions/Action/CurveBy.ts +++ b/src/engine/Actions/Action/CurveBy.ts @@ -1,6 +1,9 @@ -import { Entity, TransformComponent } from '../../EntityComponentSystem'; -import { BezierCurve, clamp, remap, vec, Vector } from '../../Math'; -import { Action, nextActionId } from '../Action'; +import type { Entity } from '../../EntityComponentSystem'; +import { TransformComponent } from '../../EntityComponentSystem'; +import type { Vector } from '../../Math'; +import { BezierCurve, clamp, remap, vec } from '../../Math'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; export interface CurveByOptions { /** diff --git a/src/engine/Actions/Action/CurveTo.ts b/src/engine/Actions/Action/CurveTo.ts index 83c64ffb..7a6f8f51 100644 --- a/src/engine/Actions/Action/CurveTo.ts +++ b/src/engine/Actions/Action/CurveTo.ts @@ -1,6 +1,9 @@ -import { Entity, TransformComponent } from '../../EntityComponentSystem'; -import { BezierCurve, clamp, remap, vec, Vector } from '../../Math'; -import { Action, nextActionId } from '../Action'; +import type { Entity } from '../../EntityComponentSystem'; +import { TransformComponent } from '../../EntityComponentSystem'; +import type { Vector } from '../../Math'; +import { BezierCurve, clamp, remap, vec } from '../../Math'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; export interface CurveToOptions { /** diff --git a/src/engine/Actions/Action/Delay.ts b/src/engine/Actions/Action/Delay.ts index b7da59d1..9da85f0f 100644 --- a/src/engine/Actions/Action/Delay.ts +++ b/src/engine/Actions/Action/Delay.ts @@ -1,4 +1,5 @@ -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; export class Delay implements Action { id = nextActionId(); diff --git a/src/engine/Actions/Action/Die.ts b/src/engine/Actions/Action/Die.ts index d343a6dd..15a3f3ee 100644 --- a/src/engine/Actions/Action/Die.ts +++ b/src/engine/Actions/Action/Die.ts @@ -1,5 +1,6 @@ -import { Entity } from '../../EntityComponentSystem/Entity'; -import { Action, nextActionId } from '../Action'; +import type { Entity } from '../../EntityComponentSystem/Entity'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; import { ActionsComponent } from '../ActionsComponent'; export class Die implements Action { diff --git a/src/engine/Actions/Action/EaseBy.ts b/src/engine/Actions/Action/EaseBy.ts index 3468bbe1..098e38af 100644 --- a/src/engine/Actions/Action/EaseBy.ts +++ b/src/engine/Actions/Action/EaseBy.ts @@ -1,8 +1,9 @@ import { MotionComponent } from '../../EntityComponentSystem/Components/MotionComponent'; import { TransformComponent } from '../../EntityComponentSystem/Components/TransformComponent'; -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { vec, Vector } from '../../Math/vector'; -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; /** * @deprecated use moveBy({offset: Vector, duration: number, easing: EasingFunction}) diff --git a/src/engine/Actions/Action/EaseTo.ts b/src/engine/Actions/Action/EaseTo.ts index 69eea7cb..93d46818 100644 --- a/src/engine/Actions/Action/EaseTo.ts +++ b/src/engine/Actions/Action/EaseTo.ts @@ -1,8 +1,9 @@ -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { TransformComponent } from '../../EntityComponentSystem/Components/TransformComponent'; import { MotionComponent } from '../../EntityComponentSystem/Components/MotionComponent'; import { vec, Vector } from '../../Math/vector'; -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; /** * @deprecated use moveTo({pos: Vector, duration: number, easing: EasingFunction}) diff --git a/src/engine/Actions/Action/Fade.ts b/src/engine/Actions/Action/Fade.ts index 0f336cb9..deffde86 100644 --- a/src/engine/Actions/Action/Fade.ts +++ b/src/engine/Actions/Action/Fade.ts @@ -1,7 +1,8 @@ -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { GraphicsComponent } from '../../Graphics/GraphicsComponent'; import { Logger } from '../../Util/Log'; -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; export class Fade implements Action { id = nextActionId(); diff --git a/src/engine/Actions/Action/Flash.ts b/src/engine/Actions/Action/Flash.ts index 366eebc9..5023f3ac 100644 --- a/src/engine/Actions/Action/Flash.ts +++ b/src/engine/Actions/Action/Flash.ts @@ -1,10 +1,11 @@ import { GraphicsComponent } from '../../Graphics/GraphicsComponent'; -import { Entity } from '../../EntityComponentSystem/Entity'; -import { Action, nextActionId } from '../Action'; -import { Actor } from '../../Actor'; -import { Material } from '../../Graphics/Context/material'; -import { Color } from '../../Color'; -import { Shader } from '../../Graphics/Context/shader'; +import type { Entity } from '../../EntityComponentSystem/Entity'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; +import type { Actor } from '../../Actor'; +import type { Material } from '../../Graphics/Context/material'; +import type { Color } from '../../Color'; +import type { Shader } from '../../Graphics/Context/shader'; export class Flash implements Action { id = nextActionId(); diff --git a/src/engine/Actions/Action/Follow.ts b/src/engine/Actions/Action/Follow.ts index 2c325820..95eb7063 100644 --- a/src/engine/Actions/Action/Follow.ts +++ b/src/engine/Actions/Action/Follow.ts @@ -1,8 +1,9 @@ import { MotionComponent } from '../../EntityComponentSystem/Components/MotionComponent'; import { TransformComponent } from '../../EntityComponentSystem/Components/TransformComponent'; -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { vec, Vector } from '../../Math/vector'; -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; export class Follow implements Action { id = nextActionId(); diff --git a/src/engine/Actions/Action/Meet.ts b/src/engine/Actions/Action/Meet.ts index 2aa99e9c..07e396e1 100644 --- a/src/engine/Actions/Action/Meet.ts +++ b/src/engine/Actions/Action/Meet.ts @@ -1,8 +1,9 @@ import { MotionComponent } from '../../EntityComponentSystem/Components/MotionComponent'; import { TransformComponent } from '../../EntityComponentSystem/Components/TransformComponent'; -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { Vector, vec } from '../../Math/vector'; -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; export class Meet implements Action { id = nextActionId(); diff --git a/src/engine/Actions/Action/MoveBy.ts b/src/engine/Actions/Action/MoveBy.ts index d8813735..888719b6 100644 --- a/src/engine/Actions/Action/MoveBy.ts +++ b/src/engine/Actions/Action/MoveBy.ts @@ -1,11 +1,13 @@ import { MotionComponent } from '../../EntityComponentSystem/Components/MotionComponent'; import { TransformComponent } from '../../EntityComponentSystem/Components/TransformComponent'; -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { clamp, remap } from '../../Math'; import { Vector, vec } from '../../Math/vector'; -import { EasingFunction, EasingFunctions } from '../../Util/EasingFunctions'; +import type { EasingFunction } from '../../Util/EasingFunctions'; +import { EasingFunctions } from '../../Util/EasingFunctions'; import { Logger } from '../../Util/Log'; -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; export interface MoveByOptions { offset: Vector; diff --git a/src/engine/Actions/Action/MoveTo.ts b/src/engine/Actions/Action/MoveTo.ts index 2da8e49f..e8131f3b 100644 --- a/src/engine/Actions/Action/MoveTo.ts +++ b/src/engine/Actions/Action/MoveTo.ts @@ -1,10 +1,12 @@ import { MotionComponent } from '../../EntityComponentSystem/Components/MotionComponent'; import { TransformComponent } from '../../EntityComponentSystem/Components/TransformComponent'; -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { clamp, remap } from '../../Math'; import { Vector, vec } from '../../Math/vector'; -import { EasingFunction, EasingFunctions } from '../../Util/EasingFunctions'; -import { Action, nextActionId } from '../Action'; +import type { EasingFunction } from '../../Util/EasingFunctions'; +import { EasingFunctions } from '../../Util/EasingFunctions'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; export interface MoveToOptions { pos: Vector; diff --git a/src/engine/Actions/Action/ParallelActions.ts b/src/engine/Actions/Action/ParallelActions.ts index 13ead8b5..c7670b71 100644 --- a/src/engine/Actions/Action/ParallelActions.ts +++ b/src/engine/Actions/Action/ParallelActions.ts @@ -1,5 +1,6 @@ -import { Entity } from '../../EntityComponentSystem'; -import { Action, nextActionId } from '../Action'; +import type { Entity } from '../../EntityComponentSystem'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; /** * Action that can run multiple {@apilink Action}s or {@apilink ActionSequence}s at the same time diff --git a/src/engine/Actions/Action/Repeat.ts b/src/engine/Actions/Action/Repeat.ts index 48681680..ca41be4f 100644 --- a/src/engine/Actions/Action/Repeat.ts +++ b/src/engine/Actions/Action/Repeat.ts @@ -1,7 +1,8 @@ -import { Entity } from '../../EntityComponentSystem/Entity'; -import { Action, nextActionId } from '../Action'; +import type { Entity } from '../../EntityComponentSystem/Entity'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; import { ActionContext } from '../ActionContext'; -import { ActionQueue } from '../ActionQueue'; +import type { ActionQueue } from '../ActionQueue'; export class Repeat implements Action { id = nextActionId(); diff --git a/src/engine/Actions/Action/RepeatForever.ts b/src/engine/Actions/Action/RepeatForever.ts index d00ab062..fddd01ff 100644 --- a/src/engine/Actions/Action/RepeatForever.ts +++ b/src/engine/Actions/Action/RepeatForever.ts @@ -1,7 +1,8 @@ -import { Entity } from '../../EntityComponentSystem/Entity'; -import { Action, nextActionId } from '../Action'; +import type { Entity } from '../../EntityComponentSystem/Entity'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; import { ActionContext } from '../ActionContext'; -import { ActionQueue } from '../ActionQueue'; +import type { ActionQueue } from '../ActionQueue'; /** * RepeatForever Action implementation, it is recommended you use the fluent action diff --git a/src/engine/Actions/Action/RotateBy.ts b/src/engine/Actions/Action/RotateBy.ts index d2c12a15..e6a19af0 100644 --- a/src/engine/Actions/Action/RotateBy.ts +++ b/src/engine/Actions/Action/RotateBy.ts @@ -1,7 +1,8 @@ -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; import { TransformComponent } from '../../EntityComponentSystem/Components/TransformComponent'; import { MotionComponent } from '../../EntityComponentSystem/Components/MotionComponent'; -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { canonicalizeAngle, clamp, TwoPI } from '../../Math/util'; import { lerpAngle, remap, RotationType } from '../../Math'; diff --git a/src/engine/Actions/Action/RotateTo.ts b/src/engine/Actions/Action/RotateTo.ts index 9bb2991f..cd88ca6c 100644 --- a/src/engine/Actions/Action/RotateTo.ts +++ b/src/engine/Actions/Action/RotateTo.ts @@ -1,8 +1,9 @@ -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; import { RotationType } from '../../Math'; import { TransformComponent } from '../../EntityComponentSystem/Components/TransformComponent'; import { MotionComponent } from '../../EntityComponentSystem/Components/MotionComponent'; -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { clamp, TwoPI } from '../../Math/util'; import { lerpAngle, remap } from '../../Math'; diff --git a/src/engine/Actions/Action/ScaleBy.ts b/src/engine/Actions/Action/ScaleBy.ts index 3e091bf0..39dbc32f 100644 --- a/src/engine/Actions/Action/ScaleBy.ts +++ b/src/engine/Actions/Action/ScaleBy.ts @@ -1,8 +1,9 @@ import { vec, Vector } from '../../Math/vector'; -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { MotionComponent } from '../../EntityComponentSystem/Components/MotionComponent'; import { TransformComponent } from '../../EntityComponentSystem/Components/TransformComponent'; -import { Action, nextActionId } from '../Action'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; import { clamp, lerpVector, remap } from '../../Math'; export interface ScaleByOptions { diff --git a/src/engine/Actions/Action/ScaleTo.ts b/src/engine/Actions/Action/ScaleTo.ts index 3e5050e6..d3205796 100644 --- a/src/engine/Actions/Action/ScaleTo.ts +++ b/src/engine/Actions/Action/ScaleTo.ts @@ -1,8 +1,9 @@ import { vec, Vector } from '../../Math/vector'; import { MotionComponent } from '../../EntityComponentSystem/Components/MotionComponent'; import { TransformComponent } from '../../EntityComponentSystem/Components/TransformComponent'; -import { Action, nextActionId } from '../Action'; -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Action } from '../Action'; +import { nextActionId } from '../Action'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { clamp, lerpVector, remap } from '../../Math'; export interface ScaleToOptions { diff --git a/src/engine/Actions/ActionContext.ts b/src/engine/Actions/ActionContext.ts index e7f140c5..07eb9c41 100644 --- a/src/engine/Actions/ActionContext.ts +++ b/src/engine/Actions/ActionContext.ts @@ -1,13 +1,20 @@ -import { EasingFunction, EasingFunctions } from '../Util/EasingFunctions'; +import type { EasingFunction } from '../Util/EasingFunctions'; +import { EasingFunctions } from '../Util/EasingFunctions'; import { ActionQueue } from './ActionQueue'; import { Repeat } from './Action/Repeat'; import { RepeatForever } from './Action/RepeatForever'; -import { isMoveByOptions, MoveBy, MoveByOptions, MoveByWithOptions } from './Action/MoveBy'; -import { isMoveToOptions, MoveTo, MoveToOptions, MoveToWithOptions } from './Action/MoveTo'; -import { RotateTo, RotateToOptions, RotateToWithOptions } from './Action/RotateTo'; -import { RotateBy, RotateByOptions, RotateByWithOptions } from './Action/RotateBy'; -import { isScaleToOptions, ScaleTo, ScaleToOptions, ScaleToWithOptions } from './Action/ScaleTo'; -import { isScaleByOptions, ScaleBy, ScaleByOptions, ScaleByWithOptions } from './Action/ScaleBy'; +import type { MoveByOptions } from './Action/MoveBy'; +import { isMoveByOptions, MoveBy, MoveByWithOptions } from './Action/MoveBy'; +import type { MoveToOptions } from './Action/MoveTo'; +import { isMoveToOptions, MoveTo, MoveToWithOptions } from './Action/MoveTo'; +import type { RotateToOptions } from './Action/RotateTo'; +import { RotateTo, RotateToWithOptions } from './Action/RotateTo'; +import type { RotateByOptions } from './Action/RotateBy'; +import { RotateBy, RotateByWithOptions } from './Action/RotateBy'; +import type { ScaleToOptions } from './Action/ScaleTo'; +import { isScaleToOptions, ScaleTo, ScaleToWithOptions } from './Action/ScaleTo'; +import type { ScaleByOptions } from './Action/ScaleBy'; +import { isScaleByOptions, ScaleBy, ScaleByWithOptions } from './Action/ScaleBy'; import { CallMethod } from './Action/CallMethod'; import { EaseTo } from './Action/EaseTo'; import { EaseBy } from './Action/EaseBy'; @@ -17,13 +24,16 @@ import { Delay } from './Action/Delay'; import { Die } from './Action/Die'; import { Follow } from './Action/Follow'; import { Meet } from './Action/Meet'; -import { Vector, RotationType } from '../Math'; -import { Entity } from '../EntityComponentSystem/Entity'; -import { Action } from './Action'; -import { Color } from '../Color'; +import type { RotationType } from '../Math'; +import { Vector } from '../Math'; +import type { Entity } from '../EntityComponentSystem/Entity'; +import type { Action } from './Action'; +import type { Color } from '../Color'; import { Flash } from './Action/Flash'; -import { CurveTo, CurveToOptions } from './Action/CurveTo'; -import { CurveBy, CurveByOptions } from './Action/CurveBy'; +import type { CurveToOptions } from './Action/CurveTo'; +import { CurveTo } from './Action/CurveTo'; +import type { CurveByOptions } from './Action/CurveBy'; +import { CurveBy } from './Action/CurveBy'; /** * The fluent Action API allows you to perform "actions" on diff --git a/src/engine/Actions/ActionQueue.ts b/src/engine/Actions/ActionQueue.ts index 500ff9ab..e2d8b738 100644 --- a/src/engine/Actions/ActionQueue.ts +++ b/src/engine/Actions/ActionQueue.ts @@ -1,6 +1,6 @@ import { ActionCompleteEvent, ActionStartEvent } from '../Events'; -import { Entity } from '../EntityComponentSystem/Entity'; -import { Action } from './Action'; +import type { Entity } from '../EntityComponentSystem/Entity'; +import type { Action } from './Action'; /** * Action Queues represent an ordered sequence of actions diff --git a/src/engine/Actions/Actionable.ts b/src/engine/Actions/Actionable.ts index d8535b5d..a2fe8cc0 100644 --- a/src/engine/Actions/Actionable.ts +++ b/src/engine/Actions/Actionable.ts @@ -1,4 +1,4 @@ -import { ActionContext } from './ActionContext'; +import type { ActionContext } from './ActionContext'; export interface Actionable { actions: ActionContext; diff --git a/src/engine/Actions/ActionsComponent.ts b/src/engine/Actions/ActionsComponent.ts index 8d71f08d..38e39e28 100644 --- a/src/engine/Actions/ActionsComponent.ts +++ b/src/engine/Actions/ActionsComponent.ts @@ -1,18 +1,18 @@ import { ActionContext } from './ActionContext'; import { Component } from '../EntityComponentSystem/Component'; -import { Entity } from '../EntityComponentSystem/Entity'; -import { Actor } from '../Actor'; +import type { Entity } from '../EntityComponentSystem/Entity'; +import type { Actor } from '../Actor'; import { MotionComponent } from '../EntityComponentSystem/Components/MotionComponent'; import { TransformComponent } from '../EntityComponentSystem/Components/TransformComponent'; -import { Vector, RotationType } from '../Math'; -import { EasingFunction } from '../Util/EasingFunctions'; -import { ActionQueue } from './ActionQueue'; -import { Action } from './Action'; -import { Color } from '../Color'; -import { CurveToOptions } from './Action/CurveTo'; -import { CurveByOptions } from './Action/CurveBy'; -import { MoveToOptions } from './Action/MoveTo'; -import { MoveByOptions, RotateByOptions, RotateToOptions, ScaleByOptions, ScaleToOptions } from './index'; +import type { Vector, RotationType } from '../Math'; +import type { EasingFunction } from '../Util/EasingFunctions'; +import type { ActionQueue } from './ActionQueue'; +import type { Action } from './Action'; +import type { Color } from '../Color'; +import type { CurveToOptions } from './Action/CurveTo'; +import type { CurveByOptions } from './Action/CurveBy'; +import type { MoveToOptions } from './Action/MoveTo'; +import type { MoveByOptions, RotateByOptions, RotateToOptions, ScaleByOptions, ScaleToOptions } from './index'; export interface ActionContextMethods extends Pick {} diff --git a/src/engine/Actions/ActionsSystem.ts b/src/engine/Actions/ActionsSystem.ts index bf5ceb81..e32fe9cc 100644 --- a/src/engine/Actions/ActionsSystem.ts +++ b/src/engine/Actions/ActionsSystem.ts @@ -1,4 +1,5 @@ -import { Query, SystemPriority, World } from '../EntityComponentSystem'; +import type { Query, World } from '../EntityComponentSystem'; +import { SystemPriority } from '../EntityComponentSystem'; import { System, SystemType } from '../EntityComponentSystem/System'; import { ActionsComponent } from './ActionsComponent'; diff --git a/src/engine/Actor.ts b/src/engine/Actor.ts index 550d750a..a399e315 100644 --- a/src/engine/Actor.ts +++ b/src/engine/Actor.ts @@ -1,13 +1,8 @@ -import { - KillEvent, - PreUpdateEvent, - PostUpdateEvent, +import type { PostCollisionEvent, PreCollisionEvent, CollisionStartEvent, CollisionEndEvent, - PostKillEvent, - PreKillEvent, EnterViewPortEvent, ExitViewPortEvent, PreDrawEvent, @@ -17,18 +12,20 @@ import { ActionStartEvent, ActionCompleteEvent } from './Events'; -import { Engine } from './Engine'; -import { Color } from './Color'; -import { CanInitialize, CanUpdate, CanBeKilled } from './Interfaces/LifecycleEvents'; -import { Scene } from './Scene'; +import { KillEvent, PreUpdateEvent, PostUpdateEvent, PostKillEvent, PreKillEvent } from './Events'; +import type { Engine } from './Engine'; +import type { Color } from './Color'; +import type { CanInitialize, CanUpdate, CanBeKilled } from './Interfaces/LifecycleEvents'; +import type { Scene } from './Scene'; import { Logger } from './Util/Log'; import { Vector, vec } from './Math/vector'; import { BodyComponent } from './Collision/BodyComponent'; -import { Eventable } from './Interfaces/Evented'; -import { PointerEvents } from './Interfaces/PointerEventHandlers'; +import type { Eventable } from './Interfaces/Evented'; +import type { PointerEvents } from './Interfaces/PointerEventHandlers'; import { CollisionType } from './Collision/CollisionType'; -import { Entity, EntityEvents } from './EntityComponentSystem/Entity'; +import type { EntityEvents } from './EntityComponentSystem/Entity'; +import { Entity } from './EntityComponentSystem/Entity'; import { TransformComponent } from './EntityComponentSystem/Components/TransformComponent'; import { MotionComponent } from './EntityComponentSystem/Components/MotionComponent'; import { GraphicsComponent } from './Graphics/GraphicsComponent'; @@ -36,15 +33,16 @@ import { Rectangle } from './Graphics/Rectangle'; import { ColliderComponent } from './Collision/ColliderComponent'; import { Shape } from './Collision/Colliders/Shape'; import { watch } from './Util/Watch'; -import { Collider, CollisionContact, CollisionGroup, Side } from './Collision/Index'; +import type { Collider, CollisionContact, CollisionGroup, Side } from './Collision/Index'; import { Circle } from './Graphics/Circle'; -import { PointerEvent } from './Input/PointerEvent'; -import { WheelEvent } from './Input/WheelEvent'; +import type { PointerEvent } from './Input/PointerEvent'; +import type { WheelEvent } from './Input/WheelEvent'; import { PointerComponent } from './Input/PointerComponent'; import { ActionsComponent } from './Actions/ActionsComponent'; import { CoordPlane } from './Math/coord-plane'; -import { EventEmitter, EventKey, Handler, Subscription } from './EventEmitter'; -import { Component } from './EntityComponentSystem'; +import type { EventKey, Handler, Subscription } from './EventEmitter'; +import { EventEmitter } from './EventEmitter'; +import type { Component } from './EntityComponentSystem'; /** * Type guard for checking if something is an Actor diff --git a/src/engine/Camera.ts b/src/engine/Camera.ts index f8aad8d0..c530abc8 100644 --- a/src/engine/Camera.ts +++ b/src/engine/Camera.ts @@ -1,16 +1,18 @@ -import { Engine } from './Engine'; -import { Screen } from './Screen'; -import { EasingFunction, EasingFunctions } from './Util/EasingFunctions'; +import type { Engine } from './Engine'; +import type { Screen } from './Screen'; +import type { EasingFunction } from './Util/EasingFunctions'; +import { EasingFunctions } from './Util/EasingFunctions'; import { Vector, vec } from './Math/vector'; -import { Actor } from './Actor'; +import type { Actor } from './Actor'; import { removeItemFromArray } from './Util/Util'; -import { CanUpdate, CanInitialize } from './Interfaces/LifecycleEvents'; +import type { CanUpdate, CanInitialize } from './Interfaces/LifecycleEvents'; import { PreUpdateEvent, PostUpdateEvent, InitializeEvent } from './Events'; import { BoundingBox } from './Collision/BoundingBox'; import { Logger } from './Util/Log'; -import { ExcaliburGraphicsContext } from './Graphics/Context/ExcaliburGraphicsContext'; +import type { ExcaliburGraphicsContext } from './Graphics/Context/ExcaliburGraphicsContext'; import { AffineMatrix } from './Math/affine-matrix'; -import { EventEmitter, EventKey, Handler, Subscription } from './EventEmitter'; +import type { EventKey, Handler, Subscription } from './EventEmitter'; +import { EventEmitter } from './EventEmitter'; import { pixelSnapEpsilon } from './Graphics'; import { sign } from './Math/util'; import { WatchVector } from './Math/watch-vector'; diff --git a/src/engine/Collision/BodyComponent.ts b/src/engine/Collision/BodyComponent.ts index 148d5c86..a752439c 100644 --- a/src/engine/Collision/BodyComponent.ts +++ b/src/engine/Collision/BodyComponent.ts @@ -1,18 +1,20 @@ import { vec, Vector } from '../Math/vector'; import { CollisionType } from './CollisionType'; -import { Clonable } from '../Interfaces/Clonable'; +import type { Clonable } from '../Interfaces/Clonable'; import { TransformComponent } from '../EntityComponentSystem/Components/TransformComponent'; import { MotionComponent } from '../EntityComponentSystem/Components/MotionComponent'; import { Component } from '../EntityComponentSystem/Component'; import { CollisionGroup } from './Group/CollisionGroup'; -import { createId, Id } from '../Id'; +import type { Id } from '../Id'; +import { createId } from '../Id'; import { clamp } from '../Math/util'; import { ColliderComponent } from './ColliderComponent'; import { Transform } from '../Math/transform'; import { EventEmitter } from '../EventEmitter'; -import { getDefaultPhysicsConfig, PhysicsConfig } from './PhysicsConfig'; -import { DeepRequired } from '../Util/Required'; -import { Entity } from '../EntityComponentSystem'; +import type { PhysicsConfig } from './PhysicsConfig'; +import { getDefaultPhysicsConfig } from './PhysicsConfig'; +import type { DeepRequired } from '../Util/Required'; +import type { Entity } from '../EntityComponentSystem'; export interface BodyComponentOptions { type?: CollisionType; diff --git a/src/engine/Collision/BoundingBox.ts b/src/engine/Collision/BoundingBox.ts index e98486b8..700e09bd 100644 --- a/src/engine/Collision/BoundingBox.ts +++ b/src/engine/Collision/BoundingBox.ts @@ -1,9 +1,9 @@ import { Vector } from '../Math/vector'; -import { Ray } from '../Math/ray'; +import type { Ray } from '../Math/ray'; import { Color } from '../Color'; import { Side } from './Side'; -import { ExcaliburGraphicsContext } from '../Graphics/Context/ExcaliburGraphicsContext'; -import { AffineMatrix } from '../Math/affine-matrix'; +import type { ExcaliburGraphicsContext } from '../Graphics/Context/ExcaliburGraphicsContext'; +import type { AffineMatrix } from '../Math/affine-matrix'; export interface BoundingBoxOptions { left: number; diff --git a/src/engine/Collision/ColliderComponent.ts b/src/engine/Collision/ColliderComponent.ts index 1f8c75a3..47358650 100644 --- a/src/engine/Collision/ColliderComponent.ts +++ b/src/engine/Collision/ColliderComponent.ts @@ -1,16 +1,16 @@ import { Vector } from '../Math/vector'; import { TransformComponent } from '../EntityComponentSystem'; import { Component } from '../EntityComponentSystem/Component'; -import { Entity } from '../EntityComponentSystem/Entity'; +import type { Entity } from '../EntityComponentSystem/Entity'; import { CollisionEndEvent, CollisionStartEvent, PostCollisionEvent, PreCollisionEvent } from '../Events'; import { Observable } from '../Util/Observable'; import { BoundingBox } from './BoundingBox'; -import { CollisionContact } from './Detection/CollisionContact'; -import { CircleCollider } from './Colliders/CircleCollider'; -import { Collider } from './Colliders/Collider'; +import type { CollisionContact } from './Detection/CollisionContact'; +import type { CircleCollider } from './Colliders/CircleCollider'; +import type { Collider } from './Colliders/Collider'; import { CompositeCollider } from './Colliders/CompositeCollider'; -import { PolygonCollider } from './Colliders/PolygonCollider'; -import { EdgeCollider } from './Colliders/EdgeCollider'; +import type { PolygonCollider } from './Colliders/PolygonCollider'; +import type { EdgeCollider } from './Colliders/EdgeCollider'; import { Shape } from './Colliders/Shape'; import { EventEmitter } from '../EventEmitter'; import { Actor } from '../Actor'; diff --git a/src/engine/Collision/Colliders/CircleCollider.ts b/src/engine/Collision/Colliders/CircleCollider.ts index b1987d7b..bc238d44 100644 --- a/src/engine/Collision/Colliders/CircleCollider.ts +++ b/src/engine/Collision/Colliders/CircleCollider.ts @@ -1,22 +1,22 @@ import { BoundingBox } from '../BoundingBox'; import { CollisionJumpTable } from './CollisionJumpTable'; -import { CollisionContact } from '../Detection/CollisionContact'; +import type { CollisionContact } from '../Detection/CollisionContact'; import { PolygonCollider } from './PolygonCollider'; import { EdgeCollider } from './EdgeCollider'; import { Projection } from '../../Math/projection'; -import { LineSegment } from '../../Math/line-segment'; +import type { LineSegment } from '../../Math/line-segment'; import { Vector } from '../../Math/vector'; -import { Ray } from '../../Math/ray'; +import type { Ray } from '../../Math/ray'; import { Color } from '../../Color'; import { Collider } from './Collider'; import { ClosestLineJumpTable } from './ClosestLineJumpTable'; -import { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; -import { Transform } from '../../Math/transform'; +import type { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; +import type { Transform } from '../../Math/transform'; import { AffineMatrix } from '../../Math/affine-matrix'; import { BodyComponent } from '../Index'; -import { RayCastHit } from '../Detection/RayCastHit'; +import type { RayCastHit } from '../Detection/RayCastHit'; import { approximatelyEqual } from '../../Math/util'; export interface CircleColliderOptions { diff --git a/src/engine/Collision/Colliders/ClosestLineJumpTable.ts b/src/engine/Collision/Colliders/ClosestLineJumpTable.ts index 86f4f4cc..ddea0d00 100644 --- a/src/engine/Collision/Colliders/ClosestLineJumpTable.ts +++ b/src/engine/Collision/Colliders/ClosestLineJumpTable.ts @@ -1,9 +1,9 @@ import { LineSegment } from '../../Math/line-segment'; import { Vector } from '../../Math/vector'; import { Ray } from '../../Math/ray'; -import { PolygonCollider } from './PolygonCollider'; -import { EdgeCollider } from './EdgeCollider'; -import { CircleCollider } from './CircleCollider'; +import type { PolygonCollider } from './PolygonCollider'; +import type { EdgeCollider } from './EdgeCollider'; +import type { CircleCollider } from './CircleCollider'; import { clamp } from '../../Math/util'; /** diff --git a/src/engine/Collision/Colliders/Collider.ts b/src/engine/Collision/Colliders/Collider.ts index 5de0ac5c..25de2074 100644 --- a/src/engine/Collision/Colliders/Collider.ts +++ b/src/engine/Collision/Colliders/Collider.ts @@ -1,18 +1,19 @@ -import { Color } from '../../Color'; -import { CollisionContact } from '../Detection/CollisionContact'; -import { BoundingBox } from '../BoundingBox'; -import { Projection } from '../../Math/projection'; -import { LineSegment } from '../../Math/line-segment'; +import type { Color } from '../../Color'; +import type { CollisionContact } from '../Detection/CollisionContact'; +import type { BoundingBox } from '../BoundingBox'; +import type { Projection } from '../../Math/projection'; +import type { LineSegment } from '../../Math/line-segment'; import { Vector } from '../../Math/vector'; -import { Ray } from '../../Math/ray'; -import { Clonable } from '../../Interfaces/Clonable'; -import { Entity } from '../../EntityComponentSystem'; -import { createId, Id } from '../../Id'; -import { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; -import { Transform } from '../../Math/transform'; +import type { Ray } from '../../Math/ray'; +import type { Clonable } from '../../Interfaces/Clonable'; +import type { Entity } from '../../EntityComponentSystem'; +import type { Id } from '../../Id'; +import { createId } from '../../Id'; +import type { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; +import type { Transform } from '../../Math/transform'; import { EventEmitter } from '../../EventEmitter'; -import { RayCastHit } from '../Detection/RayCastHit'; -import { CompositeCollider } from './CompositeCollider'; +import type { RayCastHit } from '../Detection/RayCastHit'; +import type { CompositeCollider } from './CompositeCollider'; /** * A collision collider specifies the geometry that can detect when other collision colliders intersect diff --git a/src/engine/Collision/Colliders/CollisionJumpTable.ts b/src/engine/Collision/Colliders/CollisionJumpTable.ts index d63e6b87..5af8e5f1 100644 --- a/src/engine/Collision/Colliders/CollisionJumpTable.ts +++ b/src/engine/Collision/Colliders/CollisionJumpTable.ts @@ -2,7 +2,8 @@ import { CollisionContact } from '../Detection/CollisionContact'; import { PolygonCollider } from './PolygonCollider'; import { EdgeCollider } from './EdgeCollider'; -import { SeparatingAxis, SeparationInfo } from './SeparatingAxis'; +import type { SeparationInfo } from './SeparatingAxis'; +import { SeparatingAxis } from './SeparatingAxis'; import { LineSegment } from '../../Math/line-segment'; import { Vector } from '../../Math/vector'; import { TransformComponent } from '../../EntityComponentSystem'; diff --git a/src/engine/Collision/Colliders/CompositeCollider.ts b/src/engine/Collision/Colliders/CompositeCollider.ts index 8700b9b3..b7195f1f 100644 --- a/src/engine/Collision/Colliders/CompositeCollider.ts +++ b/src/engine/Collision/Colliders/CompositeCollider.ts @@ -1,18 +1,18 @@ import { Util } from '../..'; import { Pair } from '../Detection/Pair'; -import { Color } from '../../Color'; -import { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; -import { LineSegment } from '../../Math/line-segment'; +import type { Color } from '../../Color'; +import type { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; +import type { LineSegment } from '../../Math/line-segment'; import { Projection } from '../../Math/projection'; -import { Ray } from '../../Math/ray'; +import type { Ray } from '../../Math/ray'; import { Vector } from '../../Math/vector'; import { BoundingBox } from '../BoundingBox'; -import { CollisionContact } from '../Detection/CollisionContact'; +import type { CollisionContact } from '../Detection/CollisionContact'; import { DynamicTree } from '../Detection/DynamicTree'; import { DynamicTreeCollisionProcessor } from '../Detection/DynamicTreeCollisionProcessor'; -import { RayCastHit } from '../Detection/RayCastHit'; +import type { RayCastHit } from '../Detection/RayCastHit'; import { Collider } from './Collider'; -import { Transform } from '../../Math/transform'; +import type { Transform } from '../../Math/transform'; import { getDefaultPhysicsConfig } from '../PhysicsConfig'; export class CompositeCollider extends Collider { diff --git a/src/engine/Collision/Colliders/EdgeCollider.ts b/src/engine/Collision/Colliders/EdgeCollider.ts index 77a3b671..9bbc9a78 100644 --- a/src/engine/Collision/Colliders/EdgeCollider.ts +++ b/src/engine/Collision/Colliders/EdgeCollider.ts @@ -1,5 +1,5 @@ import { BoundingBox } from '../BoundingBox'; -import { CollisionContact } from '../Detection/CollisionContact'; +import type { CollisionContact } from '../Detection/CollisionContact'; import { CollisionJumpTable } from './CollisionJumpTable'; import { CircleCollider } from './CircleCollider'; import { PolygonCollider } from './PolygonCollider'; @@ -7,15 +7,15 @@ import { PolygonCollider } from './PolygonCollider'; import { Projection } from '../../Math/projection'; import { LineSegment } from '../../Math/line-segment'; import { Vector } from '../../Math/vector'; -import { Ray } from '../../Math/ray'; -import { Color } from '../../Color'; +import type { Ray } from '../../Math/ray'; +import type { Color } from '../../Color'; import { Collider } from './Collider'; import { ClosestLineJumpTable } from './ClosestLineJumpTable'; -import { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; -import { Transform } from '../../Math/transform'; +import type { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; +import type { Transform } from '../../Math/transform'; import { AffineMatrix } from '../../Math/affine-matrix'; import { BodyComponent } from '../Index'; -import { RayCastHit } from '../Detection/RayCastHit'; +import type { RayCastHit } from '../Detection/RayCastHit'; export interface EdgeColliderOptions { /** diff --git a/src/engine/Collision/Colliders/PolygonCollider.ts b/src/engine/Collision/Colliders/PolygonCollider.ts index caae1cc5..2c340a6e 100644 --- a/src/engine/Collision/Colliders/PolygonCollider.ts +++ b/src/engine/Collision/Colliders/PolygonCollider.ts @@ -1,20 +1,21 @@ -import { Color } from '../../Color'; +import type { Color } from '../../Color'; import { BoundingBox } from '../BoundingBox'; import { EdgeCollider } from './EdgeCollider'; import { CollisionJumpTable } from './CollisionJumpTable'; import { CircleCollider } from './CircleCollider'; -import { CollisionContact } from '../Detection/CollisionContact'; +import type { CollisionContact } from '../Detection/CollisionContact'; import { Projection } from '../../Math/projection'; import { LineSegment } from '../../Math/line-segment'; import { Vector, vec } from '../../Math/vector'; import { Ray } from '../../Math/ray'; import { ClosestLineJumpTable } from './ClosestLineJumpTable'; import { Collider } from './Collider'; -import { BodyComponent, Debug, ExcaliburGraphicsContext, Logger, sign } from '../..'; +import type { ExcaliburGraphicsContext } from '../..'; +import { BodyComponent, Debug, Logger, sign } from '../..'; import { CompositeCollider } from './CompositeCollider'; import { Shape } from './Shape'; import { Transform } from '../../Math/transform'; -import { RayCastHit } from '../Detection/RayCastHit'; +import type { RayCastHit } from '../Detection/RayCastHit'; export interface PolygonColliderOptions { /** diff --git a/src/engine/Collision/Colliders/SeparatingAxis.ts b/src/engine/Collision/Colliders/SeparatingAxis.ts index a1c99ecb..ec68ad5d 100644 --- a/src/engine/Collision/Colliders/SeparatingAxis.ts +++ b/src/engine/Collision/Colliders/SeparatingAxis.ts @@ -1,8 +1,9 @@ import { LineSegment } from '../../Math/line-segment'; -import { Vector, vec } from '../../Math/vector'; -import { Collider } from './Collider'; -import { CircleCollider } from './CircleCollider'; -import { PolygonCollider } from './PolygonCollider'; +import type { Vector } from '../../Math/vector'; +import { vec } from '../../Math/vector'; +import type { Collider } from './Collider'; +import type { CircleCollider } from './CircleCollider'; +import type { PolygonCollider } from './PolygonCollider'; import { AffineMatrix } from '../../Math/affine-matrix'; import { Pool } from '../../Util/Pool'; diff --git a/src/engine/Collision/CollisionSystem.ts b/src/engine/Collision/CollisionSystem.ts index 1356401e..89c95ce3 100644 --- a/src/engine/Collision/CollisionSystem.ts +++ b/src/engine/Collision/CollisionSystem.ts @@ -1,22 +1,23 @@ -import { ComponentCtor, Query, SystemPriority, World } from '../EntityComponentSystem'; +import type { ComponentCtor, Query, World } from '../EntityComponentSystem'; +import { SystemPriority } from '../EntityComponentSystem'; import { MotionComponent } from '../EntityComponentSystem/Components/MotionComponent'; import { TransformComponent } from '../EntityComponentSystem/Components/TransformComponent'; import { System, SystemType } from '../EntityComponentSystem/System'; import { CollisionEndEvent, CollisionStartEvent, ContactEndEvent, ContactStartEvent } from '../Events'; import { SolverStrategy } from './SolverStrategy'; import { ArcadeSolver } from './Solver/ArcadeSolver'; -import { Collider } from './Colliders/Collider'; -import { CollisionContact } from './Detection/CollisionContact'; +import type { Collider } from './Colliders/Collider'; +import type { CollisionContact } from './Detection/CollisionContact'; import { RealisticSolver } from './Solver/RealisticSolver'; -import { CollisionSolver } from './Solver/Solver'; +import type { CollisionSolver } from './Solver/Solver'; import { ColliderComponent } from './ColliderComponent'; import { CompositeCollider } from './Colliders/CompositeCollider'; -import { Engine } from '../Engine'; -import { ExcaliburGraphicsContext } from '../Graphics/Context/ExcaliburGraphicsContext'; -import { Scene } from '../Scene'; +import type { Engine } from '../Engine'; +import type { ExcaliburGraphicsContext } from '../Graphics/Context/ExcaliburGraphicsContext'; +import type { Scene } from '../Scene'; import { Side } from '../Collision/Side'; -import { PhysicsWorld } from './PhysicsWorld'; -import { CollisionProcessor } from './Detection/CollisionProcessor'; +import type { PhysicsWorld } from './PhysicsWorld'; +import type { CollisionProcessor } from './Detection/CollisionProcessor'; import { SeparatingAxis } from './Colliders/SeparatingAxis'; import { MotionSystem } from './MotionSystem'; import { Pair } from './Detection/Pair'; diff --git a/src/engine/Collision/Detection/CollisionContact.ts b/src/engine/Collision/Detection/CollisionContact.ts index 8f50698a..f5e2bbc8 100644 --- a/src/engine/Collision/Detection/CollisionContact.ts +++ b/src/engine/Collision/Detection/CollisionContact.ts @@ -1,8 +1,8 @@ -import { Vector } from '../../Math/vector'; -import { Collider } from '../Colliders/Collider'; +import type { Vector } from '../../Math/vector'; +import type { Collider } from '../Colliders/Collider'; import { CollisionType } from '../CollisionType'; import { Pair } from './Pair'; -import { SeparationInfo } from '../Colliders/SeparatingAxis'; +import type { SeparationInfo } from '../Colliders/SeparatingAxis'; import { BodyComponent } from '../BodyComponent'; /** diff --git a/src/engine/Collision/Detection/CollisionProcessor.ts b/src/engine/Collision/Detection/CollisionProcessor.ts index f6220e55..9e732fe9 100644 --- a/src/engine/Collision/Detection/CollisionProcessor.ts +++ b/src/engine/Collision/Detection/CollisionProcessor.ts @@ -1,13 +1,13 @@ -import { FrameStats } from '../../Debug'; -import { Pair } from './Pair'; -import { Collider } from '../Colliders/Collider'; -import { CollisionContact } from './CollisionContact'; -import { RayCastOptions } from './RayCastOptions'; -import { Ray } from '../../Math/ray'; -import { RayCastHit } from './RayCastHit'; -import { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; -import { BoundingBox } from '../BoundingBox'; -import { Vector } from '../../Math/vector'; +import type { FrameStats } from '../../Debug'; +import type { Pair } from './Pair'; +import type { Collider } from '../Colliders/Collider'; +import type { CollisionContact } from './CollisionContact'; +import type { RayCastOptions } from './RayCastOptions'; +import type { Ray } from '../../Math/ray'; +import type { RayCastHit } from './RayCastHit'; +import type { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; +import type { BoundingBox } from '../BoundingBox'; +import type { Vector } from '../../Math/vector'; /** * Definition for collision processor diff --git a/src/engine/Collision/Detection/DynamicTree.ts b/src/engine/Collision/Detection/DynamicTree.ts index e0a1bde2..c00cf47b 100644 --- a/src/engine/Collision/Detection/DynamicTree.ts +++ b/src/engine/Collision/Detection/DynamicTree.ts @@ -1,11 +1,12 @@ import { BoundingBox } from '../BoundingBox'; -import { Ray } from '../../Math/ray'; +import type { Ray } from '../../Math/ray'; import { Logger } from '../../Util/Log'; -import { Id } from '../../Id'; -import { Entity } from '../../EntityComponentSystem/Entity'; +import type { Id } from '../../Id'; +import type { Entity } from '../../EntityComponentSystem/Entity'; import { BodyComponent } from '../BodyComponent'; -import { Color, ExcaliburGraphicsContext } from '../..'; -import { DynamicTreeConfig } from '../PhysicsConfig'; +import type { ExcaliburGraphicsContext } from '../..'; +import { Color } from '../..'; +import type { DynamicTreeConfig } from '../PhysicsConfig'; /** * Dynamic Tree Node used for tracking bounds within the tree diff --git a/src/engine/Collision/Detection/DynamicTreeCollisionProcessor.ts b/src/engine/Collision/Detection/DynamicTreeCollisionProcessor.ts index 85ee04f4..5dee7429 100644 --- a/src/engine/Collision/Detection/DynamicTreeCollisionProcessor.ts +++ b/src/engine/Collision/Detection/DynamicTreeCollisionProcessor.ts @@ -1,22 +1,22 @@ -import { CollisionProcessor } from './CollisionProcessor'; +import type { CollisionProcessor } from './CollisionProcessor'; import { DynamicTree } from './DynamicTree'; import { Pair } from './Pair'; import { Vector } from '../../Math/vector'; import { Ray } from '../../Math/ray'; -import { FrameStats } from '../../Debug'; +import type { FrameStats } from '../../Debug'; import { Logger } from '../../Util/Log'; import { CollisionType } from '../CollisionType'; -import { Collider } from '../Colliders/Collider'; -import { CollisionContact } from '../Detection/CollisionContact'; +import type { Collider } from '../Colliders/Collider'; +import type { CollisionContact } from '../Detection/CollisionContact'; import { BodyComponent } from '../BodyComponent'; import { CompositeCollider } from '../Colliders/CompositeCollider'; import { CollisionGroup } from '../Group/CollisionGroup'; -import { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; -import { RayCastHit } from './RayCastHit'; -import { DeepRequired } from '../../Util/Required'; -import { PhysicsConfig } from '../PhysicsConfig'; -import { RayCastOptions } from './RayCastOptions'; +import type { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; +import type { RayCastHit } from './RayCastHit'; +import type { DeepRequired } from '../../Util/Required'; +import type { PhysicsConfig } from '../PhysicsConfig'; +import type { RayCastOptions } from './RayCastOptions'; import { BoundingBox } from '../BoundingBox'; import { createId } from '../../Id'; diff --git a/src/engine/Collision/Detection/Pair.ts b/src/engine/Collision/Detection/Pair.ts index 29ba01be..440051e0 100644 --- a/src/engine/Collision/Detection/Pair.ts +++ b/src/engine/Collision/Detection/Pair.ts @@ -1,8 +1,8 @@ -import { CollisionContact } from './CollisionContact'; +import type { CollisionContact } from './CollisionContact'; import { CollisionType } from '../CollisionType'; import { BodyComponent } from '../BodyComponent'; -import { Id } from '../../Id'; -import { Collider } from '../Colliders/Collider'; +import type { Id } from '../../Id'; +import type { Collider } from '../Colliders/Collider'; /** * Models a potential collision between 2 colliders diff --git a/src/engine/Collision/Detection/QuadTree.ts b/src/engine/Collision/Detection/QuadTree.ts index 015a1a35..79ea6d0b 100644 --- a/src/engine/Collision/Detection/QuadTree.ts +++ b/src/engine/Collision/Detection/QuadTree.ts @@ -1,5 +1,5 @@ import { Color } from '../../Color'; -import { ExcaliburGraphicsContext } from '../../Graphics'; +import type { ExcaliburGraphicsContext } from '../../Graphics'; import { BoundingBox } from '../BoundingBox'; export interface QuadTreeItem { diff --git a/src/engine/Collision/Detection/RayCastHit.ts b/src/engine/Collision/Detection/RayCastHit.ts index 89979abe..aa490f24 100644 --- a/src/engine/Collision/Detection/RayCastHit.ts +++ b/src/engine/Collision/Detection/RayCastHit.ts @@ -1,6 +1,6 @@ -import { Vector } from '../../Math/vector'; -import { Collider } from '../Colliders/Collider'; -import { BodyComponent } from '../BodyComponent'; +import type { Vector } from '../../Math/vector'; +import type { Collider } from '../Colliders/Collider'; +import type { BodyComponent } from '../BodyComponent'; export interface RayCastHit { /** diff --git a/src/engine/Collision/Detection/RayCastOptions.ts b/src/engine/Collision/Detection/RayCastOptions.ts index 668059e7..1061ce3d 100644 --- a/src/engine/Collision/Detection/RayCastOptions.ts +++ b/src/engine/Collision/Detection/RayCastOptions.ts @@ -1,5 +1,5 @@ -import { CollisionGroup } from '../Group/CollisionGroup'; -import { RayCastHit } from './RayCastHit'; +import type { CollisionGroup } from '../Group/CollisionGroup'; +import type { RayCastHit } from './RayCastHit'; export interface RayCastOptions { /** diff --git a/src/engine/Collision/Detection/SparseHashGrid.ts b/src/engine/Collision/Detection/SparseHashGrid.ts index ac396cee..632bbfb7 100644 --- a/src/engine/Collision/Detection/SparseHashGrid.ts +++ b/src/engine/Collision/Detection/SparseHashGrid.ts @@ -1,6 +1,7 @@ import { Color } from '../../Color'; -import { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; -import { Vector, vec } from '../../Math/vector'; +import type { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; +import type { Vector } from '../../Math/vector'; +import { vec } from '../../Math/vector'; import { RentalPool } from '../../Util/RentalPool'; import { BoundingBox } from '../BoundingBox'; diff --git a/src/engine/Collision/Detection/SparseHashGridCollisionProcessor.ts b/src/engine/Collision/Detection/SparseHashGridCollisionProcessor.ts index 201b611e..f1f6c4f4 100644 --- a/src/engine/Collision/Detection/SparseHashGridCollisionProcessor.ts +++ b/src/engine/Collision/Detection/SparseHashGridCollisionProcessor.ts @@ -1,21 +1,22 @@ -import { FrameStats } from '../../Debug/DebugConfig'; -import { Entity } from '../../EntityComponentSystem'; -import { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; +import type { FrameStats } from '../../Debug/DebugConfig'; +import type { Entity } from '../../EntityComponentSystem'; +import type { ExcaliburGraphicsContext } from '../../Graphics/Context/ExcaliburGraphicsContext'; import { createId } from '../../Id'; -import { Ray } from '../../Math/ray'; -import { Vector, vec } from '../../Math/vector'; +import type { Ray } from '../../Math/ray'; +import type { Vector } from '../../Math/vector'; +import { vec } from '../../Math/vector'; import { Pool } from '../../Util/Pool'; import { BodyComponent } from '../BodyComponent'; -import { BoundingBox } from '../BoundingBox'; -import { Collider } from '../Colliders/Collider'; +import type { BoundingBox } from '../BoundingBox'; +import type { Collider } from '../Colliders/Collider'; import { CompositeCollider } from '../Colliders/CompositeCollider'; import { CollisionType } from '../CollisionType'; import { CollisionGroup } from '../Group/CollisionGroup'; -import { CollisionContact } from './CollisionContact'; -import { CollisionProcessor } from './CollisionProcessor'; +import type { CollisionContact } from './CollisionContact'; +import type { CollisionProcessor } from './CollisionProcessor'; import { Pair } from './Pair'; -import { RayCastHit } from './RayCastHit'; -import { RayCastOptions } from './RayCastOptions'; +import type { RayCastHit } from './RayCastHit'; +import type { RayCastOptions } from './RayCastOptions'; import { HashGridCell, HashGridProxy, SparseHashGrid } from './SparseHashGrid'; /** diff --git a/src/engine/Collision/Integrator.ts b/src/engine/Collision/Integrator.ts index 74f89b77..e51a4368 100644 --- a/src/engine/Collision/Integrator.ts +++ b/src/engine/Collision/Integrator.ts @@ -1,6 +1,6 @@ import { Vector } from '../Math/vector'; -import { TransformComponent } from '../EntityComponentSystem'; -import { MotionComponent } from '../EntityComponentSystem/Components/MotionComponent'; +import type { TransformComponent } from '../EntityComponentSystem'; +import type { MotionComponent } from '../EntityComponentSystem/Components/MotionComponent'; export class EulerIntegrator { // Scratch vectors to avoid allocation diff --git a/src/engine/Collision/MotionSystem.ts b/src/engine/Collision/MotionSystem.ts index 1c9f0997..8380b3bf 100644 --- a/src/engine/Collision/MotionSystem.ts +++ b/src/engine/Collision/MotionSystem.ts @@ -1,11 +1,12 @@ -import { Entity, Query, SystemPriority, World } from '../EntityComponentSystem'; +import type { Entity, Query, World } from '../EntityComponentSystem'; +import { SystemPriority } from '../EntityComponentSystem'; import { MotionComponent } from '../EntityComponentSystem/Components/MotionComponent'; import { TransformComponent } from '../EntityComponentSystem/Components/TransformComponent'; import { System, SystemType } from '../EntityComponentSystem/System'; import { BodyComponent } from './BodyComponent'; import { CollisionType } from './CollisionType'; import { EulerIntegrator } from './Integrator'; -import { PhysicsWorld } from './PhysicsWorld'; +import type { PhysicsWorld } from './PhysicsWorld'; export class MotionSystem extends System { static priority = SystemPriority.Higher; diff --git a/src/engine/Collision/PhysicsConfig.ts b/src/engine/Collision/PhysicsConfig.ts index 52bc2d9f..19d4c2f0 100644 --- a/src/engine/Collision/PhysicsConfig.ts +++ b/src/engine/Collision/PhysicsConfig.ts @@ -1,5 +1,6 @@ -import { Vector, vec } from '../Math/vector'; -import { DeepRequired } from '../Util/Required'; +import type { Vector } from '../Math/vector'; +import { vec } from '../Math/vector'; +import type { DeepRequired } from '../Util/Required'; import { SolverStrategy } from './SolverStrategy'; import { ContactSolveBias } from './Solver/ContactBias'; import { SpatialPartitionStrategy } from './Detection/SpatialPartitionStrategy'; diff --git a/src/engine/Collision/PhysicsWorld.ts b/src/engine/Collision/PhysicsWorld.ts index 243b0173..f22f3e9b 100644 --- a/src/engine/Collision/PhysicsWorld.ts +++ b/src/engine/Collision/PhysicsWorld.ts @@ -1,19 +1,12 @@ -import { Ray } from '../Math/ray'; -import { DeepRequired } from '../Util/Required'; +import type { Ray } from '../Math/ray'; +import type { DeepRequired } from '../Util/Required'; import { Observable } from '../Util/Observable'; -import { - BoundingBox, - Collider, - CollisionProcessor, - DynamicTreeCollisionProcessor, - RayCastHit, - RayCastOptions, - SparseHashGridCollisionProcessor -} from './Index'; +import type { BoundingBox, Collider, CollisionProcessor, RayCastHit, RayCastOptions } from './Index'; +import { DynamicTreeCollisionProcessor, SparseHashGridCollisionProcessor } from './Index'; import { BodyComponent } from './BodyComponent'; -import { PhysicsConfig } from './PhysicsConfig'; +import type { PhysicsConfig } from './PhysicsConfig'; import { watchDeep } from '../Util/Watch'; -import { Vector } from '../Math/vector'; +import type { Vector } from '../Math/vector'; import { SpatialPartitionStrategy } from './Detection/SpatialPartitionStrategy'; export class PhysicsWorld { diff --git a/src/engine/Collision/Side.ts b/src/engine/Collision/Side.ts index e27547d6..cd522169 100644 --- a/src/engine/Collision/Side.ts +++ b/src/engine/Collision/Side.ts @@ -1,4 +1,4 @@ -import { Vector } from '../Math/vector'; +import type { Vector } from '../Math/vector'; /** * An enum that describes the sides of an axis aligned box for collision diff --git a/src/engine/Collision/Solver/ArcadeSolver.ts b/src/engine/Collision/Solver/ArcadeSolver.ts index 523bfe89..69d81a48 100644 --- a/src/engine/Collision/Solver/ArcadeSolver.ts +++ b/src/engine/Collision/Solver/ArcadeSolver.ts @@ -1,12 +1,13 @@ import { PostCollisionEvent, PreCollisionEvent } from '../../Events'; -import { CollisionContact } from '../Detection/CollisionContact'; +import type { CollisionContact } from '../Detection/CollisionContact'; import { CollisionType } from '../CollisionType'; import { Side } from '../Side'; -import { CollisionSolver } from './Solver'; +import type { CollisionSolver } from './Solver'; import { BodyComponent } from '../BodyComponent'; -import { ContactBias, ContactSolveBias, HorizontalFirst, None, VerticalFirst } from './ContactBias'; -import { PhysicsConfig } from '../PhysicsConfig'; -import { DeepRequired } from '../../Util/Required'; +import type { ContactBias } from './ContactBias'; +import { ContactSolveBias, HorizontalFirst, None, VerticalFirst } from './ContactBias'; +import type { PhysicsConfig } from '../PhysicsConfig'; +import type { DeepRequired } from '../../Util/Required'; /** * ArcadeSolver is the default in Excalibur. It solves collisions so that there is no overlap between contacts, diff --git a/src/engine/Collision/Solver/ContactConstraintPoint.ts b/src/engine/Collision/Solver/ContactConstraintPoint.ts index a160e619..c62315f6 100644 --- a/src/engine/Collision/Solver/ContactConstraintPoint.ts +++ b/src/engine/Collision/Solver/ContactConstraintPoint.ts @@ -1,5 +1,5 @@ import { Vector } from '../../Math/vector'; -import { CollisionContact } from '../Detection/CollisionContact'; +import type { CollisionContact } from '../Detection/CollisionContact'; /** * Holds information about contact points, meant to be reused over multiple frames of contact diff --git a/src/engine/Collision/Solver/RealisticSolver.ts b/src/engine/Collision/Solver/RealisticSolver.ts index 0320e9a8..63bea6c2 100644 --- a/src/engine/Collision/Solver/RealisticSolver.ts +++ b/src/engine/Collision/Solver/RealisticSolver.ts @@ -1,15 +1,16 @@ import { CollisionPostSolveEvent, CollisionPreSolveEvent, PostCollisionEvent, PreCollisionEvent } from '../../Events'; import { clamp } from '../../Math/util'; -import { CollisionContact } from '../Detection/CollisionContact'; +import type { CollisionContact } from '../Detection/CollisionContact'; import { CollisionType } from '../CollisionType'; import { ContactConstraintPoint } from './ContactConstraintPoint'; import { Side } from '../Side'; -import { CollisionSolver } from './Solver'; +import type { CollisionSolver } from './Solver'; import { DegreeOfFreedom } from '../BodyComponent'; import { CollisionJumpTable } from '../Colliders/CollisionJumpTable'; -import { DeepRequired } from '../../Util/Required'; -import { PhysicsConfig } from '../PhysicsConfig'; -import { ContactBias, ContactSolveBias, HorizontalFirst, None, VerticalFirst } from './ContactBias'; +import type { DeepRequired } from '../../Util/Required'; +import type { PhysicsConfig } from '../PhysicsConfig'; +import type { ContactBias } from './ContactBias'; +import { ContactSolveBias, HorizontalFirst, None, VerticalFirst } from './ContactBias'; export class RealisticSolver implements CollisionSolver { directionMap = new Map(); diff --git a/src/engine/Collision/Solver/Solver.ts b/src/engine/Collision/Solver/Solver.ts index f9dae8e3..8ebf18eb 100644 --- a/src/engine/Collision/Solver/Solver.ts +++ b/src/engine/Collision/Solver/Solver.ts @@ -1,4 +1,4 @@ -import { CollisionContact } from '../Detection/CollisionContact'; +import type { CollisionContact } from '../Detection/CollisionContact'; /** * A collision solver figures out how to position colliders such that they are no longer overlapping diff --git a/src/engine/Debug/DebugConfig.ts b/src/engine/Debug/DebugConfig.ts index a9cb3607..8a98a6d6 100644 --- a/src/engine/Debug/DebugConfig.ts +++ b/src/engine/Debug/DebugConfig.ts @@ -1,8 +1,8 @@ import { ColorBlindFlags } from './DebugFlags'; -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; import { Color } from '../Color'; -import { CollisionContact } from '../Collision/Detection/CollisionContact'; -import { StandardClock, TestClock } from '../Util/Clock'; +import type { CollisionContact } from '../Collision/Detection/CollisionContact'; +import type { StandardClock, TestClock } from '../Util/Clock'; /** * Debug stats containing current and previous frame statistics diff --git a/src/engine/Debug/DebugFlags.ts b/src/engine/Debug/DebugFlags.ts index bc4d3295..73039805 100644 --- a/src/engine/Debug/DebugFlags.ts +++ b/src/engine/Debug/DebugFlags.ts @@ -1,6 +1,6 @@ import { ColorBlindnessMode } from '../Graphics/PostProcessor/ColorBlindnessMode'; import { ColorBlindnessPostProcessor } from '../Graphics/PostProcessor/ColorBlindnessPostProcessor'; -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; import { ExcaliburGraphicsContextWebGL } from '../Graphics/Context/ExcaliburGraphicsContextWebGL'; export class ColorBlindFlags { diff --git a/src/engine/Debug/DebugSystem.ts b/src/engine/Debug/DebugSystem.ts index dd23c9aa..57d38046 100644 --- a/src/engine/Debug/DebugSystem.ts +++ b/src/engine/Debug/DebugSystem.ts @@ -1,11 +1,12 @@ -import { Engine } from '../Engine'; -import { Scene } from '../Scene'; -import { Camera } from '../Camera'; +import type { Engine } from '../Engine'; +import type { Scene } from '../Scene'; +import type { Camera } from '../Camera'; import { MotionComponent } from '../EntityComponentSystem/Components/MotionComponent'; import { ColliderComponent } from '../Collision/ColliderComponent'; -import { Entity, Query, SystemPriority, TransformComponent, World } from '../EntityComponentSystem'; +import type { Entity, Query, World } from '../EntityComponentSystem'; +import { SystemPriority, TransformComponent } from '../EntityComponentSystem'; import { System, SystemType } from '../EntityComponentSystem/System'; -import { ExcaliburGraphicsContext } from '../Graphics/Context/ExcaliburGraphicsContext'; +import type { ExcaliburGraphicsContext } from '../Graphics/Context/ExcaliburGraphicsContext'; import { vec, Vector } from '../Math/vector'; import { toDegrees } from '../Math/util'; import { BodyComponent } from '../Collision/BodyComponent'; diff --git a/src/engine/Director/CrossFade.ts b/src/engine/Director/CrossFade.ts index b1da77f1..e17033e5 100644 --- a/src/engine/Director/CrossFade.ts +++ b/src/engine/Director/CrossFade.ts @@ -1,7 +1,9 @@ -import { ImageSource, Sprite } from '../Graphics'; -import { Engine } from '../Engine'; -import { Scene } from '../Scene'; -import { Transition, TransitionOptions } from './Transition'; +import type { Sprite } from '../Graphics'; +import { ImageSource } from '../Graphics'; +import type { Engine } from '../Engine'; +import type { Scene } from '../Scene'; +import type { TransitionOptions } from './Transition'; +import { Transition } from './Transition'; import { vec } from '../Math/vector'; export interface CrossFadeOptions { diff --git a/src/engine/Director/DefaultLoader.ts b/src/engine/Director/DefaultLoader.ts index 1b9e24f5..ab972a7c 100644 --- a/src/engine/Director/DefaultLoader.ts +++ b/src/engine/Director/DefaultLoader.ts @@ -1,12 +1,13 @@ import { WebAudio } from '../Util/WebAudio'; -import { Engine } from '../Engine'; -import { Loadable } from '../Interfaces/Loadable'; +import type { Engine } from '../Engine'; +import type { Loadable } from '../Interfaces/Loadable'; import { Canvas } from '../Graphics/Canvas'; import { ImageFiltering } from '../Graphics/Filtering'; import { clamp } from '../Math/util'; import { Sound } from '../Resources/Sound/Sound'; import { Future } from '../Util/Future'; -import { EventEmitter, EventKey, Handler, Subscription } from '../EventEmitter'; +import type { EventKey, Handler, Subscription } from '../EventEmitter'; +import { EventEmitter } from '../EventEmitter'; import { Color } from '../Color'; import { delay } from '../Util/Util'; diff --git a/src/engine/Director/Director.ts b/src/engine/Director/Director.ts index 6e5d7624..dc3942c0 100644 --- a/src/engine/Director/Director.ts +++ b/src/engine/Director/Director.ts @@ -1,7 +1,9 @@ -import { Engine } from '../Engine'; -import { DefaultLoader, LoaderConstructor, isLoaderConstructor } from './DefaultLoader'; -import { Scene, SceneConstructor, isSceneConstructor } from '../Scene'; -import { Transition } from './Transition'; +import type { Engine } from '../Engine'; +import type { LoaderConstructor } from './DefaultLoader'; +import { DefaultLoader, isLoaderConstructor } from './DefaultLoader'; +import type { SceneConstructor } from '../Scene'; +import { Scene, isSceneConstructor } from '../Scene'; +import type { Transition } from './Transition'; import { Loader } from './Loader'; import { Logger } from '../Util/Log'; import { ActivateEvent, DeactivateEvent } from '../Events'; diff --git a/src/engine/Director/FadeInOut.ts b/src/engine/Director/FadeInOut.ts index d0a1ea01..6fd9da39 100644 --- a/src/engine/Director/FadeInOut.ts +++ b/src/engine/Director/FadeInOut.ts @@ -1,7 +1,8 @@ -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; import { Color } from '../Color'; import { Rectangle } from '../Graphics'; -import { Transition, TransitionOptions } from './Transition'; +import type { TransitionOptions } from './Transition'; +import { Transition } from './Transition'; export interface FadeOptions { duration?: number; diff --git a/src/engine/Director/Loader.ts b/src/engine/Director/Loader.ts index 56286d3a..69be3e26 100644 --- a/src/engine/Director/Loader.ts +++ b/src/engine/Director/Loader.ts @@ -1,15 +1,16 @@ import { Color } from '../Color'; -import { Loadable } from '../Interfaces/Loadable'; +import type { Loadable } from '../Interfaces/Loadable'; import * as DrawUtil from '../Util/DrawUtil'; import logoImg from './Loader.logo.png'; import loaderCss from './Loader.css'; -import { Vector } from '../Math/vector'; +import type { Vector } from '../Math/vector'; import { delay } from '../Util/Util'; import { EventEmitter } from '../EventEmitter'; -import { DefaultLoader, DefaultLoaderOptions } from './DefaultLoader'; -import { Engine } from '../Engine'; -import { Screen } from '../Screen'; +import type { DefaultLoaderOptions } from './DefaultLoader'; +import { DefaultLoader } from './DefaultLoader'; +import type { Engine } from '../Engine'; +import type { Screen } from '../Screen'; import { Logger } from '../Util/Log'; import { Future } from '../Util/Future'; diff --git a/src/engine/Director/Slide.ts b/src/engine/Director/Slide.ts index ec86e265..8e089e81 100644 --- a/src/engine/Director/Slide.ts +++ b/src/engine/Director/Slide.ts @@ -1,10 +1,14 @@ -import { ImageSource, Sprite } from '../Graphics'; -import { Engine } from '../Engine'; -import { Scene } from '../Scene'; -import { Transition, TransitionOptions } from './Transition'; -import { vec, Vector } from '../Math/vector'; -import { Camera } from '../Camera'; -import { EasingFunction, EasingFunctions } from '../Util/EasingFunctions'; +import type { Sprite } from '../Graphics'; +import { ImageSource } from '../Graphics'; +import type { Engine } from '../Engine'; +import type { Scene } from '../Scene'; +import type { TransitionOptions } from './Transition'; +import { Transition } from './Transition'; +import type { Vector } from '../Math/vector'; +import { vec } from '../Math/vector'; +import type { Camera } from '../Camera'; +import type { EasingFunction } from '../Util/EasingFunctions'; +import { EasingFunctions } from '../Util/EasingFunctions'; import { CoordPlane } from '../Math/coord-plane'; export interface SlideOptions { diff --git a/src/engine/Director/Transition.ts b/src/engine/Director/Transition.ts index a2f131d6..b0e76e8b 100644 --- a/src/engine/Director/Transition.ts +++ b/src/engine/Director/Transition.ts @@ -1,13 +1,15 @@ -import { Engine } from '../Engine'; -import { Scene } from '../Scene'; +import type { Engine } from '../Engine'; +import type { Scene } from '../Scene'; import { Future } from '../Util/Future'; import { Entity, TransformComponent } from '../EntityComponentSystem'; import { GraphicsComponent } from '../Graphics'; import { CoordPlane } from '../Math/coord-plane'; import { Vector } from '../Math/vector'; import { clamp } from '../Math/util'; -import { EasingFunction, EasingFunctions } from '../Util/EasingFunctions'; -import { coroutine, CoroutineInstance } from '../Util/Coroutine'; +import type { EasingFunction } from '../Util/EasingFunctions'; +import { EasingFunctions } from '../Util/EasingFunctions'; +import type { CoroutineInstance } from '../Util/Coroutine'; +import { coroutine } from '../Util/Coroutine'; import { Logger } from '../Util/Log'; export interface TransitionOptions { diff --git a/src/engine/Engine.ts b/src/engine/Engine.ts index baaa5a59..ad98f487 100644 --- a/src/engine/Engine.ts +++ b/src/engine/Engine.ts @@ -1,17 +1,19 @@ import { EX_VERSION } from './'; import { Future } from './Util/Future'; -import { EventEmitter, EventKey, Handler, Subscription } from './EventEmitter'; +import type { EventKey, Handler, Subscription } from './EventEmitter'; +import { EventEmitter } from './EventEmitter'; import { PointerScope } from './Input/PointerScope'; import { Flags } from './Flags'; import { polyfill } from './Polyfill'; polyfill(); -import { CanUpdate, CanDraw, CanInitialize } from './Interfaces/LifecycleEvents'; -import { Vector } from './Math/vector'; -import { Screen, DisplayMode, Resolution, ViewportDimension } from './Screen'; -import { ScreenElement } from './ScreenElement'; -import { Actor } from './Actor'; -import { Timer } from './Timer'; -import { TileMap } from './TileMap'; +import type { CanUpdate, CanDraw, CanInitialize } from './Interfaces/LifecycleEvents'; +import type { Vector } from './Math/vector'; +import type { ViewportDimension } from './Screen'; +import { Screen, DisplayMode, Resolution } from './Screen'; +import type { ScreenElement } from './ScreenElement'; +import type { Actor } from './Actor'; +import type { Timer } from './Timer'; +import type { TileMap } from './TileMap'; import { DefaultLoader } from './Director/DefaultLoader'; import { Loader } from './Director/Loader'; import { Detector } from './Util/Detector'; @@ -30,30 +32,36 @@ import { } from './Events'; import { Logger, LogLevel } from './Util/Log'; import { Color } from './Color'; -import { Scene, SceneConstructor, isSceneConstructor } from './Scene'; +import type { SceneConstructor } from './Scene'; +import { Scene, isSceneConstructor } from './Scene'; import { Entity } from './EntityComponentSystem/Entity'; -import { DebugConfig, DebugStats } from './Debug/DebugConfig'; +import type { DebugStats } from './Debug/DebugConfig'; +import { DebugConfig } from './Debug/DebugConfig'; import { BrowserEvents } from './Util/Browser'; +import type { AntialiasOptions, ExcaliburGraphicsContext } from './Graphics'; import { - AntialiasOptions, DefaultAntialiasOptions, DefaultPixelArtOptions, - ExcaliburGraphicsContext, ExcaliburGraphicsContext2DCanvas, ExcaliburGraphicsContextWebGL, TextureLoader } from './Graphics'; -import { Clock, StandardClock } from './Util/Clock'; +import type { Clock } from './Util/Clock'; +import { StandardClock } from './Util/Clock'; import { ImageFiltering } from './Graphics/Filtering'; import { GraphicsDiagnostics } from './Graphics/GraphicsDiagnostics'; import { Toaster } from './Util/Toaster'; -import { InputMapper } from './Input/InputMapper'; -import { GoToOptions, SceneMap, Director, StartOptions, SceneWithOptions, WithRoot, DirectorEvents } from './Director/Director'; +import type { InputMapper } from './Input/InputMapper'; +import type { GoToOptions, SceneMap, StartOptions, SceneWithOptions, WithRoot } from './Director/Director'; +import { Director, DirectorEvents } from './Director/Director'; import { InputHost } from './Input/InputHost'; -import { getDefaultPhysicsConfig, PhysicsConfig } from './Collision/PhysicsConfig'; -import { DeepRequired } from './Util/Required'; -import { Context, createContext, useContext } from './Context'; -import { DefaultGarbageCollectionOptions, GarbageCollectionOptions, GarbageCollector } from './GarbageCollector'; +import type { PhysicsConfig } from './Collision/PhysicsConfig'; +import { getDefaultPhysicsConfig } from './Collision/PhysicsConfig'; +import type { DeepRequired } from './Util/Required'; +import type { Context } from './Context'; +import { createContext, useContext } from './Context'; +import type { GarbageCollectionOptions } from './GarbageCollector'; +import { DefaultGarbageCollectionOptions, GarbageCollector } from './GarbageCollector'; import { mergeDeep } from './Util/Util'; export type EngineEvents = DirectorEvents & { diff --git a/src/engine/EntityComponentSystem/Component.ts b/src/engine/EntityComponentSystem/Component.ts index 142dffcf..528ec61a 100644 --- a/src/engine/EntityComponentSystem/Component.ts +++ b/src/engine/EntityComponentSystem/Component.ts @@ -1,4 +1,4 @@ -import { Entity } from './Entity'; +import type { Entity } from './Entity'; /** * Component Constructor Types diff --git a/src/engine/EntityComponentSystem/Components/TransformComponent.ts b/src/engine/EntityComponentSystem/Components/TransformComponent.ts index 6ea86594..4a0ef555 100644 --- a/src/engine/EntityComponentSystem/Components/TransformComponent.ts +++ b/src/engine/EntityComponentSystem/Components/TransformComponent.ts @@ -1,8 +1,8 @@ -import { Vector } from '../../Math/vector'; +import type { Vector } from '../../Math/vector'; import { CoordPlane } from '../../Math/coord-plane'; import { Transform } from '../../Math/transform'; import { Component } from '../Component'; -import { Entity } from '../Entity'; +import type { Entity } from '../Entity'; import { Observable } from '../../Util/Observable'; import { Logger } from '../../Util/Log'; diff --git a/src/engine/EntityComponentSystem/Entity.ts b/src/engine/EntityComponentSystem/Entity.ts index 967494db..4b287708 100644 --- a/src/engine/EntityComponentSystem/Entity.ts +++ b/src/engine/EntityComponentSystem/Entity.ts @@ -1,14 +1,17 @@ -import { Component, ComponentCtor, isComponentCtor } from './Component'; +import type { ComponentCtor } from './Component'; +import { Component, isComponentCtor } from './Component'; -import { Observable, Message } from '../Util/Observable'; -import { OnInitialize, OnPreUpdate, OnPostUpdate, OnAdd, OnRemove } from '../Interfaces/LifecycleEvents'; -import { Engine } from '../Engine'; +import type { Message } from '../Util/Observable'; +import { Observable } from '../Util/Observable'; +import type { OnInitialize, OnPreUpdate, OnPostUpdate, OnAdd, OnRemove } from '../Interfaces/LifecycleEvents'; +import type { Engine } from '../Engine'; import { InitializeEvent, PreUpdateEvent, PostUpdateEvent, AddEvent, RemoveEvent } from '../Events'; import { KillEvent } from '../Events'; -import { EventEmitter, EventKey, Handler, Subscription } from '../EventEmitter'; -import { Scene } from '../Scene'; +import type { EventKey, Handler, Subscription } from '../EventEmitter'; +import { EventEmitter } from '../EventEmitter'; +import type { Scene } from '../Scene'; import { removeItemFromArray } from '../Util/Util'; -import { MaybeKnownComponent } from './Types'; +import type { MaybeKnownComponent } from './Types'; import { Logger } from '../Util/Log'; /** diff --git a/src/engine/EntityComponentSystem/EntityManager.ts b/src/engine/EntityComponentSystem/EntityManager.ts index fd7aa9af..459ddec0 100644 --- a/src/engine/EntityComponentSystem/EntityManager.ts +++ b/src/engine/EntityComponentSystem/EntityManager.ts @@ -1,7 +1,7 @@ import { Entity } from './Entity'; -import { World } from './World'; +import type { World } from './World'; import { removeItemFromArray } from '../Util/Util'; -import { Scene } from '../Scene'; +import type { Scene } from '../Scene'; // Add/Remove entities and components diff --git a/src/engine/EntityComponentSystem/Query.ts b/src/engine/EntityComponentSystem/Query.ts index a0c4e79b..9f99f59e 100644 --- a/src/engine/EntityComponentSystem/Query.ts +++ b/src/engine/EntityComponentSystem/Query.ts @@ -1,6 +1,6 @@ -import { Entity } from './Entity'; +import type { Entity } from './Entity'; import { Observable } from '../Util/Observable'; -import { Component, ComponentCtor } from '../EntityComponentSystem/Component'; +import type { Component, ComponentCtor } from '../EntityComponentSystem/Component'; export type ComponentInstance = T extends ComponentCtor ? R : never; diff --git a/src/engine/EntityComponentSystem/QueryManager.ts b/src/engine/EntityComponentSystem/QueryManager.ts index 44f4e577..4d0c0310 100644 --- a/src/engine/EntityComponentSystem/QueryManager.ts +++ b/src/engine/EntityComponentSystem/QueryManager.ts @@ -1,7 +1,7 @@ -import { Entity } from './Entity'; +import type { Entity } from './Entity'; import { Query } from './Query'; -import { Component, ComponentCtor } from './Component'; -import { World } from './World'; +import type { Component, ComponentCtor } from './Component'; +import type { World } from './World'; import { TagQuery } from './TagQuery'; /** diff --git a/src/engine/EntityComponentSystem/System.ts b/src/engine/EntityComponentSystem/System.ts index 41d3215a..9caf312a 100644 --- a/src/engine/EntityComponentSystem/System.ts +++ b/src/engine/EntityComponentSystem/System.ts @@ -1,6 +1,6 @@ -import { Scene } from '../Scene'; +import type { Scene } from '../Scene'; import { SystemPriority } from './Priority'; -import { World } from './World'; +import type { World } from './World'; /** * Enum that determines whether to run the system in the update or draw phase diff --git a/src/engine/EntityComponentSystem/SystemManager.ts b/src/engine/EntityComponentSystem/SystemManager.ts index 3d57a8db..491412e3 100644 --- a/src/engine/EntityComponentSystem/SystemManager.ts +++ b/src/engine/EntityComponentSystem/SystemManager.ts @@ -1,6 +1,7 @@ -import { System, SystemType } from './System'; -import { Scene } from '../Scene'; -import { World } from './World'; +import type { SystemType } from './System'; +import { System } from './System'; +import type { Scene } from '../Scene'; +import type { World } from './World'; import { removeItemFromArray } from '../Util/Util'; export interface SystemCtor { diff --git a/src/engine/EntityComponentSystem/TagQuery.ts b/src/engine/EntityComponentSystem/TagQuery.ts index ced97cad..ea537e22 100644 --- a/src/engine/EntityComponentSystem/TagQuery.ts +++ b/src/engine/EntityComponentSystem/TagQuery.ts @@ -1,5 +1,5 @@ import { Observable } from '../Util/Observable'; -import { Entity } from './Entity'; +import type { Entity } from './Entity'; export class TagQuery { public readonly id: string; diff --git a/src/engine/EntityComponentSystem/World.ts b/src/engine/EntityComponentSystem/World.ts index b10c0cc2..291a68d9 100644 --- a/src/engine/EntityComponentSystem/World.ts +++ b/src/engine/EntityComponentSystem/World.ts @@ -1,13 +1,14 @@ -import { Scene } from '../Scene'; +import type { Scene } from '../Scene'; import { Logger } from '../Util/Log'; -import { Component, ComponentCtor } from './Component'; +import type { Component, ComponentCtor } from './Component'; import { Entity } from './Entity'; import { EntityManager } from './EntityManager'; -import { Query } from './Query'; +import type { Query } from './Query'; import { QueryManager } from './QueryManager'; import { System, SystemType } from './System'; -import { SystemCtor, SystemManager, isSystemConstructor } from './SystemManager'; -import { TagQuery } from './TagQuery'; +import type { SystemCtor } from './SystemManager'; +import { SystemManager, isSystemConstructor } from './SystemManager'; +import type { TagQuery } from './TagQuery'; /** * The World is a self-contained entity component system for a particular context. diff --git a/src/engine/Events.ts b/src/engine/Events.ts index d449cada..eee261be 100644 --- a/src/engine/Events.ts +++ b/src/engine/Events.ts @@ -1,18 +1,18 @@ -import { Scene } from './Scene'; -import { Vector } from './Math/vector'; -import { Actor } from './Actor'; -import { Trigger } from './Trigger'; -import { FrameStats } from './Debug'; -import { Engine } from './Engine'; -import { TileMap } from './TileMap'; -import { Side } from './Collision/Side'; -import { CollisionContact } from './Collision/Detection/CollisionContact'; -import { Collider } from './Collision/Colliders/Collider'; -import { Entity } from './EntityComponentSystem/Entity'; -import { OnInitialize, OnPreUpdate, OnPostUpdate, SceneActivationContext, OnAdd, OnRemove } from './Interfaces/LifecycleEvents'; -import { ExcaliburGraphicsContext } from './Graphics'; -import { Axes, Buttons, Gamepad } from './Input/Gamepad'; -import { Action } from './Actions/Action'; +import type { Scene } from './Scene'; +import type { Vector } from './Math/vector'; +import type { Actor } from './Actor'; +import type { Trigger } from './Trigger'; +import type { FrameStats } from './Debug'; +import type { Engine } from './Engine'; +import type { TileMap } from './TileMap'; +import type { Side } from './Collision/Side'; +import type { CollisionContact } from './Collision/Detection/CollisionContact'; +import type { Collider } from './Collision/Colliders/Collider'; +import type { Entity } from './EntityComponentSystem/Entity'; +import type { OnInitialize, OnPreUpdate, OnPostUpdate, SceneActivationContext, OnAdd, OnRemove } from './Interfaces/LifecycleEvents'; +import type { ExcaliburGraphicsContext } from './Graphics'; +import type { Axes, Buttons, Gamepad } from './Input/Gamepad'; +import type { Action } from './Actions/Action'; export enum EventTypes { Kill = 'kill', diff --git a/src/engine/Events/MediaEvents.ts b/src/engine/Events/MediaEvents.ts index 40e9c796..82a6e8e9 100644 --- a/src/engine/Events/MediaEvents.ts +++ b/src/engine/Events/MediaEvents.ts @@ -1,7 +1,7 @@ import { GameEvent } from '../Events'; -import { Sound } from '../Resources/Sound/Sound'; -import { Actor } from '../Actor'; -import { WebAudioInstance } from '../Resources/Sound/WebAudioInstance'; +import type { Sound } from '../Resources/Sound/Sound'; +import type { Actor } from '../Actor'; +import type { WebAudioInstance } from '../Resources/Sound/WebAudioInstance'; export class MediaEvent extends GameEvent { /** diff --git a/src/engine/Events/PointerEvents.ts b/src/engine/Events/PointerEvents.ts index 025aaa62..04b0e9ab 100644 --- a/src/engine/Events/PointerEvents.ts +++ b/src/engine/Events/PointerEvents.ts @@ -1,5 +1,5 @@ -import { GlobalCoordinates } from '../Math/global-coordinates'; -import { WheelDeltaMode } from '../Input/WheelDeltaMode'; +import type { GlobalCoordinates } from '../Math/global-coordinates'; +import type { WheelDeltaMode } from '../Input/WheelDeltaMode'; import { ExEvent } from './ExEvent'; export abstract class PointerEvent extends ExEvent<'down' | 'up' | 'move' | 'cancel'> { diff --git a/src/engine/Graphics/Animation.ts b/src/engine/Graphics/Animation.ts index f90801b0..d8bb7ff2 100644 --- a/src/engine/Graphics/Animation.ts +++ b/src/engine/Graphics/Animation.ts @@ -1,6 +1,7 @@ -import { Graphic, GraphicOptions } from './Graphic'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; -import { GetSpriteOptions, SpriteSheet } from './SpriteSheet'; +import type { GraphicOptions } from './Graphic'; +import { Graphic } from './Graphic'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { GetSpriteOptions, SpriteSheet } from './SpriteSheet'; import { Logger } from '../Util/Log'; import { clamp } from '../Math/util'; import { EventEmitter } from '../EventEmitter'; diff --git a/src/engine/Graphics/Canvas.ts b/src/engine/Graphics/Canvas.ts index d326fb2a..a48097e9 100644 --- a/src/engine/Graphics/Canvas.ts +++ b/src/engine/Graphics/Canvas.ts @@ -1,5 +1,6 @@ -import { GraphicOptions } from './Graphic'; -import { Raster, RasterOptions } from './Raster'; +import type { GraphicOptions } from './Graphic'; +import type { RasterOptions } from './Raster'; +import { Raster } from './Raster'; export interface CanvasOptions { draw?: (ctx: CanvasRenderingContext2D) => void; diff --git a/src/engine/Graphics/Circle.ts b/src/engine/Graphics/Circle.ts index 07639923..c71ef61a 100644 --- a/src/engine/Graphics/Circle.ts +++ b/src/engine/Graphics/Circle.ts @@ -1,5 +1,6 @@ import { ImageFiltering } from './Filtering'; -import { Raster, RasterOptions } from './Raster'; +import type { RasterOptions } from './Raster'; +import { Raster } from './Raster'; export interface CircleOptions { radius: number; diff --git a/src/engine/Graphics/Context/ExcaliburGraphicsContext.ts b/src/engine/Graphics/Context/ExcaliburGraphicsContext.ts index 9a375d4b..4968d91d 100644 --- a/src/engine/Graphics/Context/ExcaliburGraphicsContext.ts +++ b/src/engine/Graphics/Context/ExcaliburGraphicsContext.ts @@ -1,9 +1,9 @@ -import { Vector } from '../../Math/vector'; -import { Color } from '../../Color'; -import { Resolution } from '../../Screen'; -import { PostProcessor } from '../PostProcessor/PostProcessor'; -import { AffineMatrix } from '../../Math/affine-matrix'; -import { Material, MaterialOptions } from './material'; +import type { Vector } from '../../Math/vector'; +import type { Color } from '../../Color'; +import type { Resolution } from '../../Screen'; +import type { PostProcessor } from '../PostProcessor/PostProcessor'; +import type { AffineMatrix } from '../../Math/affine-matrix'; +import type { Material, MaterialOptions } from './material'; import { ImageFiltering } from '../Filtering'; export type HTMLImageSource = HTMLImageElement | HTMLCanvasElement; diff --git a/src/engine/Graphics/Context/ExcaliburGraphicsContext2DCanvas.ts b/src/engine/Graphics/Context/ExcaliburGraphicsContext2DCanvas.ts index 45e6656e..64add84e 100644 --- a/src/engine/Graphics/Context/ExcaliburGraphicsContext2DCanvas.ts +++ b/src/engine/Graphics/Context/ExcaliburGraphicsContext2DCanvas.ts @@ -1,4 +1,4 @@ -import { +import type { ExcaliburGraphicsContext, LineGraphicsOptions, PointGraphicsOptions, @@ -6,15 +6,15 @@ import { DebugDraw, HTMLImageSource } from './ExcaliburGraphicsContext'; -import { Vector } from '../../Math/vector'; +import type { Vector } from '../../Math/vector'; import { Color } from '../../Color'; import { StateStack } from './state-stack'; import { GraphicsDiagnostics } from '../GraphicsDiagnostics'; import { DebugText } from './debug-text'; -import { Resolution } from '../../Screen'; -import { PostProcessor } from '../PostProcessor/PostProcessor'; -import { AffineMatrix } from '../../Math/affine-matrix'; -import { Material, MaterialOptions } from './material'; +import type { Resolution } from '../../Screen'; +import type { PostProcessor } from '../PostProcessor/PostProcessor'; +import type { AffineMatrix } from '../../Math/affine-matrix'; +import type { Material, MaterialOptions } from './material'; const pixelSnapEpsilon = 0.0001; diff --git a/src/engine/Graphics/Context/ExcaliburGraphicsContextWebGL.ts b/src/engine/Graphics/Context/ExcaliburGraphicsContextWebGL.ts index a2431d31..accb4fa8 100644 --- a/src/engine/Graphics/Context/ExcaliburGraphicsContextWebGL.ts +++ b/src/engine/Graphics/Context/ExcaliburGraphicsContextWebGL.ts @@ -1,4 +1,4 @@ -import { +import type { ExcaliburGraphicsContext, LineGraphicsOptions, RectGraphicsOptions, @@ -10,16 +10,17 @@ import { import { Matrix } from '../../Math/matrix'; import { TransformStack } from './transform-stack'; -import { Vector, vec } from '../../Math/vector'; +import type { Vector } from '../../Math/vector'; +import { vec } from '../../Math/vector'; import { Color } from '../../Color'; import { StateStack } from './state-stack'; import { Logger } from '../../Util/Log'; import { DebugText } from './debug-text'; -import { Resolution } from '../../Screen'; +import type { Resolution } from '../../Screen'; import { RenderTarget } from './render-target'; -import { PostProcessor } from '../PostProcessor/PostProcessor'; +import type { PostProcessor } from '../PostProcessor/PostProcessor'; import { TextureLoader } from './texture-loader'; -import { RendererPlugin } from './renderer'; +import type { RendererPlugin } from './renderer'; // renderers import { LineRenderer } from './line-renderer/line-renderer'; @@ -30,11 +31,13 @@ import { RectangleRenderer } from './rectangle-renderer/rectangle-renderer'; import { CircleRenderer } from './circle-renderer/circle-renderer'; import { Pool } from '../../Util/Pool'; import { DrawCall } from './draw-call'; -import { AffineMatrix } from '../../Math/affine-matrix'; -import { Material, MaterialOptions } from './material'; +import type { AffineMatrix } from '../../Math/affine-matrix'; +import type { MaterialOptions } from './material'; +import { Material } from './material'; import { MaterialRenderer } from './material-renderer/material-renderer'; -import { Shader, ShaderOptions } from './shader'; -import { GarbageCollector } from '../../GarbageCollector'; +import type { ShaderOptions } from './shader'; +import { Shader } from './shader'; +import type { GarbageCollector } from '../../GarbageCollector'; import { ParticleRenderer } from './particle-renderer/particle-renderer'; import { ImageRendererV2 } from './image-renderer-v2/image-renderer-v2'; import { Flags } from '../../Flags'; diff --git a/src/engine/Graphics/Context/circle-renderer/circle-renderer.ts b/src/engine/Graphics/Context/circle-renderer/circle-renderer.ts index 6543542c..7294b410 100644 --- a/src/engine/Graphics/Context/circle-renderer/circle-renderer.ts +++ b/src/engine/Graphics/Context/circle-renderer/circle-renderer.ts @@ -1,9 +1,11 @@ import { Color } from '../../../Color'; -import { vec, Vector } from '../../../Math/vector'; +import type { Vector } from '../../../Math/vector'; +import { vec } from '../../../Math/vector'; import { GraphicsDiagnostics } from '../../GraphicsDiagnostics'; -import { ExcaliburGraphicsContextWebGL, pixelSnapEpsilon } from '../ExcaliburGraphicsContextWebGL'; +import type { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; +import { pixelSnapEpsilon } from '../ExcaliburGraphicsContextWebGL'; import { QuadIndexBuffer } from '../quad-index-buffer'; -import { RendererPlugin } from '../renderer'; +import type { RendererPlugin } from '../renderer'; import { Shader } from '../shader'; import { VertexBuffer } from '../vertex-buffer'; import { VertexLayout } from '../vertex-layout'; diff --git a/src/engine/Graphics/Context/debug-text.ts b/src/engine/Graphics/Context/debug-text.ts index 05f06631..21d49e30 100644 --- a/src/engine/Graphics/Context/debug-text.ts +++ b/src/engine/Graphics/Context/debug-text.ts @@ -1,8 +1,8 @@ -import { ExcaliburGraphicsContext } from '../Context/ExcaliburGraphicsContext'; +import type { ExcaliburGraphicsContext } from '../Context/ExcaliburGraphicsContext'; import { ImageSource } from '../ImageSource'; import { SpriteFont } from '../SpriteFont'; import { SpriteSheet } from '../SpriteSheet'; -import { Vector } from '../../Math/vector'; +import type { Vector } from '../../Math/vector'; import debugFont from './debug-font.png'; /** diff --git a/src/engine/Graphics/Context/draw-call.ts b/src/engine/Graphics/Context/draw-call.ts index 829c99f8..11ee4600 100644 --- a/src/engine/Graphics/Context/draw-call.ts +++ b/src/engine/Graphics/Context/draw-call.ts @@ -1,6 +1,6 @@ import { AffineMatrix } from '../../Math/affine-matrix'; import { Color } from '../../Color'; -import { ExcaliburGraphicsContextState } from './ExcaliburGraphicsContext'; +import type { ExcaliburGraphicsContextState } from './ExcaliburGraphicsContext'; export class DrawCall { public z: number = 0; diff --git a/src/engine/Graphics/Context/image-renderer-v2/image-renderer-v2.ts b/src/engine/Graphics/Context/image-renderer-v2/image-renderer-v2.ts index b1489e6b..51acb29f 100644 --- a/src/engine/Graphics/Context/image-renderer-v2/image-renderer-v2.ts +++ b/src/engine/Graphics/Context/image-renderer-v2/image-renderer-v2.ts @@ -7,9 +7,10 @@ import { ImageSourceAttributeConstants } from '../../ImageSource'; import { parseImageWrapping } from '../../Wrapping'; // import { ImageSourceAttributeConstants } from '../../ImageSource'; // import { parseImageWrapping } from '../../Wrapping'; -import { HTMLImageSource } from '../ExcaliburGraphicsContext'; -import { ExcaliburGraphicsContextWebGL, pixelSnapEpsilon } from '../ExcaliburGraphicsContextWebGL'; -import { RendererPlugin } from '../renderer'; +import type { HTMLImageSource } from '../ExcaliburGraphicsContext'; +import type { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; +import { pixelSnapEpsilon } from '../ExcaliburGraphicsContextWebGL'; +import type { RendererPlugin } from '../renderer'; import { Shader } from '../shader'; import { VertexBuffer } from '../vertex-buffer'; import { getMaxShaderComplexity } from '../webgl-util'; diff --git a/src/engine/Graphics/Context/image-renderer/image-renderer.ts b/src/engine/Graphics/Context/image-renderer/image-renderer.ts index f6b48263..c9519b04 100644 --- a/src/engine/Graphics/Context/image-renderer/image-renderer.ts +++ b/src/engine/Graphics/Context/image-renderer/image-renderer.ts @@ -4,10 +4,11 @@ import { parseImageFiltering } from '../../Filtering'; import { GraphicsDiagnostics } from '../../GraphicsDiagnostics'; import { ImageSourceAttributeConstants } from '../../ImageSource'; import { parseImageWrapping } from '../../Wrapping'; -import { HTMLImageSource } from '../ExcaliburGraphicsContext'; -import { ExcaliburGraphicsContextWebGL, pixelSnapEpsilon } from '../ExcaliburGraphicsContextWebGL'; +import type { HTMLImageSource } from '../ExcaliburGraphicsContext'; +import type { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; +import { pixelSnapEpsilon } from '../ExcaliburGraphicsContextWebGL'; import { QuadIndexBuffer } from '../quad-index-buffer'; -import { RendererPlugin } from '../renderer'; +import type { RendererPlugin } from '../renderer'; import { Shader } from '../shader'; import { VertexBuffer } from '../vertex-buffer'; import { VertexLayout } from '../vertex-layout'; diff --git a/src/engine/Graphics/Context/line-renderer/line-renderer.ts b/src/engine/Graphics/Context/line-renderer/line-renderer.ts index 309003ff..6004b5e2 100644 --- a/src/engine/Graphics/Context/line-renderer/line-renderer.ts +++ b/src/engine/Graphics/Context/line-renderer/line-renderer.ts @@ -1,9 +1,10 @@ -import { vec, Vector } from '../../../Math/vector'; -import { Color } from '../../../Color'; +import type { Vector } from '../../../Math/vector'; +import { vec } from '../../../Math/vector'; +import type { Color } from '../../../Color'; import lineVertexSource from './line-vertex.glsl'; import lineFragmentSource from './line-fragment.glsl'; -import { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; -import { RendererPlugin } from '../renderer'; +import type { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; +import type { RendererPlugin } from '../renderer'; import { Shader, VertexBuffer, VertexLayout } from '../..'; import { GraphicsDiagnostics } from '../../GraphicsDiagnostics'; diff --git a/src/engine/Graphics/Context/material-renderer/material-renderer.ts b/src/engine/Graphics/Context/material-renderer/material-renderer.ts index aa4c1534..ab1957c3 100644 --- a/src/engine/Graphics/Context/material-renderer/material-renderer.ts +++ b/src/engine/Graphics/Context/material-renderer/material-renderer.ts @@ -3,10 +3,10 @@ import { parseImageFiltering } from '../../Filtering'; import { GraphicsDiagnostics } from '../../GraphicsDiagnostics'; import { ImageSourceAttributeConstants } from '../../ImageSource'; import { parseImageWrapping } from '../../Wrapping'; -import { HTMLImageSource } from '../ExcaliburGraphicsContext'; -import { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; +import type { HTMLImageSource } from '../ExcaliburGraphicsContext'; +import type { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; import { QuadIndexBuffer } from '../quad-index-buffer'; -import { RendererPlugin } from '../renderer'; +import type { RendererPlugin } from '../renderer'; import { VertexBuffer } from '../vertex-buffer'; import { VertexLayout } from '../vertex-layout'; diff --git a/src/engine/Graphics/Context/material.ts b/src/engine/Graphics/Context/material.ts index d3365702..08fac0b1 100644 --- a/src/engine/Graphics/Context/material.ts +++ b/src/engine/Graphics/Context/material.ts @@ -1,10 +1,10 @@ import { Color } from '../../Color'; -import { ExcaliburGraphicsContext } from './ExcaliburGraphicsContext'; +import type { ExcaliburGraphicsContext } from './ExcaliburGraphicsContext'; import { ExcaliburGraphicsContextWebGL } from './ExcaliburGraphicsContextWebGL'; -import { Shader, UniformDictionary } from './shader'; +import type { Shader, UniformDictionary } from './shader'; import { Logger } from '../../Util/Log'; -import { ImageSource } from '../ImageSource'; -import { ImageFiltering } from '../Filtering'; +import type { ImageSource } from '../ImageSource'; +import type { ImageFiltering } from '../Filtering'; export interface MaterialOptions { /** diff --git a/src/engine/Graphics/Context/particle-renderer/particle-renderer.ts b/src/engine/Graphics/Context/particle-renderer/particle-renderer.ts index c43820e9..e6425fb3 100644 --- a/src/engine/Graphics/Context/particle-renderer/particle-renderer.ts +++ b/src/engine/Graphics/Context/particle-renderer/particle-renderer.ts @@ -1,12 +1,12 @@ -import { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; -import { RendererPlugin } from '../renderer'; +import type { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; +import type { RendererPlugin } from '../renderer'; import { Shader } from '../shader'; import particleVertexSource from './particle-vertex.glsl'; import particleFragmentSource from './particle-fragment.glsl'; -import { GpuParticleRenderer } from '../../../Particles/GpuParticleRenderer'; +import type { GpuParticleRenderer } from '../../../Particles/GpuParticleRenderer'; import { vec } from '../../../Math/vector'; import { Color } from '../../../Color'; -import { HTMLImageSource } from '../ExcaliburGraphicsContext'; +import type { HTMLImageSource } from '../ExcaliburGraphicsContext'; import { ImageSourceAttributeConstants } from '../../ImageSource'; import { parseImageWrapping } from '../../Wrapping'; import { parseImageFiltering } from '../../Filtering'; diff --git a/src/engine/Graphics/Context/point-renderer/point-renderer.ts b/src/engine/Graphics/Context/point-renderer/point-renderer.ts index d9a81961..5743f8af 100644 --- a/src/engine/Graphics/Context/point-renderer/point-renderer.ts +++ b/src/engine/Graphics/Context/point-renderer/point-renderer.ts @@ -1,9 +1,10 @@ import pointVertexSource from './point-vertex.glsl'; import pointFragmentSource from './point-fragment.glsl'; -import { Vector } from '../../../Math/vector'; -import { Color } from '../../../Color'; -import { ExcaliburGraphicsContextWebGL, pixelSnapEpsilon } from '../ExcaliburGraphicsContextWebGL'; -import { RendererPlugin } from '../renderer'; +import type { Vector } from '../../../Math/vector'; +import type { Color } from '../../../Color'; +import type { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; +import { pixelSnapEpsilon } from '../ExcaliburGraphicsContextWebGL'; +import type { RendererPlugin } from '../renderer'; import { Shader } from '../shader'; import { VertexBuffer } from '../vertex-buffer'; import { VertexLayout } from '../vertex-layout'; diff --git a/src/engine/Graphics/Context/rectangle-renderer/rectangle-renderer.ts b/src/engine/Graphics/Context/rectangle-renderer/rectangle-renderer.ts index c13b1462..3bb24807 100644 --- a/src/engine/Graphics/Context/rectangle-renderer/rectangle-renderer.ts +++ b/src/engine/Graphics/Context/rectangle-renderer/rectangle-renderer.ts @@ -1,9 +1,10 @@ import { Color } from '../../../Color'; import { vec, Vector } from '../../../Math/vector'; import { GraphicsDiagnostics } from '../../GraphicsDiagnostics'; -import { ExcaliburGraphicsContextWebGL, pixelSnapEpsilon } from '../ExcaliburGraphicsContextWebGL'; +import type { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; +import { pixelSnapEpsilon } from '../ExcaliburGraphicsContextWebGL'; import { QuadIndexBuffer } from '../quad-index-buffer'; -import { RendererPlugin } from '../renderer'; +import type { RendererPlugin } from '../renderer'; import { Shader } from '../shader'; import { VertexBuffer } from '../vertex-buffer'; import { VertexLayout } from '../vertex-layout'; diff --git a/src/engine/Graphics/Context/renderer.ts b/src/engine/Graphics/Context/renderer.ts index 2ea7dffb..4e72d570 100644 --- a/src/engine/Graphics/Context/renderer.ts +++ b/src/engine/Graphics/Context/renderer.ts @@ -1,4 +1,4 @@ -import { ExcaliburGraphicsContextWebGL } from './ExcaliburGraphicsContextWebGL'; +import type { ExcaliburGraphicsContextWebGL } from './ExcaliburGraphicsContextWebGL'; /** * Interface that defines an Excalibur Renderer that can be called with .draw() in the {@apilink ExcaliburGraphicsContext} diff --git a/src/engine/Graphics/Context/screen-pass-painter/screen-pass-painter.ts b/src/engine/Graphics/Context/screen-pass-painter/screen-pass-painter.ts index 248186fb..48e70ea4 100644 --- a/src/engine/Graphics/Context/screen-pass-painter/screen-pass-painter.ts +++ b/src/engine/Graphics/Context/screen-pass-painter/screen-pass-painter.ts @@ -3,8 +3,8 @@ import screenFragment from './screen-fragment.glsl'; import { Shader } from '../shader'; import { VertexBuffer } from '../vertex-buffer'; import { VertexLayout } from '../vertex-layout'; -import { PostProcessor } from '../../PostProcessor/PostProcessor'; -import { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; +import type { PostProcessor } from '../../PostProcessor/PostProcessor'; +import type { ExcaliburGraphicsContextWebGL } from '../ExcaliburGraphicsContextWebGL'; /** * This is responsible for painting the entire screen during the render passes diff --git a/src/engine/Graphics/Context/shader.ts b/src/engine/Graphics/Context/shader.ts index 13388a0c..80d880f8 100644 --- a/src/engine/Graphics/Context/shader.ts +++ b/src/engine/Graphics/Context/shader.ts @@ -1,17 +1,15 @@ +import type { ExcaliburGraphicsContext, ImageSource, TextureLoader } from '../..'; import { AffineMatrix, Color, - ExcaliburGraphicsContext, ExcaliburGraphicsContextWebGL, - ImageSource, ImageSourceAttributeConstants, Logger, parseImageFiltering, parseImageWrapping, - TextureLoader, Vector } from '../..'; -import { Matrix } from '../../Math/matrix'; +import type { Matrix } from '../../Math/matrix'; import { watch } from '../../Util/Watch'; import { UniformBuffer } from './uniform-buffer'; import { getAttributeComponentSize, getAttributePointerType } from './webgl-util'; diff --git a/src/engine/Graphics/Context/state-stack.ts b/src/engine/Graphics/Context/state-stack.ts index 52fc64d7..280d8c2c 100644 --- a/src/engine/Graphics/Context/state-stack.ts +++ b/src/engine/Graphics/Context/state-stack.ts @@ -1,7 +1,7 @@ import { Color } from '../../Color'; import { RentalPool } from '../../Util/RentalPool'; -import { ExcaliburGraphicsContextState } from './ExcaliburGraphicsContext'; -import { Material } from './material'; +import type { ExcaliburGraphicsContextState } from './ExcaliburGraphicsContext'; +import type { Material } from './material'; export class ContextState implements ExcaliburGraphicsContextState { opacity: number = 1; diff --git a/src/engine/Graphics/Context/texture-loader.ts b/src/engine/Graphics/Context/texture-loader.ts index 14bb09c6..510638fa 100644 --- a/src/engine/Graphics/Context/texture-loader.ts +++ b/src/engine/Graphics/Context/texture-loader.ts @@ -1,9 +1,9 @@ -import { GarbageCollector } from '../../GarbageCollector'; +import type { GarbageCollector } from '../../GarbageCollector'; import { Logger } from '../../Util/Log'; import { ImageFiltering } from '../Filtering'; -import { ImageSourceOptions, ImageWrapConfiguration } from '../ImageSource'; +import type { ImageSourceOptions, ImageWrapConfiguration } from '../ImageSource'; import { ImageWrapping } from '../Wrapping'; -import { HTMLImageSource } from './ExcaliburGraphicsContext'; +import type { HTMLImageSource } from './ExcaliburGraphicsContext'; /** * Manages loading image sources into webgl textures, a unique id is associated with all sources diff --git a/src/engine/Graphics/Context/vertex-layout.ts b/src/engine/Graphics/Context/vertex-layout.ts index 4e5f3b33..9d10e604 100644 --- a/src/engine/Graphics/Context/vertex-layout.ts +++ b/src/engine/Graphics/Context/vertex-layout.ts @@ -1,6 +1,6 @@ import { Logger } from '../..'; -import { Shader, VertexAttributeDefinition } from './shader'; -import { VertexBuffer } from './vertex-buffer'; +import type { Shader, VertexAttributeDefinition } from './shader'; +import type { VertexBuffer } from './vertex-buffer'; import { getGLTypeFromSource, getGlTypeSizeBytes, isAttributeInSource } from './webgl-util'; export interface VertexLayoutOptions { diff --git a/src/engine/Graphics/Debug.ts b/src/engine/Graphics/Debug.ts index 57f490d9..67fbcf8f 100644 --- a/src/engine/Graphics/Debug.ts +++ b/src/engine/Graphics/Debug.ts @@ -1,8 +1,8 @@ -import { Vector } from '../Math/vector'; -import { ExcaliburGraphicsContext, LineGraphicsOptions, PointGraphicsOptions } from './Context/ExcaliburGraphicsContext'; +import type { Vector } from '../Math/vector'; +import type { ExcaliburGraphicsContext, LineGraphicsOptions, PointGraphicsOptions } from './Context/ExcaliburGraphicsContext'; import { Color } from '../Color'; -import { Ray } from '../Math/ray'; -import { BoundingBox } from '../Collision/BoundingBox'; +import type { Ray } from '../Math/ray'; +import type { BoundingBox } from '../Collision/BoundingBox'; export class Debug { static _drawCalls: ((ctx: ExcaliburGraphicsContext) => void)[] = []; diff --git a/src/engine/Graphics/DebugGraphicsComponent.ts b/src/engine/Graphics/DebugGraphicsComponent.ts index 53707242..d91cf08d 100644 --- a/src/engine/Graphics/DebugGraphicsComponent.ts +++ b/src/engine/Graphics/DebugGraphicsComponent.ts @@ -1,5 +1,5 @@ -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; -import { DebugConfig } from '../Debug'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { DebugConfig } from '../Debug'; import { Component } from '../EntityComponentSystem/Component'; /** diff --git a/src/engine/Graphics/Font.ts b/src/engine/Graphics/Font.ts index 695b1218..d8555c89 100644 --- a/src/engine/Graphics/Font.ts +++ b/src/engine/Graphics/Font.ts @@ -1,10 +1,12 @@ -import { Vector } from '../Math/vector'; +import type { Vector } from '../Math/vector'; import { BoundingBox } from '../Collision/Index'; import { Color } from '../Color'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; -import { BaseAlign, Direction, FontOptions, FontStyle, FontUnit, TextAlign, FontRenderer } from './FontCommon'; -import { Graphic, GraphicOptions } from './Graphic'; -import { RasterOptions } from './Raster'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { FontOptions, FontRenderer } from './FontCommon'; +import { BaseAlign, Direction, FontStyle, FontUnit, TextAlign } from './FontCommon'; +import type { GraphicOptions } from './Graphic'; +import { Graphic } from './Graphic'; +import type { RasterOptions } from './Raster'; import { ImageFiltering } from './Filtering'; import { FontTextInstance } from './FontTextInstance'; import { FontCache } from './FontCache'; diff --git a/src/engine/Graphics/FontCache.ts b/src/engine/Graphics/FontCache.ts index 4f75cf9c..7be0bd8a 100644 --- a/src/engine/Graphics/FontCache.ts +++ b/src/engine/Graphics/FontCache.ts @@ -1,7 +1,7 @@ -import { BoundingBox } from '../Collision/BoundingBox'; -import { Color } from '../Color'; +import type { BoundingBox } from '../Collision/BoundingBox'; +import type { Color } from '../Color'; import { Logger } from '../Util/Log'; -import { Font } from './Font'; +import type { Font } from './Font'; import { FontTextInstance } from './FontTextInstance'; export class FontCache { diff --git a/src/engine/Graphics/FontCommon.ts b/src/engine/Graphics/FontCommon.ts index ebf19e0a..9ca85909 100644 --- a/src/engine/Graphics/FontCommon.ts +++ b/src/engine/Graphics/FontCommon.ts @@ -1,7 +1,7 @@ -import { BoundingBox } from '../Collision/BoundingBox'; -import { Color } from '../Color'; -import { Vector } from '../Math/vector'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { BoundingBox } from '../Collision/BoundingBox'; +import type { Color } from '../Color'; +import type { Vector } from '../Math/vector'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; /** * Enum representing the different font size units diff --git a/src/engine/Graphics/FontTextInstance.ts b/src/engine/Graphics/FontTextInstance.ts index 1ac2f805..0e838b13 100644 --- a/src/engine/Graphics/FontTextInstance.ts +++ b/src/engine/Graphics/FontTextInstance.ts @@ -2,8 +2,8 @@ import { BoundingBox } from '../Collision/BoundingBox'; import { Color } from '../Color'; import { line } from '../Util/DrawUtil'; import { ExcaliburGraphicsContextWebGL } from './Context/ExcaliburGraphicsContextWebGL'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; -import { Font } from './Font'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { Font } from './Font'; export class FontTextInstance { public canvas: HTMLCanvasElement; diff --git a/src/engine/Graphics/Graphic.ts b/src/engine/Graphics/Graphic.ts index 398bb2f1..d95093fe 100644 --- a/src/engine/Graphics/Graphic.ts +++ b/src/engine/Graphics/Graphic.ts @@ -1,7 +1,7 @@ import { Vector, vec } from '../Math/vector'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; import { BoundingBox } from '../Collision/BoundingBox'; -import { Color } from '../Color'; +import type { Color } from '../Color'; import { watch } from '../Util/Watch'; import { AffineMatrix } from '../Math/affine-matrix'; diff --git a/src/engine/Graphics/GraphicsComponent.ts b/src/engine/Graphics/GraphicsComponent.ts index f51c3e0b..acb29e8a 100644 --- a/src/engine/Graphics/GraphicsComponent.ts +++ b/src/engine/Graphics/GraphicsComponent.ts @@ -1,15 +1,15 @@ import { Vector, vec } from '../Math/vector'; import { Graphic } from './Graphic'; -import { HasTick } from './Animation'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { HasTick } from './Animation'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; import { BoundingBox } from '../Collision/Index'; import { Component } from '../EntityComponentSystem/Component'; -import { Material } from './Context/material'; +import type { Material } from './Context/material'; import { Logger } from '../Util/Log'; import { WatchVector } from '../Math/watch-vector'; import { TransformComponent } from '../EntityComponentSystem'; import { GraphicsGroup } from '../Graphics/GraphicsGroup'; -import { Color } from '../Color'; +import type { Color } from '../Color'; import { Raster } from './Raster'; import { Text } from './Text'; diff --git a/src/engine/Graphics/GraphicsGroup.ts b/src/engine/Graphics/GraphicsGroup.ts index 5b12db45..4513f641 100644 --- a/src/engine/Graphics/GraphicsGroup.ts +++ b/src/engine/Graphics/GraphicsGroup.ts @@ -1,7 +1,9 @@ import { Vector } from '../Math/vector'; -import { Graphic, GraphicOptions } from './Graphic'; -import { Animation, HasTick } from './Animation'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { GraphicOptions } from './Graphic'; +import { Graphic } from './Graphic'; +import type { HasTick } from './Animation'; +import { Animation } from './Animation'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; import { BoundingBox } from '../Collision/Index'; import { Logger } from '../Util/Log'; diff --git a/src/engine/Graphics/GraphicsSystem.ts b/src/engine/Graphics/GraphicsSystem.ts index 9d04db97..63bafd70 100644 --- a/src/engine/Graphics/GraphicsSystem.ts +++ b/src/engine/Graphics/GraphicsSystem.ts @@ -1,12 +1,13 @@ -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; -import { Scene } from '../Scene'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { Scene } from '../Scene'; import { GraphicsComponent } from './GraphicsComponent'; import { vec, Vector } from '../Math/vector'; import { TransformComponent } from '../EntityComponentSystem/Components/TransformComponent'; -import { Entity } from '../EntityComponentSystem/Entity'; -import { Camera } from '../Camera'; -import { Query, System, SystemPriority, SystemType, World } from '../EntityComponentSystem'; -import { Engine } from '../Engine'; +import type { Entity } from '../EntityComponentSystem/Entity'; +import type { Camera } from '../Camera'; +import type { Query, World } from '../EntityComponentSystem'; +import { System, SystemPriority, SystemType } from '../EntityComponentSystem'; +import type { Engine } from '../Engine'; import { GraphicsGroup } from './GraphicsGroup'; import { ParallaxComponent } from './ParallaxComponent'; import { CoordPlane } from '../Math/coord-plane'; diff --git a/src/engine/Graphics/ImageSource.ts b/src/engine/Graphics/ImageSource.ts index 5f843fef..ad29d99a 100644 --- a/src/engine/Graphics/ImageSource.ts +++ b/src/engine/Graphics/ImageSource.ts @@ -1,12 +1,13 @@ import { Resource } from '../Resources/Resource'; -import { Sprite, SpriteOptions } from './Sprite'; -import { Loadable } from '../Interfaces/Index'; +import type { SpriteOptions } from './Sprite'; +import { Sprite } from './Sprite'; +import type { Loadable } from '../Interfaces/Index'; import { Logger } from '../Util/Log'; import { ImageFiltering } from './Filtering'; import { Future } from '../Util/Future'; import { TextureLoader } from '../Graphics/Context/texture-loader'; import { ImageWrapping } from './Wrapping'; -import { GraphicOptions } from './Graphic'; +import type { GraphicOptions } from './Graphic'; export interface ImageSourceOptions { filtering?: ImageFiltering; diff --git a/src/engine/Graphics/Line.ts b/src/engine/Graphics/Line.ts index 2cf397d1..cbf8b1bf 100644 --- a/src/engine/Graphics/Line.ts +++ b/src/engine/Graphics/Line.ts @@ -1,7 +1,7 @@ import { BoundingBox } from '../Collision/BoundingBox'; import { Color } from '../Color'; -import { Vector } from '../Math/vector'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { Vector } from '../Math/vector'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; import { Graphic } from './Graphic'; export interface LineOptions { diff --git a/src/engine/Graphics/NineSlice.ts b/src/engine/Graphics/NineSlice.ts index d88acbee..aaaef68a 100644 --- a/src/engine/Graphics/NineSlice.ts +++ b/src/engine/Graphics/NineSlice.ts @@ -1,6 +1,7 @@ -import { Graphic, GraphicOptions } from './Graphic'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; -import { ImageSource } from './ImageSource'; +import type { GraphicOptions } from './Graphic'; +import { Graphic } from './Graphic'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { ImageSource } from './ImageSource'; import { Logger } from '../Util/Log'; import { Vector } from '../Math/vector'; diff --git a/src/engine/Graphics/OffscreenSystem.ts b/src/engine/Graphics/OffscreenSystem.ts index 69840688..629cda31 100644 --- a/src/engine/Graphics/OffscreenSystem.ts +++ b/src/engine/Graphics/OffscreenSystem.ts @@ -1,15 +1,16 @@ import { GraphicsComponent } from './GraphicsComponent'; import { EnterViewPortEvent, ExitViewPortEvent } from '../Events'; -import { Scene } from '../Scene'; -import { Screen } from '../Screen'; +import type { Scene } from '../Scene'; +import type { Screen } from '../Screen'; import { TransformComponent } from '../EntityComponentSystem/Components/TransformComponent'; -import { Camera } from '../Camera'; +import type { Camera } from '../Camera'; import { System, SystemType } from '../EntityComponentSystem/System'; import { ParallaxComponent } from './ParallaxComponent'; import { Vector } from '../Math/vector'; import { CoordPlane } from '../Math/coord-plane'; -import { BoundingBox } from '../Collision/BoundingBox'; -import { Query, SystemPriority, World } from '../EntityComponentSystem'; +import type { BoundingBox } from '../Collision/BoundingBox'; +import type { Query, World } from '../EntityComponentSystem'; +import { SystemPriority } from '../EntityComponentSystem'; export class OffscreenSystem extends System { static priority: number = SystemPriority.Higher; diff --git a/src/engine/Graphics/ParallaxComponent.ts b/src/engine/Graphics/ParallaxComponent.ts index b462bcbb..f0f5c21c 100644 --- a/src/engine/Graphics/ParallaxComponent.ts +++ b/src/engine/Graphics/ParallaxComponent.ts @@ -1,5 +1,6 @@ import { Component } from '../EntityComponentSystem/Component'; -import { vec, Vector } from '../Math/vector'; +import type { Vector } from '../Math/vector'; +import { vec } from '../Math/vector'; export class ParallaxComponent extends Component { parallaxFactor = vec(1.0, 1.0); diff --git a/src/engine/Graphics/Polygon.ts b/src/engine/Graphics/Polygon.ts index 6c7ebcbe..95407384 100644 --- a/src/engine/Graphics/Polygon.ts +++ b/src/engine/Graphics/Polygon.ts @@ -1,6 +1,8 @@ import { ImageFiltering } from './Filtering'; -import { Vector, vec } from '../Math/vector'; -import { Raster, RasterOptions } from './Raster'; +import type { Vector } from '../Math/vector'; +import { vec } from '../Math/vector'; +import type { RasterOptions } from './Raster'; +import { Raster } from './Raster'; export interface PolygonOptions { points: Vector[]; diff --git a/src/engine/Graphics/PostProcessor/ColorBlindnessPostProcessor.ts b/src/engine/Graphics/PostProcessor/ColorBlindnessPostProcessor.ts index e3e7d093..b0fae7da 100644 --- a/src/engine/Graphics/PostProcessor/ColorBlindnessPostProcessor.ts +++ b/src/engine/Graphics/PostProcessor/ColorBlindnessPostProcessor.ts @@ -1,10 +1,10 @@ import colorBlindCorrectSource from './color-blind-fragment.glsl'; -import { PostProcessor } from './PostProcessor'; +import type { PostProcessor } from './PostProcessor'; import { ColorBlindnessMode } from './ColorBlindnessMode'; -import { Shader } from '../Context/shader'; -import { VertexLayout } from '../Context/vertex-layout'; +import type { Shader } from '../Context/shader'; +import type { VertexLayout } from '../Context/vertex-layout'; import { ScreenShader } from './ScreenShader'; -import { ExcaliburGraphicsContextWebGL } from '../Context/ExcaliburGraphicsContextWebGL'; +import type { ExcaliburGraphicsContextWebGL } from '../Context/ExcaliburGraphicsContextWebGL'; export class ColorBlindnessPostProcessor implements PostProcessor { private _shader!: ScreenShader; diff --git a/src/engine/Graphics/PostProcessor/PostProcessor.ts b/src/engine/Graphics/PostProcessor/PostProcessor.ts index 13fc99f0..2035419c 100644 --- a/src/engine/Graphics/PostProcessor/PostProcessor.ts +++ b/src/engine/Graphics/PostProcessor/PostProcessor.ts @@ -1,6 +1,6 @@ -import { VertexLayout } from '../Context/vertex-layout'; -import { Shader } from '../Context/shader'; -import { ExcaliburGraphicsContextWebGL } from '../Context/ExcaliburGraphicsContextWebGL'; +import type { VertexLayout } from '../Context/vertex-layout'; +import type { Shader } from '../Context/shader'; +import type { ExcaliburGraphicsContextWebGL } from '../Context/ExcaliburGraphicsContextWebGL'; /** * PostProcessors can be used to apply a shader to the entire screen. It is recommended diff --git a/src/engine/Graphics/PostProcessor/ScreenShader.ts b/src/engine/Graphics/PostProcessor/ScreenShader.ts index bff5ed8c..c9eaa32e 100644 --- a/src/engine/Graphics/PostProcessor/ScreenShader.ts +++ b/src/engine/Graphics/PostProcessor/ScreenShader.ts @@ -1,5 +1,5 @@ import { Logger } from '../../Util/Log'; -import { ExcaliburGraphicsContextWebGL } from '../Context/ExcaliburGraphicsContextWebGL'; +import type { ExcaliburGraphicsContextWebGL } from '../Context/ExcaliburGraphicsContextWebGL'; import { Shader } from '../Context/shader'; import { VertexBuffer } from '../Context/vertex-buffer'; import { VertexLayout } from '../Context/vertex-layout'; diff --git a/src/engine/Graphics/Raster.ts b/src/engine/Graphics/Raster.ts index 10e53fd0..bc78d11b 100644 --- a/src/engine/Graphics/Raster.ts +++ b/src/engine/Graphics/Raster.ts @@ -1,10 +1,11 @@ -import { Graphic, GraphicOptions } from './Graphic'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { GraphicOptions } from './Graphic'; +import { Graphic } from './Graphic'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; import { Color } from '../Color'; import { Vector } from '../Math/vector'; import { BoundingBox } from '../Collision/BoundingBox'; import { watch } from '../Util/Watch'; -import { ImageFiltering } from './Filtering'; +import type { ImageFiltering } from './Filtering'; import { omit } from '../Util/Util'; export interface RasterOptions extends GraphicOptions { diff --git a/src/engine/Graphics/Rectangle.ts b/src/engine/Graphics/Rectangle.ts index affb7528..94ee3fe6 100644 --- a/src/engine/Graphics/Rectangle.ts +++ b/src/engine/Graphics/Rectangle.ts @@ -1,4 +1,5 @@ -import { Raster, RasterOptions } from './Raster'; +import type { RasterOptions } from './Raster'; +import { Raster } from './Raster'; export interface RectangleOptions { width: number; diff --git a/src/engine/Graphics/Sprite.ts b/src/engine/Graphics/Sprite.ts index 6d70dab7..154d34ad 100644 --- a/src/engine/Graphics/Sprite.ts +++ b/src/engine/Graphics/Sprite.ts @@ -1,6 +1,7 @@ -import { Graphic, GraphicOptions } from './Graphic'; -import { ImageSource } from './ImageSource'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { GraphicOptions } from './Graphic'; +import { Graphic } from './Graphic'; +import type { ImageSource } from './ImageSource'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; import { Logger } from '../Util/Log'; export type SourceView = { x: number; y: number; width: number; height: number }; diff --git a/src/engine/Graphics/SpriteFont.ts b/src/engine/Graphics/SpriteFont.ts index 06853048..6953990e 100644 --- a/src/engine/Graphics/SpriteFont.ts +++ b/src/engine/Graphics/SpriteFont.ts @@ -1,10 +1,11 @@ import { Vector } from '../Math/vector'; import { Logger } from '../Util/Log'; -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; -import { FontRenderer } from './FontCommon'; -import { Graphic, GraphicOptions } from './Graphic'; -import { Sprite } from './Sprite'; -import { SpriteSheet } from './SpriteSheet'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { FontRenderer } from './FontCommon'; +import type { GraphicOptions } from './Graphic'; +import { Graphic } from './Graphic'; +import type { Sprite } from './Sprite'; +import type { SpriteSheet } from './SpriteSheet'; import { BoundingBox } from '../Collision/BoundingBox'; export interface SpriteFontOptions { diff --git a/src/engine/Graphics/SpriteSheet.ts b/src/engine/Graphics/SpriteSheet.ts index 0d2bde7c..4b61de82 100644 --- a/src/engine/Graphics/SpriteSheet.ts +++ b/src/engine/Graphics/SpriteSheet.ts @@ -1,7 +1,9 @@ -import { ImageSource } from './ImageSource'; -import { SourceView, Sprite } from './Sprite'; -import { GraphicOptions } from './Graphic'; -import { TiledSprite, TiledSpriteOptions } from './TiledSprite'; +import type { ImageSource } from './ImageSource'; +import type { SourceView } from './Sprite'; +import { Sprite } from './Sprite'; +import type { GraphicOptions } from './Graphic'; +import type { TiledSpriteOptions } from './TiledSprite'; +import { TiledSprite } from './TiledSprite'; import { Vector } from '../Math/vector'; /** diff --git a/src/engine/Graphics/Text.ts b/src/engine/Graphics/Text.ts index 0a33e9e1..7499f461 100644 --- a/src/engine/Graphics/Text.ts +++ b/src/engine/Graphics/Text.ts @@ -1,7 +1,8 @@ -import { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; -import { BoundingBox } from '../Collision/BoundingBox'; -import { SpriteFont } from './SpriteFont'; -import { Graphic, GraphicOptions } from './Graphic'; +import type { ExcaliburGraphicsContext } from './Context/ExcaliburGraphicsContext'; +import type { BoundingBox } from '../Collision/BoundingBox'; +import type { SpriteFont } from './SpriteFont'; +import type { GraphicOptions } from './Graphic'; +import { Graphic } from './Graphic'; import { Color } from '../Color'; import { Font } from './Font'; diff --git a/src/engine/Graphics/TiledAnimation.ts b/src/engine/Graphics/TiledAnimation.ts index 5d5ff8ed..8df65d39 100644 --- a/src/engine/Graphics/TiledAnimation.ts +++ b/src/engine/Graphics/TiledAnimation.ts @@ -1,9 +1,11 @@ -import { ImageFiltering } from './Filtering'; -import { ImageWrapConfiguration } from './ImageSource'; -import { SourceView, Sprite } from './Sprite'; -import { ImageWrapping } from './Wrapping'; -import { Animation, AnimationOptions } from './Animation'; -import { GraphicOptions } from './Graphic'; +import type { ImageFiltering } from './Filtering'; +import type { ImageWrapConfiguration } from './ImageSource'; +import type { SourceView } from './Sprite'; +import { Sprite } from './Sprite'; +import type { ImageWrapping } from './Wrapping'; +import type { AnimationOptions } from './Animation'; +import { Animation } from './Animation'; +import type { GraphicOptions } from './Graphic'; import { TiledSprite } from './TiledSprite'; import { watch } from '../Util/Watch'; import { Future } from '../Util/Future'; diff --git a/src/engine/Graphics/TiledSprite.ts b/src/engine/Graphics/TiledSprite.ts index 406a407a..f0d64402 100644 --- a/src/engine/Graphics/TiledSprite.ts +++ b/src/engine/Graphics/TiledSprite.ts @@ -1,8 +1,10 @@ import { Future } from '../Util/Future'; -import { ImageFiltering } from './Filtering'; -import { GraphicOptions } from './Graphic'; -import { ImageSource, ImageWrapConfiguration } from './ImageSource'; -import { SourceView, Sprite } from './Sprite'; +import type { ImageFiltering } from './Filtering'; +import type { GraphicOptions } from './Graphic'; +import type { ImageWrapConfiguration } from './ImageSource'; +import { ImageSource } from './ImageSource'; +import type { SourceView } from './Sprite'; +import { Sprite } from './Sprite'; import { ImageWrapping } from './Wrapping'; export interface TiledSpriteOptions { diff --git a/src/engine/Input/Gamepad.ts b/src/engine/Input/Gamepad.ts index 392cb7c5..66fa227e 100644 --- a/src/engine/Input/Gamepad.ts +++ b/src/engine/Input/Gamepad.ts @@ -1,5 +1,6 @@ import { GamepadConnectEvent, GamepadDisconnectEvent, GamepadButtonEvent, GamepadAxisEvent } from '../Events'; -import { EventEmitter, EventKey, Handler, Subscription } from '../EventEmitter'; +import type { EventKey, Handler, Subscription } from '../EventEmitter'; +import { EventEmitter } from '../EventEmitter'; export type GamepadEvents = { connect: GamepadConnectEvent; diff --git a/src/engine/Input/InputHost.ts b/src/engine/Input/InputHost.ts index 6abdbdff..56d0dbba 100644 --- a/src/engine/Input/InputHost.ts +++ b/src/engine/Input/InputHost.ts @@ -1,4 +1,4 @@ -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; import { Gamepads } from './Gamepad'; import { InputMapper } from './InputMapper'; import { Keyboard } from './Keyboard'; diff --git a/src/engine/Input/InputMapper.ts b/src/engine/Input/InputMapper.ts index c6e9e2b3..0c20cad5 100644 --- a/src/engine/Input/InputMapper.ts +++ b/src/engine/Input/InputMapper.ts @@ -1,6 +1,6 @@ -import { Gamepads } from './Gamepad'; -import { Keyboard } from './Keyboard'; -import { PointerEventReceiver } from './PointerEventReceiver'; +import type { Gamepads } from './Gamepad'; +import type { Keyboard } from './Keyboard'; +import type { PointerEventReceiver } from './PointerEventReceiver'; export interface InputsOptions { keyboard: Keyboard; diff --git a/src/engine/Input/Keyboard.ts b/src/engine/Input/Keyboard.ts index f44d4849..8043d3f6 100644 --- a/src/engine/Input/Keyboard.ts +++ b/src/engine/Input/Keyboard.ts @@ -1,7 +1,8 @@ import { Logger } from '../Util/Log'; import * as Events from '../Events'; import { isCrossOriginIframe } from '../Util/IFrame'; -import { EventEmitter, EventKey, Handler, Subscription } from '../EventEmitter'; +import type { EventKey, Handler, Subscription } from '../EventEmitter'; +import { EventEmitter } from '../EventEmitter'; /** * Enum representing physical input key codes diff --git a/src/engine/Input/PointerAbstraction.ts b/src/engine/Input/PointerAbstraction.ts index a657d2a3..d484d3a8 100644 --- a/src/engine/Input/PointerAbstraction.ts +++ b/src/engine/Input/PointerAbstraction.ts @@ -1,9 +1,10 @@ import { Vector } from '../Math/vector'; -import { PointerEvent } from './PointerEvent'; -import { EventEmitter, EventKey, Handler, Subscription } from '../EventEmitter'; -import { PointerEvents } from './PointerEventReceiver'; +import type { PointerEvent } from './PointerEvent'; +import type { EventKey, Handler, Subscription } from '../EventEmitter'; +import { EventEmitter } from '../EventEmitter'; +import type { PointerEvents } from './PointerEventReceiver'; import { GlobalCoordinates } from '../Math/global-coordinates'; -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; export class PointerAbstraction { public events = new EventEmitter(); diff --git a/src/engine/Input/PointerComponent.ts b/src/engine/Input/PointerComponent.ts index 44094dfb..020a2d6b 100644 --- a/src/engine/Input/PointerComponent.ts +++ b/src/engine/Input/PointerComponent.ts @@ -1,5 +1,5 @@ import { Component } from '../EntityComponentSystem/Component'; -import { BoundingBox } from '../Collision/BoundingBox'; +import type { BoundingBox } from '../Collision/BoundingBox'; export interface PointerComponentOptions { useColliderShape?: boolean; diff --git a/src/engine/Input/PointerEvent.ts b/src/engine/Input/PointerEvent.ts index 73971496..dd42cf9f 100644 --- a/src/engine/Input/PointerEvent.ts +++ b/src/engine/Input/PointerEvent.ts @@ -1,7 +1,7 @@ -import { GlobalCoordinates } from '../Math/global-coordinates'; -import { Vector } from '../Math/vector'; -import { PointerButton } from './PointerButton'; -import { PointerType } from './PointerType'; +import type { GlobalCoordinates } from '../Math/global-coordinates'; +import type { Vector } from '../Math/vector'; +import type { PointerButton } from './PointerButton'; +import type { PointerType } from './PointerType'; export class PointerEvent { public active = true; diff --git a/src/engine/Input/PointerEventReceiver.ts b/src/engine/Input/PointerEventReceiver.ts index 338c1730..79f6a9cc 100644 --- a/src/engine/Input/PointerEventReceiver.ts +++ b/src/engine/Input/PointerEventReceiver.ts @@ -1,6 +1,8 @@ -import { Engine, ScrollPreventionMode } from '../Engine'; +import type { Engine } from '../Engine'; +import { ScrollPreventionMode } from '../Engine'; import { GlobalCoordinates } from '../Math/global-coordinates'; -import { vec, Vector } from '../Math/vector'; +import type { Vector } from '../Math/vector'; +import { vec } from '../Math/vector'; import { PointerEvent } from './PointerEvent'; import { WheelEvent } from './WheelEvent'; import { PointerAbstraction } from './PointerAbstraction'; @@ -12,7 +14,8 @@ import { PointerButton } from './PointerButton'; import { fail } from '../Util/Util'; import { PointerType } from './PointerType'; import { isCrossOriginIframe } from '../Util/IFrame'; -import { EventEmitter, EventKey, Handler, Subscription } from '../EventEmitter'; +import type { EventKey, Handler, Subscription } from '../EventEmitter'; +import { EventEmitter } from '../EventEmitter'; export type NativePointerEvent = globalThis.PointerEvent; export type NativeMouseEvent = globalThis.MouseEvent; diff --git a/src/engine/Input/PointerEventsToObjectDispatcher.ts b/src/engine/Input/PointerEventsToObjectDispatcher.ts index acc94178..b4b748a9 100644 --- a/src/engine/Input/PointerEventsToObjectDispatcher.ts +++ b/src/engine/Input/PointerEventsToObjectDispatcher.ts @@ -1,7 +1,7 @@ -import { EventEmitter } from '../EventEmitter'; -import { PointerEvent } from './PointerEvent'; -import { GlobalCoordinates } from '../Math'; -import { PointerEventReceiver } from './PointerEventReceiver'; +import type { EventEmitter } from '../EventEmitter'; +import type { PointerEvent } from './PointerEvent'; +import type { GlobalCoordinates } from '../Math'; +import type { PointerEventReceiver } from './PointerEventReceiver'; import { RentalPool } from '../Util/RentalPool'; /** diff --git a/src/engine/Input/PointerSystem.ts b/src/engine/Input/PointerSystem.ts index 0315c029..7d39627c 100644 --- a/src/engine/Input/PointerSystem.ts +++ b/src/engine/Input/PointerSystem.ts @@ -1,9 +1,10 @@ -import { Engine } from '../Engine'; -import { System, TransformComponent, SystemType, Entity, World, Query, SystemPriority } from '../EntityComponentSystem'; +import type { Engine } from '../Engine'; +import type { Entity, World, Query } from '../EntityComponentSystem'; +import { System, TransformComponent, SystemType, SystemPriority } from '../EntityComponentSystem'; import { GraphicsComponent } from '../Graphics/GraphicsComponent'; -import { Scene } from '../Scene'; +import type { Scene } from '../Scene'; import { PointerComponent } from './PointerComponent'; -import { PointerEventReceiver } from './PointerEventReceiver'; +import type { PointerEventReceiver } from './PointerEventReceiver'; import { CoordPlane } from '../Math/coord-plane'; import { SparseHashGrid } from '../Collision/Detection/SparseHashGrid'; import { PointerEventsToObjectDispatcher } from './PointerEventsToObjectDispatcher'; diff --git a/src/engine/Input/WheelEvent.ts b/src/engine/Input/WheelEvent.ts index bc15916b..9d5d9a30 100644 --- a/src/engine/Input/WheelEvent.ts +++ b/src/engine/Input/WheelEvent.ts @@ -1,4 +1,4 @@ -import { WheelDeltaMode } from './WheelDeltaMode'; +import type { WheelDeltaMode } from './WheelDeltaMode'; export class WheelEvent { public active = true; diff --git a/src/engine/Interfaces/AudioImplementation.ts b/src/engine/Interfaces/AudioImplementation.ts index 288e93fb..9a783c9b 100644 --- a/src/engine/Interfaces/AudioImplementation.ts +++ b/src/engine/Interfaces/AudioImplementation.ts @@ -1,4 +1,4 @@ -import { Audio } from './Audio'; +import type { Audio } from './Audio'; export type ExResponseType = '' | 'arraybuffer' | 'blob' | 'document' | 'json' | 'text'; diff --git a/src/engine/Interfaces/Evented.ts b/src/engine/Interfaces/Evented.ts index 4fda8d32..f458d0d6 100644 --- a/src/engine/Interfaces/Evented.ts +++ b/src/engine/Interfaces/Evented.ts @@ -1,4 +1,4 @@ -import { Handler } from '../EventEmitter'; +import type { Handler } from '../EventEmitter'; export interface Eventable { /** diff --git a/src/engine/Interfaces/LifecycleEvents.ts b/src/engine/Interfaces/LifecycleEvents.ts index 91bc938f..4755d3fb 100644 --- a/src/engine/Interfaces/LifecycleEvents.ts +++ b/src/engine/Interfaces/LifecycleEvents.ts @@ -1,7 +1,7 @@ -import { Engine } from './../Engine'; -import * as Events from './../Events'; -import { Scene } from '../Scene'; -import { ExcaliburGraphicsContext } from '../Graphics'; +import type { Engine } from './../Engine'; +import type * as Events from './../Events'; +import type { Scene } from '../Scene'; +import type { ExcaliburGraphicsContext } from '../Graphics'; // eslint-disable-next-line @typescript-eslint/naming-convention export interface _initialize { diff --git a/src/engine/Interfaces/PointerEventHandlers.ts b/src/engine/Interfaces/PointerEventHandlers.ts index 791438e7..d92b1dd7 100644 --- a/src/engine/Interfaces/PointerEventHandlers.ts +++ b/src/engine/Interfaces/PointerEventHandlers.ts @@ -1,6 +1,6 @@ -import * as Events from '../Events'; -import { PointerEvent } from '../Input/PointerEvent'; -import { WheelEvent } from '../Input/WheelEvent'; +import type * as Events from '../Events'; +import type { PointerEvent } from '../Input/PointerEvent'; +import type { WheelEvent } from '../Input/WheelEvent'; export interface PointerEvents { on(eventName: Events.pointerup, handler: (event: PointerEvent) => void): void; on(eventName: Events.pointerdown, handler: (event: PointerEvent) => void): void; diff --git a/src/engine/Label.ts b/src/engine/Label.ts index fae988df..1a0c47af 100644 --- a/src/engine/Label.ts +++ b/src/engine/Label.ts @@ -1,11 +1,12 @@ -import { Engine } from './Engine'; -import { Color } from './Color'; +import type { Engine } from './Engine'; +import type { Color } from './Color'; import { vec, Vector } from './Math/vector'; import { Text } from './Graphics/Text'; -import { GraphicsComponent, SpriteFont } from './Graphics'; +import type { SpriteFont } from './Graphics'; +import { GraphicsComponent } from './Graphics'; import { Font } from './Graphics/Font'; import { Actor } from './Actor'; -import { ActorArgs } from './Actor'; +import type { ActorArgs } from './Actor'; /** * Option for creating a label diff --git a/src/engine/Math/bezier-curve.ts b/src/engine/Math/bezier-curve.ts index dcc0e056..5d40c664 100644 --- a/src/engine/Math/bezier-curve.ts +++ b/src/engine/Math/bezier-curve.ts @@ -1,5 +1,5 @@ import { lerpVector, remap } from './lerp'; -import { Vector } from './vector'; +import type { Vector } from './vector'; export interface BezierCurveOptions { /** diff --git a/src/engine/Math/global-coordinates.ts b/src/engine/Math/global-coordinates.ts index 865d61b5..f5d64e0c 100644 --- a/src/engine/Math/global-coordinates.ts +++ b/src/engine/Math/global-coordinates.ts @@ -1,4 +1,4 @@ -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; import { Vector } from './vector'; export class GlobalCoordinates { diff --git a/src/engine/Math/lerp.ts b/src/engine/Math/lerp.ts index 2aa34933..93c30bf1 100644 --- a/src/engine/Math/lerp.ts +++ b/src/engine/Math/lerp.ts @@ -1,6 +1,6 @@ import { RotationType } from './rotation-type'; import { TwoPI } from './util'; -import { Vector } from './vector'; +import type { Vector } from './vector'; /** * Linear interpolation between `a` and `b`, at `time = 0` the value will be `a` at `time = 1` the value will be `b` diff --git a/src/engine/Math/line-segment.ts b/src/engine/Math/line-segment.ts index 5590fbaa..2963212f 100644 --- a/src/engine/Math/line-segment.ts +++ b/src/engine/Math/line-segment.ts @@ -1,4 +1,4 @@ -import { AffineMatrix } from './affine-matrix'; +import type { AffineMatrix } from './affine-matrix'; import { Vector } from './vector'; /** diff --git a/src/engine/Math/ray.ts b/src/engine/Math/ray.ts index 44989fc8..3e1d5b6d 100644 --- a/src/engine/Math/ray.ts +++ b/src/engine/Math/ray.ts @@ -1,5 +1,5 @@ -import { LineSegment } from './line-segment'; -import { Vector } from './vector'; +import type { LineSegment } from './line-segment'; +import type { Vector } from './vector'; /** * A 2D ray that can be cast into the scene to do collision detection diff --git a/src/engine/Math/transform.ts b/src/engine/Math/transform.ts index 01a9756a..387470a4 100644 --- a/src/engine/Math/transform.ts +++ b/src/engine/Math/transform.ts @@ -1,6 +1,7 @@ import { AffineMatrix } from './affine-matrix'; import { canonicalizeAngle, sign } from './util'; -import { vec, Vector } from './vector'; +import type { Vector } from './vector'; +import { vec } from './vector'; import { VectorView } from './vector-view'; import { WatchVector } from './watch-vector'; diff --git a/src/engine/Math/vector.ts b/src/engine/Math/vector.ts index 863ddd00..4d0ef4a1 100644 --- a/src/engine/Math/vector.ts +++ b/src/engine/Math/vector.ts @@ -1,4 +1,4 @@ -import { Clonable } from '../Interfaces/Clonable'; +import type { Clonable } from '../Interfaces/Clonable'; import { RotationType } from './rotation-type'; import { canonicalizeAngle, clamp, TwoPI } from './util'; diff --git a/src/engine/Particles/GpuParticleEmitter.ts b/src/engine/Particles/GpuParticleEmitter.ts index 1a1fa965..8b012eae 100644 --- a/src/engine/Particles/GpuParticleEmitter.ts +++ b/src/engine/Particles/GpuParticleEmitter.ts @@ -1,14 +1,17 @@ -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; import { Actor } from '../Actor'; import { EmitterType } from './EmitterType'; -import { ParticleEmitterArgs, ParticleTransform } from './Particles'; -import { GpuParticleConfig, GpuParticleRenderer } from './GpuParticleRenderer'; +import type { ParticleEmitterArgs } from './Particles'; +import { ParticleTransform } from './Particles'; +import type { GpuParticleConfig } from './GpuParticleRenderer'; +import { GpuParticleRenderer } from './GpuParticleRenderer'; import { GraphicsComponent } from '../Graphics/GraphicsComponent'; import { Random } from '../Math/Random'; -import { vec, Vector } from '../Math/vector'; +import type { Vector } from '../Math/vector'; +import { vec } from '../Math/vector'; import { clamp } from '../Math'; -import { ExcaliburGraphicsContextWebGL } from '../Graphics/Context/ExcaliburGraphicsContextWebGL'; -import { ParticleRenderer } from '../Graphics/Context/particle-renderer/particle-renderer'; +import type { ExcaliburGraphicsContextWebGL } from '../Graphics/Context/ExcaliburGraphicsContextWebGL'; +import type { ParticleRenderer } from '../Graphics/Context/particle-renderer/particle-renderer'; export class GpuParticleEmitter extends Actor { public particle: GpuParticleConfig = { diff --git a/src/engine/Particles/GpuParticleRenderer.ts b/src/engine/Particles/GpuParticleRenderer.ts index cc7974ee..a1576b0a 100644 --- a/src/engine/Particles/GpuParticleRenderer.ts +++ b/src/engine/Particles/GpuParticleRenderer.ts @@ -1,9 +1,10 @@ import { randomInRange, TwoPI } from '../Math/util'; -import { ExcaliburGraphicsContextWebGL } from '../Graphics/Context/ExcaliburGraphicsContextWebGL'; -import { GpuParticleEmitter } from './GpuParticleEmitter'; -import { ParticleConfig, ParticleTransform } from './Particles'; -import { Random } from '../Math/Random'; -import { Sprite } from '../Graphics/Sprite'; +import type { ExcaliburGraphicsContextWebGL } from '../Graphics/Context/ExcaliburGraphicsContextWebGL'; +import type { GpuParticleEmitter } from './GpuParticleEmitter'; +import type { ParticleConfig } from './Particles'; +import { ParticleTransform } from './Particles'; +import type { Random } from '../Math/Random'; +import type { Sprite } from '../Graphics/Sprite'; import { EmitterType } from './EmitterType'; import { assert } from '../Util/Assert'; import { vec } from '../Math/vector'; diff --git a/src/engine/Particles/ParticleEmitter.ts b/src/engine/Particles/ParticleEmitter.ts index 98e2ffc2..da0e2f55 100644 --- a/src/engine/Particles/ParticleEmitter.ts +++ b/src/engine/Particles/ParticleEmitter.ts @@ -1,11 +1,12 @@ -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; import { Actor } from '../Actor'; import { vec } from '../Math/vector'; import { Random } from '../Math/Random'; import { CollisionType } from '../Collision/CollisionType'; import { randomInRange } from '../Math/util'; import { EmitterType } from './EmitterType'; -import { Particle, ParticleTransform, ParticleEmitterArgs, ParticleConfig } from './Particles'; +import type { ParticleEmitterArgs, ParticleConfig } from './Particles'; +import { Particle, ParticleTransform } from './Particles'; import { RentalPool } from '../Util/RentalPool'; /** diff --git a/src/engine/Particles/Particles.ts b/src/engine/Particles/Particles.ts index 4e6dd97d..37bb1149 100644 --- a/src/engine/Particles/Particles.ts +++ b/src/engine/Particles/Particles.ts @@ -1,14 +1,14 @@ -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; import { Color } from '../Color'; import { Vector, vec } from '../Math/vector'; -import { Random } from '../Math/Random'; +import type { Random } from '../Math/Random'; import { TransformComponent } from '../EntityComponentSystem/Components/TransformComponent'; import { GraphicsComponent } from '../Graphics/GraphicsComponent'; import { Entity } from '../EntityComponentSystem/Entity'; import { BoundingBox } from '../Collision/BoundingBox'; import { clamp } from '../Math/util'; -import { Graphic } from '../Graphics'; -import { EmitterType } from './EmitterType'; +import type { Graphic } from '../Graphics'; +import type { EmitterType } from './EmitterType'; import { MotionComponent } from '../EntityComponentSystem'; import { EulerIntegrator } from '../Collision/Integrator'; import type { ParticleEmitter } from './ParticleEmitter'; diff --git a/src/engine/Resources/Font.ts b/src/engine/Resources/Font.ts index d2dec1b0..3d781b74 100644 --- a/src/engine/Resources/Font.ts +++ b/src/engine/Resources/Font.ts @@ -1,7 +1,7 @@ import { Font } from '../Graphics/Font'; -import { FontOptions } from '../Graphics/FontCommon'; -import { GraphicOptions, RasterOptions } from '../Graphics'; -import { Loadable } from '../Interfaces/Loadable'; +import type { FontOptions } from '../Graphics/FontCommon'; +import type { GraphicOptions, RasterOptions } from '../Graphics'; +import type { Loadable } from '../Interfaces/Loadable'; import { Resource } from './Resource'; export interface FontSourceOptions extends Omit, GraphicOptions, RasterOptions { diff --git a/src/engine/Resources/Gif.ts b/src/engine/Resources/Gif.ts index a2f274ba..7c59207b 100644 --- a/src/engine/Resources/Gif.ts +++ b/src/engine/Resources/Gif.ts @@ -1,8 +1,8 @@ import { Resource } from './Resource'; -import { Sprite } from '../Graphics/Sprite'; +import type { Sprite } from '../Graphics/Sprite'; import { SpriteSheet } from '../Graphics/SpriteSheet'; import { Animation } from '../Graphics/Animation'; -import { Loadable } from '../Interfaces/Index'; +import type { Loadable } from '../Interfaces/Index'; import { ImageSource } from '../Graphics/ImageSource'; /** * The {@apilink Texture} object allows games built in Excalibur to load image resources. diff --git a/src/engine/Resources/Resource.ts b/src/engine/Resources/Resource.ts index 945511fa..02dedf34 100644 --- a/src/engine/Resources/Resource.ts +++ b/src/engine/Resources/Resource.ts @@ -1,4 +1,4 @@ -import { Loadable } from '../Interfaces/Loadable'; +import type { Loadable } from '../Interfaces/Loadable'; import { Logger } from '../Util/Log'; import { EventEmitter } from '../EventEmitter'; diff --git a/src/engine/Resources/Sound/Sound.ts b/src/engine/Resources/Sound/Sound.ts index 84281a18..f2bfe65a 100644 --- a/src/engine/Resources/Sound/Sound.ts +++ b/src/engine/Resources/Sound/Sound.ts @@ -1,14 +1,15 @@ import { ExResponse } from '../../Interfaces/AudioImplementation'; -import { Audio } from '../../Interfaces/Audio'; -import { Engine } from '../../Engine'; +import type { Audio } from '../../Interfaces/Audio'; +import type { Engine } from '../../Engine'; import { Resource } from '../Resource'; import { WebAudioInstance } from './WebAudioInstance'; import { AudioContextFactory } from './AudioContext'; import { NativeSoundEvent, NativeSoundProcessedEvent } from '../../Events/MediaEvents'; import { canPlayFile } from '../../Util/Sound'; -import { Loadable } from '../../Interfaces/Index'; +import type { Loadable } from '../../Interfaces/Index'; import { Logger } from '../../Util/Log'; -import { EventEmitter, EventKey, Handler, Subscription } from '../../EventEmitter'; +import type { EventKey, Handler, Subscription } from '../../EventEmitter'; +import { EventEmitter } from '../../EventEmitter'; export type SoundEvents = { volumechange: NativeSoundEvent; diff --git a/src/engine/Resources/Sound/WebAudioInstance.ts b/src/engine/Resources/Sound/WebAudioInstance.ts index e4b236fb..a7f74bf2 100644 --- a/src/engine/Resources/Sound/WebAudioInstance.ts +++ b/src/engine/Resources/Sound/WebAudioInstance.ts @@ -1,5 +1,5 @@ import { StateMachine } from '../../Util/StateMachine'; -import { Audio } from '../../Interfaces/Audio'; +import type { Audio } from '../../Interfaces/Audio'; import { clamp } from '../../Math/util'; import { AudioContextFactory } from './AudioContext'; import { Future } from '../../Util/Future'; diff --git a/src/engine/Scene.ts b/src/engine/Scene.ts index 354ab383..a7679570 100644 --- a/src/engine/Scene.ts +++ b/src/engine/Scene.ts @@ -1,8 +1,7 @@ import { isScreenElement, ScreenElement } from './ScreenElement'; +import type { ActivateEvent, DeactivateEvent } from './Events'; import { InitializeEvent, - ActivateEvent, - DeactivateEvent, PreUpdateEvent, PostUpdateEvent, PreDrawEvent, @@ -12,11 +11,11 @@ import { } from './Events'; import { Logger } from './Util/Log'; import { Timer } from './Timer'; -import { Engine } from './Engine'; +import type { Engine } from './Engine'; import { TileMap } from './TileMap'; import { Camera } from './Camera'; import { Actor } from './Actor'; -import { CanInitialize, CanActivate, CanDeactivate, CanUpdate, CanDraw, SceneActivationContext } from './Interfaces/LifecycleEvents'; +import type { CanInitialize, CanActivate, CanDeactivate, CanUpdate, CanDraw, SceneActivationContext } from './Interfaces/LifecycleEvents'; import * as Util from './Util/Util'; import { Trigger } from './Trigger'; import { SystemType } from './EntityComponentSystem/System'; @@ -30,12 +29,13 @@ import { PointerSystem } from './Input/PointerSystem'; import { ActionsSystem } from './Actions/ActionsSystem'; import { IsometricEntitySystem } from './TileMap/IsometricEntitySystem'; import { OffscreenSystem } from './Graphics/OffscreenSystem'; -import { ExcaliburGraphicsContext } from './Graphics'; +import type { ExcaliburGraphicsContext } from './Graphics'; import { PhysicsWorld } from './Collision/PhysicsWorld'; -import { EventEmitter, EventKey, Handler, Subscription } from './EventEmitter'; -import { Color } from './Color'; -import { DefaultLoader } from './Director/DefaultLoader'; -import { Transition } from './Director'; +import type { EventKey, Handler, Subscription } from './EventEmitter'; +import { EventEmitter } from './EventEmitter'; +import type { Color } from './Color'; +import type { DefaultLoader } from './Director/DefaultLoader'; +import type { Transition } from './Director'; import { InputHost } from './Input/InputHost'; import { PointerScope } from './Input/PointerScope'; import { getDefaultPhysicsConfig } from './Collision/PhysicsConfig'; diff --git a/src/engine/Screen.ts b/src/engine/Screen.ts index 74c5cccf..2d098d31 100644 --- a/src/engine/Screen.ts +++ b/src/engine/Screen.ts @@ -1,9 +1,9 @@ import { vec, Vector } from './Math/vector'; import { Logger } from './Util/Log'; -import { Camera } from './Camera'; -import { BrowserEvents } from './Util/Browser'; +import type { Camera } from './Camera'; +import type { BrowserEvents } from './Util/Browser'; import { BoundingBox } from './Collision/Index'; -import { ExcaliburGraphicsContext } from './Graphics/Context/ExcaliburGraphicsContext'; +import type { ExcaliburGraphicsContext } from './Graphics/Context/ExcaliburGraphicsContext'; import { getPosition } from './Util/Util'; import { ExcaliburGraphicsContextWebGL } from './Graphics/Context/ExcaliburGraphicsContextWebGL'; import { ExcaliburGraphicsContext2DCanvas } from './Graphics/Context/ExcaliburGraphicsContext2DCanvas'; diff --git a/src/engine/ScreenElement.ts b/src/engine/ScreenElement.ts index 85b800d2..3f29e74b 100644 --- a/src/engine/ScreenElement.ts +++ b/src/engine/ScreenElement.ts @@ -1,6 +1,7 @@ import { Vector, vec } from './Math/vector'; -import { Engine } from './Engine'; -import { Actor, ActorArgs } from './Actor'; +import type { Engine } from './Engine'; +import type { ActorArgs } from './Actor'; +import { Actor } from './Actor'; import { TransformComponent } from './EntityComponentSystem/Components/TransformComponent'; import { CollisionType } from './Collision/CollisionType'; import { CoordPlane } from './Math/coord-plane'; diff --git a/src/engine/TileMap/IsometricEntityComponent.ts b/src/engine/TileMap/IsometricEntityComponent.ts index ef96a990..3263251f 100644 --- a/src/engine/TileMap/IsometricEntityComponent.ts +++ b/src/engine/TileMap/IsometricEntityComponent.ts @@ -1,5 +1,5 @@ import { Component } from '../EntityComponentSystem/Component'; -import { IsometricMap } from './IsometricMap'; +import type { IsometricMap } from './IsometricMap'; export interface IsometricEntityComponentOptions { columns: number; diff --git a/src/engine/TileMap/IsometricEntitySystem.ts b/src/engine/TileMap/IsometricEntitySystem.ts index d518dd35..27b57462 100644 --- a/src/engine/TileMap/IsometricEntitySystem.ts +++ b/src/engine/TileMap/IsometricEntitySystem.ts @@ -1,7 +1,8 @@ import { System, SystemType } from '../EntityComponentSystem/System'; import { TransformComponent } from '../EntityComponentSystem/Components/TransformComponent'; import { IsometricEntityComponent } from './IsometricEntityComponent'; -import { Query, SystemPriority, World } from '../EntityComponentSystem'; +import type { Query, World } from '../EntityComponentSystem'; +import { SystemPriority } from '../EntityComponentSystem'; export class IsometricEntitySystem extends System { static priority: number = SystemPriority.Lower; diff --git a/src/engine/TileMap/IsometricMap.ts b/src/engine/TileMap/IsometricMap.ts index bfe99129..c4e6e036 100644 --- a/src/engine/TileMap/IsometricMap.ts +++ b/src/engine/TileMap/IsometricMap.ts @@ -1,20 +1,23 @@ import { BodyComponent } from '../Collision/BodyComponent'; import { BoundingBox } from '../Collision/BoundingBox'; import { ColliderComponent } from '../Collision/ColliderComponent'; -import { Collider } from '../Collision/Colliders/Collider'; +import type { Collider } from '../Collision/Colliders/Collider'; import { CollisionType } from '../Collision/CollisionType'; import { CompositeCollider } from '../Collision/Colliders/CompositeCollider'; import { vec, Vector } from '../Math/vector'; import { TransformComponent } from '../EntityComponentSystem/Components/TransformComponent'; -import { Entity, EntityEvents } from '../EntityComponentSystem/Entity'; -import { DebugGraphicsComponent, ExcaliburGraphicsContext, Graphic, GraphicsComponent } from '../Graphics'; +import type { EntityEvents } from '../EntityComponentSystem/Entity'; +import { Entity } from '../EntityComponentSystem/Entity'; +import type { ExcaliburGraphicsContext, Graphic } from '../Graphics'; +import { DebugGraphicsComponent, GraphicsComponent } from '../Graphics'; import { IsometricEntityComponent } from './IsometricEntityComponent'; -import { DebugConfig } from '../Debug'; +import type { DebugConfig } from '../Debug'; import { PointerComponent } from '../Input/PointerComponent'; -import { PointerEvent } from '../Input/PointerEvent'; +import type { PointerEvent } from '../Input/PointerEvent'; import { EventEmitter } from '../EventEmitter'; -import { HasNestedPointerEvents, PointerEventsToObjectDispatcher } from '../Input/PointerEventsToObjectDispatcher'; -import { PointerEventReceiver } from '../Input/PointerEventReceiver'; +import type { HasNestedPointerEvents } from '../Input/PointerEventsToObjectDispatcher'; +import { PointerEventsToObjectDispatcher } from '../Input/PointerEventsToObjectDispatcher'; +import type { PointerEventReceiver } from '../Input/PointerEventReceiver'; export type IsometricTilePointerEvents = { pointerup: PointerEvent; diff --git a/src/engine/TileMap/TileMap.ts b/src/engine/TileMap/TileMap.ts index 1a75aaee..26092a8f 100644 --- a/src/engine/TileMap/TileMap.ts +++ b/src/engine/TileMap/TileMap.ts @@ -1,28 +1,32 @@ import { BoundingBox } from '../Collision/BoundingBox'; -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; import { Vector, vec } from '../Math/vector'; import { Logger } from '../Util/Log'; -import { Entity, EntityEvents } from '../EntityComponentSystem/Entity'; +import type { EntityEvents } from '../EntityComponentSystem/Entity'; +import { Entity } from '../EntityComponentSystem/Entity'; import { TransformComponent } from '../EntityComponentSystem/Components/TransformComponent'; import { BodyComponent } from '../Collision/BodyComponent'; import { CollisionType } from '../Collision/CollisionType'; import { Shape } from '../Collision/Colliders/Shape'; -import { ExcaliburGraphicsContext, Graphic, GraphicsComponent, hasGraphicsTick, ParallaxComponent } from '../Graphics'; +import type { ExcaliburGraphicsContext, Graphic } from '../Graphics'; +import { GraphicsComponent, hasGraphicsTick, ParallaxComponent } from '../Graphics'; import { MotionComponent } from '../EntityComponentSystem/Components/MotionComponent'; import { ColliderComponent } from '../Collision/ColliderComponent'; -import { CompositeCollider } from '../Collision/Colliders/CompositeCollider'; +import type { CompositeCollider } from '../Collision/Colliders/CompositeCollider'; import { DebugGraphicsComponent } from '../Graphics/DebugGraphicsComponent'; -import { Collider } from '../Collision/Colliders/Collider'; +import type { Collider } from '../Collision/Colliders/Collider'; import { PostDrawEvent, PostUpdateEvent, PreDrawEvent, PreUpdateEvent } from '../Events'; -import { EventEmitter, EventKey, Handler, Subscription } from '../EventEmitter'; +import type { EventKey, Handler, Subscription } from '../EventEmitter'; +import { EventEmitter } from '../EventEmitter'; import { CoordPlane } from '../Math/coord-plane'; -import { DebugConfig } from '../Debug'; +import type { DebugConfig } from '../Debug'; import { clamp } from '../Math/util'; import { PointerComponent } from '../Input/PointerComponent'; -import { PointerEvent } from '../Input/PointerEvent'; -import { PointerEventReceiver } from '../Input/PointerEventReceiver'; -import { HasNestedPointerEvents, PointerEventsToObjectDispatcher } from '../Input/PointerEventsToObjectDispatcher'; -import { GlobalCoordinates } from '../Math'; +import type { PointerEvent } from '../Input/PointerEvent'; +import type { PointerEventReceiver } from '../Input/PointerEventReceiver'; +import type { HasNestedPointerEvents } from '../Input/PointerEventsToObjectDispatcher'; +import { PointerEventsToObjectDispatcher } from '../Input/PointerEventsToObjectDispatcher'; +import type { GlobalCoordinates } from '../Math'; export interface TileMapOptions { /** diff --git a/src/engine/Timer.ts b/src/engine/Timer.ts index fde95e0b..9901dc93 100644 --- a/src/engine/Timer.ts +++ b/src/engine/Timer.ts @@ -1,6 +1,6 @@ -import { Scene } from './Scene'; +import type { Scene } from './Scene'; import { Logger } from './Util/Log'; -import * as ex from './index'; +import type * as ex from './index'; import { Random } from './Math/Random'; export interface TimerOptions { diff --git a/src/engine/Trigger.ts b/src/engine/Trigger.ts index a968cb9c..c6a01dd4 100644 --- a/src/engine/Trigger.ts +++ b/src/engine/Trigger.ts @@ -1,8 +1,10 @@ -import { Vector } from './Math/vector'; -import { ExitTriggerEvent, EnterTriggerEvent, CollisionEndEvent, CollisionStartEvent } from './Events'; +import type { Vector } from './Math/vector'; +import type { CollisionEndEvent, CollisionStartEvent } from './Events'; +import { ExitTriggerEvent, EnterTriggerEvent } from './Events'; import { CollisionType } from './Collision/CollisionType'; -import { Entity } from './EntityComponentSystem'; -import { Actor, ActorArgs, ActorEvents } from './Actor'; +import type { Entity } from './EntityComponentSystem'; +import type { ActorArgs, ActorEvents } from './Actor'; +import { Actor } from './Actor'; import { EventEmitter } from './EventEmitter'; export type TriggerEvents = ActorEvents & { diff --git a/src/engine/Util/Coroutine.ts b/src/engine/Util/Coroutine.ts index 5cb76aaf..fab186aa 100644 --- a/src/engine/Util/Coroutine.ts +++ b/src/engine/Util/Coroutine.ts @@ -1,6 +1,6 @@ import { createContext, useContext } from '../Context'; import { Engine } from '../Engine'; -import { ScheduledCallbackTiming } from './Clock'; +import type { ScheduledCallbackTiming } from './Clock'; import { Logger } from './Log'; export type CoroutineGenerator = () => Generator | undefined, void, number>; diff --git a/src/engine/Util/DrawUtil.ts b/src/engine/Util/DrawUtil.ts index 78ca4b4e..6930d718 100644 --- a/src/engine/Util/DrawUtil.ts +++ b/src/engine/Util/DrawUtil.ts @@ -1,5 +1,5 @@ import { Color } from '../Color'; -import { Vector } from '../Math/vector'; +import type { Vector } from '../Math/vector'; /** * A canvas linecap style. "butt" is the default flush style, "round" is a semi-circle cap with a radius half the width of diff --git a/src/engine/Util/Log.ts b/src/engine/Util/Log.ts index e709e228..e963d8d5 100644 --- a/src/engine/Util/Log.ts +++ b/src/engine/Util/Log.ts @@ -1,6 +1,6 @@ /* eslint-disable no-console */ -import { Engine } from '../Engine'; +import type { Engine } from '../Engine'; import { vec } from '../Math/vector'; import { Color } from '../Color'; diff --git a/src/engine/Util/Util.ts b/src/engine/Util/Util.ts index e876d4eb..98e16585 100644 --- a/src/engine/Util/Util.ts +++ b/src/engine/Util/Util.ts @@ -1,5 +1,5 @@ import { Vector, vec } from '../Math/vector'; -import { Clock } from './Clock'; +import type { Clock } from './Clock'; import { Future } from './Future'; /** diff --git a/src/engine/index.ts b/src/engine/index.ts index 453206d6..3e14c90f 100644 --- a/src/engine/index.ts +++ b/src/engine/index.ts @@ -59,16 +59,16 @@ export { PointerButton } from './Input/PointerButton'; export { NativePointerButton } from './Input/NativePointerButton'; -export { CapturePointerConfig } from './Input/CapturePointerConfig'; +export type { CapturePointerConfig } from './Input/CapturePointerConfig'; -export { +export type { NativePointerEvent, NativeMouseEvent, NativeTouchEvent, NativeWheelEvent, - PointerInitOptions, - PointerEventReceiver + PointerInitOptions } from './Input/PointerEventReceiver'; +export { PointerEventReceiver } from './Input/PointerEventReceiver'; export { PointerAbstraction } from './Input/PointerAbstraction'; export { PointerComponent } from './Input/PointerComponent'; @@ -76,19 +76,17 @@ export { PointerSystem } from './Input/PointerSystem'; export { PointerType } from './Input/PointerType'; export { PointerScope } from './Input/PointerScope'; -export { - Gamepads, - Gamepad, - Buttons, - Axes, +export type { NavigatorGamepads, NavigatorGamepad, NavigatorGamepadButton, NavigatorGamepadEvent, GamepadConfiguration } from './Input/Gamepad'; +export { Gamepads, Gamepad, Buttons, Axes } from './Input/Gamepad'; -export { Keys, KeyEvent, KeyboardInitOptions, Keyboard } from './Input/Keyboard'; +export type { KeyboardInitOptions } from './Input/Keyboard'; +export { Keys, KeyEvent, Keyboard } from './Input/Keyboard'; export * from './Input/InputHost'; export * from './Input/InputMapper'; diff --git a/src/spec/ColorBlindCorrectorSpec.ts b/src/spec/ColorBlindCorrectorSpec.ts deleted file mode 100644 index 0e7f732a..00000000 --- a/src/spec/ColorBlindCorrectorSpec.ts +++ /dev/null @@ -1,129 +0,0 @@ -import * as ex from '@excalibur'; -import { TestUtils } from './util/TestUtils'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers, ensureImagesLoaded } from 'excalibur-jasmine'; - -describe('A ColorBlindCorrector', () => { - let bg: ex.ImageSource; - let engine: ex.Engine; - let clock: ex.TestClock; - - beforeEach(async () => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - - engine = TestUtils.engine({ width: 800, height: 200 }, []); - bg = new ex.ImageSource('src/spec/images/ColorBlindCorrectorSpec/actor.png'); - const loader = new ex.Loader([bg]); - clock = engine.clock as ex.TestClock; - await TestUtils.runToReady(engine, loader); - }); - - afterEach(() => { - engine.stop(); - engine.dispose(); - }); - - it('is normal', (done) => { - const actor = new ex.Actor(); - actor.graphics.use(bg.toSprite()); - engine.add(actor); - engine.once('postframe', (ev: ex.PostDrawEvent) => { - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/ColorBlindCorrectorSpec/normal.png') - .then(() => { - done(); - }); - }); - clock.step(1); - }); - - it('corrects deuteranopia', (done) => { - const actor = new ex.Actor(); - actor.graphics.use(bg.toSprite()); - engine.add(actor); - engine.debug.colorBlindMode.correct(ex.ColorBlindnessMode.Deuteranope); - engine.once('postframe', (ev: ex.PostDrawEvent) => { - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/ColorBlindCorrectorSpec/deuteranope_correct.png') - .then(() => { - done(); - }); - }); - clock.step(1); - }); - - it('simulates deuteranopia', (done) => { - const actor = new ex.Actor(); - actor.graphics.use(bg.toSprite()); - engine.add(actor); - engine.debug.colorBlindMode.simulate(ex.ColorBlindnessMode.Deuteranope); - engine.once('postframe', (ev: ex.PostDrawEvent) => { - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/ColorBlindCorrectorSpec/deuteranope_simulate.png') - .then(() => { - done(); - }); - }); - clock.step(1); - }); - - it('corrects protanopia', (done) => { - const actor = new ex.Actor(); - actor.graphics.use(bg.toSprite()); - engine.add(actor); - engine.debug.colorBlindMode.correct(ex.ColorBlindnessMode.Protanope); - engine.once('postframe', (ev: ex.PostDrawEvent) => { - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/ColorBlindCorrectorSpec/protanope_correct.png') - .then(() => { - done(); - }); - }); - clock.step(1); - }); - - it('simulates protanopia', (done) => { - const actor = new ex.Actor(); - actor.graphics.use(bg.toSprite()); - engine.add(actor); - engine.debug.colorBlindMode.simulate(ex.ColorBlindnessMode.Protanope); - engine.once('postframe', (ev: ex.PostDrawEvent) => { - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/ColorBlindCorrectorSpec/protanope_simulate.png') - .then(() => { - done(); - }); - }); - clock.step(1); - }); - - it('corrects tritanopia', (done) => { - const actor = new ex.Actor(); - actor.graphics.use(bg.toSprite()); - engine.add(actor); - engine.debug.colorBlindMode.correct(ex.ColorBlindnessMode.Tritanope); - engine.once('postframe', (ev: ex.PostDrawEvent) => { - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/ColorBlindCorrectorSpec/tritanope_correct.png') - .then(() => { - done(); - }); - }); - clock.step(1); - }); - - it('simulates tritanopia', (done) => { - const actor = new ex.Actor(); - actor.graphics.use(bg.toSprite()); - engine.add(actor); - engine.debug.colorBlindMode.simulate(ex.ColorBlindnessMode.Tritanope); - engine.once('postframe', (ev: ex.PostDrawEvent) => { - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/ColorBlindCorrectorSpec/tritanope_simulate.png') - .then(() => { - done(); - }); - }); - clock.step(1); - }); -}); diff --git a/src/spec/FutureSpec.ts b/src/spec/FutureSpec.ts deleted file mode 100644 index 8ac52c31..00000000 --- a/src/spec/FutureSpec.ts +++ /dev/null @@ -1,73 +0,0 @@ -import * as ex from '@excalibur'; - -describe('A Future', () => { - it('exists', () => { - expect(ex.Future).toBeDefined(); - }); - - it('it can be constructed', () => { - const future = new ex.Future(); - - expect(future).toBeDefined(); - }); - - it('can be resolved', (done) => { - const future = new ex.Future(); - - expect(future.isCompleted).toBe(false); - - future.promise.then(() => { - expect(future.isCompleted).toBe(true); - done(); - }); - future.resolve(); - }); - - it('can be resolved multiple times without error', (done) => { - const future = new ex.Future(); - - expect(future.isCompleted).toBe(false); - - future.promise.then(() => { - expect(future.isCompleted).toBe(true); - done(); - }); - expect(() => { - future.resolve(); - future.resolve(); - future.resolve(); - future.resolve(); - }).not.toThrow(); - }); - - it('can be rejected', (done) => { - const future = new ex.Future(); - - expect(future.isCompleted).toBe(false); - - future.promise.catch((err) => { - expect(err).toEqual(new Error('Some error')); - expect(future.isCompleted).toBe(true); - done(); - }); - future.reject(new Error('Some error')); - }); - - it('can be rejected multiple times without error', (done) => { - const future = new ex.Future(); - - expect(future.isCompleted).toBe(false); - - future.promise.catch(() => { - expect(future.isCompleted).toBe(true); - done(); - }); - expect(() => { - future.reject(new Error('Some error')); - future.reject(new Error('Some error')); - future.reject(new Error('Some error')); - future.reject(new Error('Some error')); - future.reject(new Error('Some error')); - }).not.toThrow(); - }); -}); diff --git a/src/spec/LoaderSpec.ts b/src/spec/LoaderSpec.ts deleted file mode 100644 index 8d5b08b1..00000000 --- a/src/spec/LoaderSpec.ts +++ /dev/null @@ -1,386 +0,0 @@ -import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers, ensureImagesLoaded } from 'excalibur-jasmine'; -import { TestUtils } from './util/TestUtils'; - -describe('A loader', () => { - let engine: ex.Engine; - - const reset = () => { - engine.stop(); - engine.dispose(); - engine = null; - (window).devicePixelRatio = 1; - const playButton = document.getElementById('excalibur-play'); - if (playButton) { - const body = playButton.parentNode.parentNode; - body.removeChild(playButton.parentNode); - } - }; - beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - engine = TestUtils.engine(); - }); - - afterEach(() => { - engine.stop(); - engine.dispose(); - engine = null; - }); - - it('exists', () => { - expect(ex.Loader).toBeDefined(); - }); - - it('can be constructed', () => { - const loader = new ex.Loader(); - expect(loader).toBeTruthy(); - }); - - it('can report progress, empty loaders are done', () => { - const loader = new ex.Loader(); - expect(loader.progress).toBe(1); - }); - - it('can report progress, loader start at 0', () => { - const loader = new ex.Loader([, , ,]); - expect(loader.progress).toBe(0); - }); - - it('can report progress', () => { - const loader = new ex.Loader([, , , ,]); - expect(loader.progress).toBe(0); - loader.markResourceComplete(); - expect(loader.progress).toBe(0.25); - loader.markResourceComplete(); - expect(loader.progress).toBe(0.5); - loader.markResourceComplete(); - expect(loader.progress).toBe(0.75); - loader.markResourceComplete(); - expect(loader.progress).toBe(1); - }); - - it('can be drawn at 0', (done) => { - const loader = new ex.Loader([, , , ,]); - (loader as any)._image.onload = () => { - loader.onInitialize(engine); - loader.onDraw(loader.canvas.ctx); - ensureImagesLoaded(loader.canvas.ctx.canvas, 'src/spec/images/LoaderSpec/zero.png').then(([canvas, image]) => { - expect(canvas).toEqualImage(image); - done(); - }); - }; - }); - - it('can be drawn at 50', (done) => { - const loader = new ex.Loader([, , , ,]); - (loader as any)._image.onload = () => { - loader.markResourceComplete(); - loader.markResourceComplete(); - - loader.onInitialize(engine); - loader.onDraw(loader.canvas.ctx); - ensureImagesLoaded(loader.canvas.ctx.canvas, 'src/spec/images/LoaderSpec/fifty.png').then(([canvas, image]) => { - expect(canvas).toEqualImage(image); - done(); - }); - }; - }); - - it('can be drawn at 100', (done) => { - const loader = new ex.Loader([, , , ,]); - (loader as any)._image.onload = () => { - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - - loader.onInitialize(engine); - loader.onDraw(loader.canvas.ctx); - ensureImagesLoaded(loader.canvas.ctx.canvas, 'src/spec/images/LoaderSpec/100.png').then(([canvas, image]) => { - expect(canvas).toEqualImage(image); - done(); - }); - }; - }); - - it('does not show progress when the play button is shown', (done) => { - const loader = new ex.Loader([, , , ,]); - (loader as any)._image.onload = () => { - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.onInitialize(engine); - loader.showPlayButton(); - - loader.onDraw(loader.canvas.ctx); - ensureImagesLoaded(loader.canvas.ctx.canvas, 'src/spec/images/LoaderSpec/playbuttonshown-noprogressbar.png').then( - ([canvas, image]) => { - expect(canvas).toEqualImage(image); - done(); - } - ); - }; - }); - - it('can have the play button position customized', () => { - const loader = new ex.Loader([, , , ,]); - loader.onInitialize(engine); - loader.playButtonPosition = ex.vec(42, 77); - loader.showPlayButton(); - loader.onDraw(loader.canvas.ctx); - // there is some dom pollution want to be sure we get the RIGHT root element - const playbutton = (loader as any)._playButtonRootElement as HTMLDivElement; - expect(playbutton.style.left).toBe('42px'); - expect(playbutton.style.top).toBe('77px'); - }); - - it('can have the logo position customized', (done) => { - const loader = new ex.Loader([, , , ,]); - (loader as any)._image.onload = () => { - loader.onInitialize(engine); - loader.logoPosition = ex.vec(0, 0); - loader.showPlayButton(); - loader.onDraw(loader.canvas.ctx); - ensureImagesLoaded(loader.canvas.ctx.canvas, 'src/spec/images/LoaderSpec/logo-position.png').then(([canvas, image]) => { - expect(canvas).toEqualImage(image); - done(); - }); - }; - }); - - it('can have the loader customized', (done) => { - const loader = new ex.Loader([, , , ,]); - loader.loadingBarPosition = ex.vec(0, 0); - loader.loadingBarColor = ex.Color.Red; - (loader as any)._image.onload = () => { - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.onInitialize(engine); - loader.onDraw(loader.canvas.ctx); - ensureImagesLoaded(loader.canvas.ctx.canvas, 'src/spec/images/LoaderSpec/loader-position-color.png').then(([canvas, image]) => { - expect(canvas).toEqualImage(image); - done(); - }); - }; - }); - - it('play button shows up after done loading', () => { - const loader = new ex.Loader([, , , ,]); - loader.loadingBarPosition = ex.vec(0, 0); - loader.loadingBarColor = ex.Color.Red; - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.showPlayButton(); - - expect(loader.playButtonRootElement).toBeTruthy(); - }); - - it('play button is cleaned up on dispose', () => { - const loader = new ex.Loader([, , , ,]); - loader.loadingBarPosition = ex.vec(0, 0); - loader.loadingBarColor = ex.Color.Red; - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.showPlayButton(); - loader.dispose(); - expect(loader.playButtonRootElement).toBeFalsy(); - }); - - it('can have the enter key pressed to start', (done) => { - const loader = new ex.Loader([, , , ,]); - loader.onInitialize(engine); - loader.loadingBarPosition = ex.vec(0, 0); - loader.loadingBarColor = ex.Color.Red; - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.showPlayButton().then(() => { - done(); - loader.dispose(); - }); - document.body.dispatchEvent(new KeyboardEvent('keyup', { key: 'Enter' })); - }); - - it('can reload without building root elements', () => { - const loader = new ex.Loader([, , ,]); - loader.showPlayButton(); - loader.showPlayButton(); - loader.showPlayButton(); - const roots = document.querySelectorAll('#excalibur-play-root'); - const buttons = document.querySelectorAll('#excalibur-play'); - expect(roots.length).toBe(1); - expect(buttons.length).toBe(1); - }); - - /** - * - */ - function executeMouseEvent(type: string, target: HTMLElement, button: ex.NativePointerButton = null, x: number = 0, y: number = 0) { - const evt = new PointerEvent(type, { - clientX: x, - clientY: y, - button: button, - bubbles: true - }); - - target.dispatchEvent(evt); - } - - it('does not propagate the start button click to pointers', async () => { - engine.dispose(); - engine = null; - engine = new ex.Engine({ width: 1000, height: 1000 }); - (ex.WebAudio as any)._UNLOCKED = true; - const clock = (engine.clock = engine.clock.toTestClock()); - const pointerHandler = jasmine.createSpy('pointerHandler'); - engine.input.pointers.primary.on('up', pointerHandler); - const loader = new ex.Loader([new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png')]); - const start = engine.start(loader); - - await loader.areResourcesLoaded(); - clock.step(200); - - const btn = (loader as any)._playButton; - const btnClickHandler = jasmine.createSpy('btnClickHandler'); - btn.addEventListener('pointerup', btnClickHandler); - const rect = btn.getBoundingClientRect(); - executeMouseEvent('pointerup', btn as any, ex.NativePointerButton.Left, rect.x + rect.width / 2, rect.y + rect.height / 2); - - expect(pointerHandler).not.toHaveBeenCalled(); - expect(btnClickHandler).toHaveBeenCalled(); - }); - - it('updates the play button position on resize', () => { - engine.dispose(); - engine = null; - engine = new ex.Engine({ width: 1000, height: 1000 }); - const loader = new ex.Loader([, , , ,]); - loader.onInitialize(engine); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.markResourceComplete(); - loader.showPlayButton(); - - expect(loader.playButtonRootElement).toBeTruthy(); - - engine.browser.window.nativeComponent.dispatchEvent(new Event('resize')); - - const oldPos = [loader.playButtonRootElement.style.left, loader.playButtonRootElement.style.top]; - - engine.screen.viewport = { width: 100, height: 100 }; - - engine.browser.window.nativeComponent.dispatchEvent(new Event('resize')); - - const newPos = [loader.playButtonRootElement.style.left, loader.playButtonRootElement.style.top]; - - expect(oldPos).not.toEqual(newPos); - }); - - it('does not throw when more than 256 images are being loaded', (done) => { - /** - * - */ - function drawRandomCircleOnContext(ctx) { - const x = Math.floor(Math.random() * 100); - const y = Math.floor(Math.random() * 100); - const radius = Math.floor(Math.random() * 20); - - const r = Math.floor(Math.random() * 255); - const g = Math.floor(Math.random() * 255); - const b = Math.floor(Math.random() * 255); - - ctx.beginPath(); - ctx.arc(x, y, radius, Math.PI * 2, 0, false); - ctx.fillStyle = 'rgba(' + r + ',' + g + ',' + b + ',1)'; - ctx.fill(); - ctx.closePath(); - } - - /** - * - */ - function generateRandomImage() { - const canvas = document.createElement('canvas'); - canvas.width = 100; - canvas.height = 100; - - const ctx = canvas.getContext('2d'); - ctx.clearRect(0, 0, 100, 100); - - for (let i = 0; i < 20; i++) { - drawRandomCircleOnContext(ctx); - } - return canvas.toDataURL('image/png'); - } - - const logger = ex.Logger.getInstance(); - spyOn(logger, 'error').and.callThrough(); - const game = TestUtils.engine({ - width: 100, - height: 100 - }); - const testClock = game.clock as ex.TestClock; - - const loader = new ex.Loader(); - - const srcs = []; - for (let i = 0; i < 800; i++) { - srcs.push(generateRandomImage()); - } - const images = srcs.map((src) => new ex.ImageSource(src)); - images.forEach((image) => { - image.ready.then(() => { - testClock.step(1); - }); - }); - loader.addResources(images); - - const ready = TestUtils.runToReady(game, loader) - .then(() => { - expect(logger.error).not.toHaveBeenCalled(); - game.dispose(); - done(); - }) - .catch(() => { - fail(); - }); - }); - - it('should not show the play button when suppressPlayButton is turned on', (done) => { - reset(); - engine = TestUtils.engine({ suppressPlayButton: false }); - engine.currentScene.add( - new ex.Actor({ - pos: new ex.Vector(250, 250), - width: 20, - height: 20, - color: ex.Color.Red - }) - ); - - const testClock = engine.clock as ex.TestClock; - const loader = new ex.Loader([new ex.ImageSource('src/spec/images/SpriteSpec/icon.png')]); - loader.suppressPlayButton = true; - - TestUtils.runToReady(engine, loader).then(() => { - // With suppress play there is another 500 ms delay in engine load() - testClock.step(1); - engine.graphicsContext.flush(); - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/EngineSpec/engine-suppress-play.png') - .then(() => { - done(); - }); - }); - }); -}); diff --git a/src/spec/ResourceSpec.ts b/src/spec/ResourceSpec.ts deleted file mode 100644 index 0cbcc3b7..00000000 --- a/src/spec/ResourceSpec.ts +++ /dev/null @@ -1,71 +0,0 @@ -import * as ex from '@excalibur'; -import { TestUtils } from './util/TestUtils'; -import { Mocks } from './util/Mocks'; - -describe('A generic Resource', () => { - let resource: ex.Resource; - const mocker = new Mocks.Mocker(); - - beforeEach(() => { - resource = new ex.Resource('a/path/to/a/resource.png', 'blob'); - - ex.Logger.getInstance().defaultLevel = ex.LogLevel.Error; - }); - - it('should not be loaded by default', () => { - expect(resource.isLoaded()).toBe(false); - }); - - it('should log failure when not found', (done) => { - const spy = jasmine.createSpy(); - spyOn(ex.Logger.getInstance(), 'error').and.callFake(spy); - - resource.events.on('error', jasmine.createSpy()); - resource.load().then( - () => fail(), - () => { - expect(spy).toHaveBeenCalled(); - done(); - } - ); - }); - - describe('without data', () => { - it('should not fail on load', async () => { - const emptyLoader = new ex.Loader(); - const game = TestUtils.engine(); - await game.start(); - expect(emptyLoader.isLoaded()).toBe(true); - game.dispose(); - }); - }); - - describe('with some data', () => { - beforeEach(() => { - resource.data = 'blob://data'; - }); - - it('should be loaded immediately', () => { - expect(resource.isLoaded()).toBe(true); - }); - - it('should return the processed data', () => { - expect(resource.data).toBe('blob://data'); - }); - - it('should not trigger an XHR when load is called', (done) => { - resource.load().then((data) => { - expect(data).not.toBeNull(); - done(); - }); - }); - - it('should load a text resource', (done) => { - const text = new ex.Resource('src/spec/images/ResourceSpec/textresource.txt', 'text', true); - text.load().then((data) => { - expect(data).not.toBeNull(); - done(); - }); - }); - }); -}); diff --git a/src/spec/ScaleSpec.ts b/src/spec/ScaleSpec.ts deleted file mode 100644 index b9651922..00000000 --- a/src/spec/ScaleSpec.ts +++ /dev/null @@ -1,57 +0,0 @@ -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; -import * as ex from '@excalibur'; -import { TestUtils } from './util/TestUtils'; -import { Mocks } from './util/Mocks'; - -describe('A scaled and rotated actor', () => { - let actor: ex.Actor; - let engine: ex.Engine; - const mock = new Mocks.Mocker(); - - beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - - actor = new ex.ScreenElement({ x: 50, y: 50, width: 100, height: 50 }); - actor.color = ex.Color.Blue; - actor.body.collisionType = ex.CollisionType.Active; - engine = TestUtils.engine({ width: 800, height: 600 }); - engine.screen.antialiasing = false; - - spyOn(engine.rootScene, 'draw').and.callThrough(); - }); - - afterEach(() => { - engine.stop(); - engine.dispose(); - }); - - it('is drawn correctly scaled at 90 degrees', (done) => { - const clock = engine.clock as ex.TestClock; - const bg = new ex.ImageSource('./src/spec/images/ScaleSpec/logo.png'); - const loader = new ex.Loader([bg]); - TestUtils.runToReady(engine, loader).then(() => { - const actor = new ex.Actor({ - x: engine.halfDrawWidth, - y: engine.halfDrawHeight, - width: 100, - height: 10, - color: ex.Color.Black - }); - actor.graphics.use(bg.toSprite()); - actor.scale.setTo(1, 0.2); - engine.add(actor); - - actor.rotation = Math.PI / 2; - - clock.step(1); - - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/ScaleSpec/scale.png') - .then(() => { - done(); - engine.dispose(); - }); - }); - }); -}); diff --git a/src/spec/SemaphoreSpec.ts b/src/spec/SemaphoreSpec.ts deleted file mode 100644 index 52218e06..00000000 --- a/src/spec/SemaphoreSpec.ts +++ /dev/null @@ -1,85 +0,0 @@ -import * as ex from '@excalibur'; -import { delay } from '../engine/Util/Util'; - -describe('A Semaphore', () => { - it('should exist', () => { - expect(ex.Semaphore).toBeDefined(); - }); - - it('can be constructed with a count', () => { - const semaphore = new ex.Semaphore(10); - expect(semaphore.count).toBe(10); - }); - - it('a trivial exit does not decrement semaphor', () => { - const semaphore = new ex.Semaphore(10); - for (let i = 0; i < 20; i++) { - semaphore.enter(); - } - expect(semaphore.waiting).toBe(10); - expect(semaphore.count).toBe(0); - semaphore.exit(0); - expect(semaphore.waiting).toBe(10); - expect(semaphore.count).toBe(0); - }); - - it('can limit async calls', () => { - const semaphore = new ex.Semaphore(10); - for (let i = 0; i < 20; i++) { - semaphore.enter(); - } - expect(semaphore.waiting).toBe(10); - semaphore.exit(); - semaphore.exit(); - semaphore.exit(); - expect(semaphore.waiting).toBe(7); - }); - - it('can block async calls', (done) => { - const mockFuture1 = new ex.Future(); - const mockMethod1 = () => { - return mockFuture1.promise; - }; - - const mockFuture2 = new ex.Future(); - const mockMethod2 = () => { - return mockFuture2.promise; - }; - const semaphore = new ex.Semaphore(1); - - const spy1 = jasmine.createSpy(); - const spy2 = jasmine.createSpy(); - - semaphore - .enter() - .then(() => { - expect(semaphore.count).toBe(0); - expect(semaphore.waiting).toBe(0); - mockMethod1().then(() => { - spy1(); - semaphore.exit(); - }); - const final = semaphore.enter().then(() => { - mockMethod2().then(() => { - spy2(); - semaphore.exit(); - }); - }); - expect(semaphore.count).toBe(0); - expect(semaphore.waiting).toBe(1); - return final; - }) - .finally(() => { - expect(spy1).toHaveBeenCalled(); - expect(spy2).toHaveBeenCalled(); - expect(spy1).toHaveBeenCalledBefore(spy2); - done(); - }); - - expect(spy1).not.toHaveBeenCalled(); - expect(spy2).not.toHaveBeenCalled(); - - mockFuture1.resolve(); - mockFuture2.resolve(); - }); -}); diff --git a/src/spec/SoundSpec.ts b/src/spec/SoundSpec.ts deleted file mode 100644 index 5741024c..00000000 --- a/src/spec/SoundSpec.ts +++ /dev/null @@ -1,498 +0,0 @@ -import * as ex from '@excalibur'; -import { canPlayFile } from '../engine/Util/Sound'; -import { delay } from '../engine/Util/Util'; -import { WebAudio } from '../engine/Util/WebAudio'; -import { TestUtils } from './util/TestUtils'; - -describe('Sound resource', () => { - let sut: ex.Sound; - - beforeAll(async () => { - ex.Logger.getInstance().clearAppenders(); - await WebAudio.unlock(); - }); - - beforeEach(() => { - sut = new ex.Sound('src/spec/images/SoundSpec/test.mp3'); - expect(sut.path).toBe('src/spec/images/SoundSpec/test.mp3'); - }); - - it('should be able to be constructed', () => { - expect(sut).toBeDefined(); - }); - - it('can detect playability of files', () => { - expect(canPlayFile('coin.mp3')).toBe(true); - }); - - it('can detect playability of files', () => { - expect(canPlayFile('coin.mp3?12234')).toBe(true); - }); - - it('can detect playability of files with multiple dots', () => { - expect(canPlayFile('coin.f74d9d70.mp3')).toBe(true); - }); - - it('can detect playability of files with querystrings', () => { - expect(canPlayFile('coin.f74d9d70.mp3?1678266496281')).toBe(true); - }); - - it('can detect playability of files with hash', () => { - expect(canPlayFile('coin.f74d9d70.mp3#1678266496281')).toBe(true); - }); - - it('can detect playability of files with querystring and hash', () => { - expect(canPlayFile('coin.f74d9d70.mp3?_=1234#1678266496281')).toBe(true); - }); - - it('should fire processed event', async () => { - const processedSpy = jasmine.createSpy('fake'); - sut.once('processed', processedSpy); - await sut.load(); - expect(processedSpy).toHaveBeenCalledTimes(1); - }); - - it('should have duration', async () => { - sut = new ex.Sound('src/spec/images/SoundSpec/preview.ogg'); - sut.duration = 5.0; - await sut.load(); - expect(sut.duration).toBeDefined(); - expect(sut.duration).toBe(5); - }); - - it('should fire playbackstart event', async () => { - const playbackSpy = jasmine.createSpy('playbackstart'); - - sut.on('playbackstart', playbackSpy); - - sut.loop = false; - await sut.load(); - await sut.play(); - expect(playbackSpy).toHaveBeenCalledTimes(1); - }); - - it('should fire playbackend event', async () => { - const playbackEndSpy = jasmine.createSpy(); - - sut.on('playbackend', playbackEndSpy); - - sut.loop = false; - await sut.load(); - await sut.play(); - expect(playbackEndSpy).toHaveBeenCalledTimes(1); - }); - - it('should fire resume event', async () => { - const resumeSpy = jasmine.createSpy('resume'); - await sut.load(); - - sut.once('resume', resumeSpy); - - sut.once('playbackstart', () => { - sut.pause(); - sut.play(); - }); - - sut.loop = false; - await sut.play(); - expect(resumeSpy).toHaveBeenCalledTimes(1); - }); - - it('should fire volumechange event', () => { - const volumenChangeSpy = jasmine.createSpy('volume'); - - sut.once('volumechange', volumenChangeSpy); - - sut.volume = 0.3; - expect(volumenChangeSpy).toHaveBeenCalledTimes(1); - }); - - it('should fire pause event', (done) => { - sut.load().then(() => { - const pauseSpy = jasmine.createSpy('pause'); - - sut.once('pause', pauseSpy); - - sut.once('playbackstart', () => { - sut.pause(); - expect(pauseSpy).toHaveBeenCalledTimes(1); - done(); - }); - sut.play(); - }); - }); - - it('should fire stop event', (done) => { - sut.load().then(() => { - const stopSpy = jasmine.createSpy('stop'); - - sut.once('stop', stopSpy); - - sut.once('playbackstart', () => { - sut.stop(); - - expect(stopSpy).toHaveBeenCalledTimes(1); - done(); - }); - - sut.play(); - }); - }); - - it('should create a new audio instance when played', (done) => { - sut.load().then(() => { - spyOn(sut, 'instanceCount').and.callThrough(); - - const initialInstancesCnt = sut.instanceCount(); - - sut.once('playbackstart', () => { - expect(sut.instanceCount()).toBeGreaterThan(initialInstancesCnt); - done(); - }); - - sut.loop = false; - sut.play(); - }); - }); - - it('should set tracks loop value same as own', (done) => { - sut.load().then(() => { - sut.loop = true; - - sut.once('playbackstart', () => { - expect(sut.instances[0].loop).toBe(sut.loop); - done(); - }); - - sut.play(); - }); - }); - - it('should not provide a duration if looping', async () => { - await sut.load(); - - const webaudio = new ex.WebAudioInstance(sut.data); - spyOn(webaudio as any, '_createNewBufferSource'); - const instance = jasmine.createSpyObj('AudioBufferSourceNode', ['start']); - (webaudio as any)._instance = instance; - webaudio.loop = true; - webaudio.play(); - - expect((webaudio as any)._createNewBufferSource).toHaveBeenCalled(); - expect(instance.start).toHaveBeenCalledWith(0, 0); - }); - - it('should provide a duration if not looping', async () => { - await sut.load(); - - const webaudio = new ex.WebAudioInstance(sut.data); - spyOn(webaudio as any, '_createNewBufferSource'); - const instance = jasmine.createSpyObj('AudioBufferSourceNode', ['start']); - (webaudio as any)._instance = instance; - webaudio.loop = false; - webaudio.play(); - - expect((webaudio as any)._createNewBufferSource).toHaveBeenCalled(); - expect(instance.start).toHaveBeenCalledWith(0, 0, sut.duration); - }); - - it('should set tracks volume value same as own', (done) => { - sut.load().then(() => { - sut.volume = 0.5; - - sut.once('playbackstart', () => { - expect(sut.instances[0].volume).toBe(sut.volume); - done(); - }); - - sut.play(); - }); - }); - - it('should set volume with argument sent to play', (done) => { - sut.load().then(() => { - sut.once('playbackstart', () => { - expect(sut.volume).toBe(0.5); - expect(sut.instances[0].volume).toBe(sut.volume); - done(); - }); - - sut.play(0.5); - }); - }); - - it('should play once and then finish if loop set to false', (done) => { - sut.load().then(() => { - sut.loop = false; - - sut.once('playbackstart', () => { - expect(sut.isPlaying()).toBe(true); - }); - - sut.play().then(() => { - expect(sut.isPlaying()).toBe(false); - - done(); - }); - }); - }); - - it('should stop all currently playing tracks', (done) => { - sut.load().then(() => { - sut.once('playbackstart', () => { - expect(sut.isPlaying()).toBe(true, 'track should be playing'); - - sut.stop(); - expect(sut.isPlaying()).toBe(false, 'track should be stopped'); - - done(); - }); - - sut.play(); - }); - }); - - it('should return the current playback position of the audio track', async () => { - sut = new ex.Sound('src/spec/images/SoundSpec/preview.ogg'); - await sut.load(); - sut.play(); - await delay(1000); - // appveyor is a little fast for some reason - expect(sut.getPlaybackPosition()).toBeGreaterThanOrEqual(0.98); - }); - - it('should variable playback rate of the audio track', async () => { - sut = new ex.Sound('src/spec/images/SoundSpec/preview.ogg'); - await sut.load(); - sut.playbackRate = 2.0; - sut.play(); - await delay(1000); - // appveyor is a little fast for some reason - expect(sut.getPlaybackPosition()).withContext('Twice the speed will be at 2 seconds').toBeGreaterThanOrEqual(1.8); - }); - - // FIXME: issue for flakey test https://github.com/excaliburjs/Excalibur/issues/1547 - xit('should stop all tracks even when paused', (done) => { - sut.play(); - - setTimeout(() => { - sut.once('stop', () => { - done(); - }); - - expect(sut.isPlaying()).toBe(true, 'should be playing'); - - // pause - sut.pause(); - - expect(sut.isPlaying()).toBe(false, 'should not be playing'); - - // stop and rewind - sut.stop(); - }, 500); - }); - - it('should not have any tracks when stopped', (done) => { - sut.load().then(() => { - sut.once('playbackstart', () => { - expect(sut.instanceCount()).toBe(1, 'should be one track'); - - sut.stop(); - - expect(sut.instanceCount()).toBe(0, 'should be no tracks'); - - done(); - }); - sut.play(); - }); - }); - - it('should not remove instance if paused', (done) => { - sut.load().then(() => { - sut.once('playbackstart', () => { - expect(sut.instanceCount()).toBe(1, 'should be one track'); - - sut.pause(); - - expect(sut.instanceCount()).toBe(1, 'should be one track'); - - done(); - }); - sut.play(); - }); - }); - - it('should remove tracks as they are done when multiple are playing', (done) => { - sut.load().then(() => { - sut.loop = false; - // start playing first track - sut.play().then(() => { - expect(sut.instanceCount()).withContext('should be on track').toBe(1); - }); - - // wait 250ms then play 2nd track - setTimeout(() => { - sut.on('playbackstart', () => { - expect(sut.instanceCount()).withContext('should be two simultaneous tracks').toBe(2); - }); - - sut.play().then(() => { - expect(sut.instanceCount()).withContext('should be no tracks').toBe(0); - done(); - }); - }, 250); - }); - }); - - it('should remove multiple tracks when stopped', (done) => { - sut.load().then(() => { - sut.loop = false; - // start playing first track - - sut.once('playbackstart', (ev: ex.NativeSoundEvent) => { - if (sut.getTrackId(ev.track) === 0) { - sut.play(); - } - sut.stop(); - - expect(sut.instanceCount()).toBe(0, 'should be no tracks'); - - done(); - }); - - sut.play(); - }); - }); - - it('can seek to a position in the sound', async () => { - sut = new ex.Sound('src/spec/images/SoundSpec/preview.ogg'); - await sut.load(); - expect(sut.getPlaybackPosition()).toBe(0); - sut.seek(6.5); - expect(sut.getPlaybackPosition()).toBe(6.5); - }); - - it('can get the total duration of the sound', async () => { - sut = new ex.Sound('src/spec/images/SoundSpec/preview.ogg'); - await sut.load(); - expect(sut.getTotalPlaybackDuration()).toBeCloseTo(13.01, 1); - }); - - it('can set/get the playback rate', async () => { - sut = new ex.Sound('src/spec/images/SoundSpec/preview.ogg'); - expect(sut.playbackRate).toBe(1.0); - sut.playbackRate = 2.5; - await sut.load(); - expect(sut.playbackRate).toBe(2.5); - }); - - it('can set the playback rate and seek to the right position', async () => { - sut = new ex.Sound('src/spec/images/SoundSpec/preview.ogg'); - expect(sut.playbackRate).toBe(1.0); - sut.playbackRate = 2.5; - await sut.load(); - sut.seek(6.5); - expect(sut.getPlaybackPosition()).toBe(6.5); - }); - - describe('wire engine', () => { - let engine: ex.Engine; - - beforeEach(() => { - engine = TestUtils.engine(); - engine.start(); - }); - - afterEach(() => { - engine.stop(); - engine.dispose(); - engine = null; - }); - - it('should stop all tracks when engine is stopped', (done) => { - sut.load().then(() => { - sut.wireEngine(engine); - - sut.once('playbackstart', () => { - expect(sut.instanceCount()).toBe(1, 'should be one track'); - - engine.stop(); - - expect(sut.instanceCount()).toBe(0, 'should be no tracks'); - expect(sut.isPlaying()).toBe(false, 'should not be playing'); - - done(); - }); - sut.play(); - }); - }); - - it('should not allow playing tracks when engine is stopped', (done) => { - sut.load().then(() => { - sut.wireEngine(engine); - sut.once('playbackstart', () => { - expect(sut.isPlaying()).toBe(true, 'should be playing'); - - engine.stop(); - - sut.play(); - - expect(sut.isPlaying()).toBe(false, 'should not allow playing'); - - done(); - }); - sut.play(); - }); - }); - - it('should pause tracks when game is hidden and pauseAudioWhenHidden is true', (done) => { - sut.load().then(() => { - engine.pauseAudioWhenHidden = true; - sut.wireEngine(engine); - - sut.once('playbackstart', () => { - expect(sut.isPlaying()).withContext('should be playing').toBe(true); - - setTimeout(() => { - engine.emit('hidden', new ex.HiddenEvent(engine)); - }, 100); - }); - - sut.play(); - - engine.once('hidden', () => { - expect(sut.isPlaying()).withContext('should pause when hidden').toBe(false); - done(); - }); - }); - }); - - it('should resume tracks when game is visible from hidden and pauseAudioWhenHidden is true', (done) => { - sut.load().then(() => { - engine.pauseAudioWhenHidden = true; - sut.wireEngine(engine); - - sut.once('playbackstart', () => { - expect(sut.isPlaying()).toBe(true, 'should be playing'); - - setTimeout(() => { - engine.emit('hidden', new ex.HiddenEvent(engine)); - }, 100); - }); - - sut.play(); - - engine.once('hidden', () => { - setTimeout(() => { - engine.emit('visible', new ex.VisibleEvent(engine)); - }, 100); - }); - - engine.once('visible', () => { - expect(sut.isPlaying()).toBe(true, 'should resume when visible'); - done(); - }); - }); - }); - }); -}); diff --git a/src/spec/fonts/Gorgeous Pixel.ttf b/src/spec/assets/fonts/Gorgeous Pixel.ttf similarity index 100% rename from src/spec/fonts/Gorgeous Pixel.ttf rename to src/spec/assets/fonts/Gorgeous Pixel.ttf diff --git a/src/spec/images/ActorSpec/zindex-blue-top.png b/src/spec/assets/images/ActorSpec/zindex-blue-top.png similarity index 100% rename from src/spec/images/ActorSpec/zindex-blue-top.png rename to src/spec/assets/images/ActorSpec/zindex-blue-top.png diff --git a/src/spec/images/ActorSpec/zindex-green-top.png b/src/spec/assets/images/ActorSpec/zindex-green-top.png similarity index 100% rename from src/spec/images/ActorSpec/zindex-green-top.png rename to src/spec/assets/images/ActorSpec/zindex-green-top.png diff --git a/src/spec/images/CameraSpec/zoomin.png b/src/spec/assets/images/CameraSpec/zoomin.png similarity index 100% rename from src/spec/images/CameraSpec/zoomin.png rename to src/spec/assets/images/CameraSpec/zoomin.png diff --git a/src/spec/images/CameraSpec/zoomout.png b/src/spec/assets/images/CameraSpec/zoomout.png similarity index 100% rename from src/spec/images/CameraSpec/zoomout.png rename to src/spec/assets/images/CameraSpec/zoomout.png diff --git a/src/spec/images/CollisionShapeSpec/circle-debug.png b/src/spec/assets/images/CollisionShapeSpec/circle-debug.png similarity index 100% rename from src/spec/images/CollisionShapeSpec/circle-debug.png rename to src/spec/assets/images/CollisionShapeSpec/circle-debug.png diff --git a/src/spec/images/CollisionShapeSpec/circle.old.png b/src/spec/assets/images/CollisionShapeSpec/circle.old.png similarity index 100% rename from src/spec/images/CollisionShapeSpec/circle.old.png rename to src/spec/assets/images/CollisionShapeSpec/circle.old.png diff --git a/src/spec/images/CollisionShapeSpec/circle.png b/src/spec/assets/images/CollisionShapeSpec/circle.png similarity index 100% rename from src/spec/images/CollisionShapeSpec/circle.png rename to src/spec/assets/images/CollisionShapeSpec/circle.png diff --git a/src/spec/images/CollisionShapeSpec/edge.png b/src/spec/assets/images/CollisionShapeSpec/edge.png similarity index 100% rename from src/spec/images/CollisionShapeSpec/edge.png rename to src/spec/assets/images/CollisionShapeSpec/edge.png diff --git a/src/spec/images/CollisionShapeSpec/triangle.png b/src/spec/assets/images/CollisionShapeSpec/triangle.png similarity index 100% rename from src/spec/images/CollisionShapeSpec/triangle.png rename to src/spec/assets/images/CollisionShapeSpec/triangle.png diff --git a/src/spec/images/ColorBlindCorrectorSpec/actor.png b/src/spec/assets/images/ColorBlindCorrectorSpec/actor.png similarity index 100% rename from src/spec/images/ColorBlindCorrectorSpec/actor.png rename to src/spec/assets/images/ColorBlindCorrectorSpec/actor.png diff --git a/src/spec/images/ColorBlindCorrectorSpec/deuteranope_correct.png b/src/spec/assets/images/ColorBlindCorrectorSpec/deuteranope_correct.png similarity index 100% rename from src/spec/images/ColorBlindCorrectorSpec/deuteranope_correct.png rename to src/spec/assets/images/ColorBlindCorrectorSpec/deuteranope_correct.png diff --git a/src/spec/images/ColorBlindCorrectorSpec/deuteranope_simulate.png b/src/spec/assets/images/ColorBlindCorrectorSpec/deuteranope_simulate.png similarity index 100% rename from src/spec/images/ColorBlindCorrectorSpec/deuteranope_simulate.png rename to src/spec/assets/images/ColorBlindCorrectorSpec/deuteranope_simulate.png diff --git a/src/spec/images/ColorBlindCorrectorSpec/normal.png b/src/spec/assets/images/ColorBlindCorrectorSpec/normal.png similarity index 100% rename from src/spec/images/ColorBlindCorrectorSpec/normal.png rename to src/spec/assets/images/ColorBlindCorrectorSpec/normal.png diff --git a/src/spec/images/ColorBlindCorrectorSpec/protanope_correct.png b/src/spec/assets/images/ColorBlindCorrectorSpec/protanope_correct.png similarity index 100% rename from src/spec/images/ColorBlindCorrectorSpec/protanope_correct.png rename to src/spec/assets/images/ColorBlindCorrectorSpec/protanope_correct.png diff --git a/src/spec/images/ColorBlindCorrectorSpec/protanope_simulate.png b/src/spec/assets/images/ColorBlindCorrectorSpec/protanope_simulate.png similarity index 100% rename from src/spec/images/ColorBlindCorrectorSpec/protanope_simulate.png rename to src/spec/assets/images/ColorBlindCorrectorSpec/protanope_simulate.png diff --git a/src/spec/images/ColorBlindCorrectorSpec/tritanope_correct.png b/src/spec/assets/images/ColorBlindCorrectorSpec/tritanope_correct.png similarity index 100% rename from src/spec/images/ColorBlindCorrectorSpec/tritanope_correct.png rename to src/spec/assets/images/ColorBlindCorrectorSpec/tritanope_correct.png diff --git a/src/spec/images/ColorBlindCorrectorSpec/tritanope_simulate.png b/src/spec/assets/images/ColorBlindCorrectorSpec/tritanope_simulate.png similarity index 100% rename from src/spec/images/ColorBlindCorrectorSpec/tritanope_simulate.png rename to src/spec/assets/images/ColorBlindCorrectorSpec/tritanope_simulate.png diff --git a/src/spec/images/CompositeColliderSpec/composite.png b/src/spec/assets/images/CompositeColliderSpec/composite.png similarity index 100% rename from src/spec/images/CompositeColliderSpec/composite.png rename to src/spec/assets/images/CompositeColliderSpec/composite.png diff --git a/src/spec/images/CrossFadeSpec/crossfade.png b/src/spec/assets/images/CrossFadeSpec/crossfade.png similarity index 100% rename from src/spec/images/CrossFadeSpec/crossfade.png rename to src/spec/assets/images/CrossFadeSpec/crossfade.png diff --git a/src/spec/images/DebugSpec/bounds.png b/src/spec/assets/images/DebugSpec/bounds.png similarity index 100% rename from src/spec/images/DebugSpec/bounds.png rename to src/spec/assets/images/DebugSpec/bounds.png diff --git a/src/spec/images/DebugSpec/circle.png b/src/spec/assets/images/DebugSpec/circle.png similarity index 100% rename from src/spec/images/DebugSpec/circle.png rename to src/spec/assets/images/DebugSpec/circle.png diff --git a/src/spec/images/DebugSpec/line.png b/src/spec/assets/images/DebugSpec/line.png similarity index 100% rename from src/spec/images/DebugSpec/line.png rename to src/spec/assets/images/DebugSpec/line.png diff --git a/src/spec/assets/images/DebugSpec/lines.png b/src/spec/assets/images/DebugSpec/lines.png new file mode 100644 index 0000000000000000000000000000000000000000..ffdef08f434263e58b9b38979b2b2a3e8b6b5217 GIT binary patch literal 220 zcmeAS@N?(olHy`uVBq!ia0y~yU;weXIM^5%7j8X;9 z6!XOzE@i?VikoIX6sS$TWri~5vy<#yFG%?gHY0S(I5GPV~IyBPN# XOH4cYxG8~wfq}u()z4*}Q$iB};&M-u literal 0 HcmV?d00001 diff --git a/src/spec/images/DebugSpec/point.png b/src/spec/assets/images/DebugSpec/point.png similarity index 100% rename from src/spec/images/DebugSpec/point.png rename to src/spec/assets/images/DebugSpec/point.png diff --git a/src/spec/images/DebugSpec/polygon.png b/src/spec/assets/images/DebugSpec/polygon.png similarity index 100% rename from src/spec/images/DebugSpec/polygon.png rename to src/spec/assets/images/DebugSpec/polygon.png diff --git a/src/spec/images/DebugSpec/ray.png b/src/spec/assets/images/DebugSpec/ray.png similarity index 100% rename from src/spec/images/DebugSpec/ray.png rename to src/spec/assets/images/DebugSpec/ray.png diff --git a/src/spec/images/DebugSpec/text.png b/src/spec/assets/images/DebugSpec/text.png similarity index 100% rename from src/spec/images/DebugSpec/text.png rename to src/spec/assets/images/DebugSpec/text.png diff --git a/src/spec/images/DebugSystemSpec/body.png b/src/spec/assets/images/DebugSystemSpec/body.png similarity index 100% rename from src/spec/images/DebugSystemSpec/body.png rename to src/spec/assets/images/DebugSystemSpec/body.png diff --git a/src/spec/images/DebugSystemSpec/collider.png b/src/spec/assets/images/DebugSystemSpec/collider.png similarity index 100% rename from src/spec/images/DebugSystemSpec/collider.png rename to src/spec/assets/images/DebugSystemSpec/collider.png diff --git a/src/spec/images/DebugSystemSpec/composite-collider.png b/src/spec/assets/images/DebugSystemSpec/composite-collider.png similarity index 100% rename from src/spec/images/DebugSystemSpec/composite-collider.png rename to src/spec/assets/images/DebugSystemSpec/composite-collider.png diff --git a/src/spec/images/DebugSystemSpec/debug-draw-component.png b/src/spec/assets/images/DebugSystemSpec/debug-draw-component.png similarity index 100% rename from src/spec/images/DebugSystemSpec/debug-draw-component.png rename to src/spec/assets/images/DebugSystemSpec/debug-draw-component.png diff --git a/src/spec/images/DebugSystemSpec/graphics.png b/src/spec/assets/images/DebugSystemSpec/graphics.png similarity index 100% rename from src/spec/images/DebugSystemSpec/graphics.png rename to src/spec/assets/images/DebugSystemSpec/graphics.png diff --git a/src/spec/images/DebugSystemSpec/motion.png b/src/spec/assets/images/DebugSystemSpec/motion.png similarity index 100% rename from src/spec/images/DebugSystemSpec/motion.png rename to src/spec/assets/images/DebugSystemSpec/motion.png diff --git a/src/spec/images/DebugSystemSpec/tilemap-debug.png b/src/spec/assets/images/DebugSystemSpec/tilemap-debug.png similarity index 100% rename from src/spec/images/DebugSystemSpec/tilemap-debug.png rename to src/spec/assets/images/DebugSystemSpec/tilemap-debug.png diff --git a/src/spec/images/DebugSystemSpec/transform.png b/src/spec/assets/images/DebugSystemSpec/transform.png similarity index 100% rename from src/spec/images/DebugSystemSpec/transform.png rename to src/spec/assets/images/DebugSystemSpec/transform.png diff --git a/src/spec/images/DebugTextSpec/draw-canvas2d.png b/src/spec/assets/images/DebugTextSpec/draw-canvas2d.png similarity index 100% rename from src/spec/images/DebugTextSpec/draw-canvas2d.png rename to src/spec/assets/images/DebugTextSpec/draw-canvas2d.png diff --git a/src/spec/images/DebugTextSpec/draw-webgl.png b/src/spec/assets/images/DebugTextSpec/draw-webgl.png similarity index 100% rename from src/spec/images/DebugTextSpec/draw-webgl.png rename to src/spec/assets/images/DebugTextSpec/draw-webgl.png diff --git a/src/spec/images/DebugTextSpec/draw.png b/src/spec/assets/images/DebugTextSpec/draw.png similarity index 100% rename from src/spec/images/DebugTextSpec/draw.png rename to src/spec/assets/images/DebugTextSpec/draw.png diff --git a/src/spec/images/DefaultLoaderSpec/loading.png b/src/spec/assets/images/DefaultLoaderSpec/loading.png similarity index 100% rename from src/spec/images/DefaultLoaderSpec/loading.png rename to src/spec/assets/images/DefaultLoaderSpec/loading.png diff --git a/src/spec/images/DirectorSpec/fadein.png b/src/spec/assets/images/DirectorSpec/fadein.png similarity index 100% rename from src/spec/images/DirectorSpec/fadein.png rename to src/spec/assets/images/DirectorSpec/fadein.png diff --git a/src/spec/images/EngineSpec/engine-load-complete.png b/src/spec/assets/images/EngineSpec/engine-load-complete.png similarity index 100% rename from src/spec/images/EngineSpec/engine-load-complete.png rename to src/spec/assets/images/EngineSpec/engine-load-complete.png diff --git a/src/spec/images/EngineSpec/engine-suppress-play.png b/src/spec/assets/images/EngineSpec/engine-suppress-play.png similarity index 100% rename from src/spec/images/EngineSpec/engine-suppress-play.png rename to src/spec/assets/images/EngineSpec/engine-suppress-play.png diff --git a/src/spec/images/EngineSpec/hero.png b/src/spec/assets/images/EngineSpec/hero.png similarity index 100% rename from src/spec/images/EngineSpec/hero.png rename to src/spec/assets/images/EngineSpec/hero.png diff --git a/src/spec/images/EngineSpec/index.png b/src/spec/assets/images/EngineSpec/index.png similarity index 100% rename from src/spec/images/EngineSpec/index.png rename to src/spec/assets/images/EngineSpec/index.png diff --git a/src/spec/images/EngineSpec/pixelart.png b/src/spec/assets/images/EngineSpec/pixelart.png similarity index 100% rename from src/spec/images/EngineSpec/pixelart.png rename to src/spec/assets/images/EngineSpec/pixelart.png diff --git a/src/spec/images/EngineSpec/screenshot.png b/src/spec/assets/images/EngineSpec/screenshot.png similarity index 100% rename from src/spec/images/EngineSpec/screenshot.png rename to src/spec/assets/images/EngineSpec/screenshot.png diff --git a/src/spec/images/EngineSpec/snaptopixel.png b/src/spec/assets/images/EngineSpec/snaptopixel.png similarity index 100% rename from src/spec/images/EngineSpec/snaptopixel.png rename to src/spec/assets/images/EngineSpec/snaptopixel.png diff --git a/src/spec/images/EngineSpec/sprite.png b/src/spec/assets/images/EngineSpec/sprite.png similarity index 100% rename from src/spec/images/EngineSpec/sprite.png rename to src/spec/assets/images/EngineSpec/sprite.png diff --git a/src/spec/images/EngineSpec/tileset.png b/src/spec/assets/images/EngineSpec/tileset.png similarity index 100% rename from src/spec/images/EngineSpec/tileset.png rename to src/spec/assets/images/EngineSpec/tileset.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/2d-circle.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-circle.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/2d-circle.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-circle.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/2d-drawgraphic.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-drawgraphic.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/2d-drawgraphic.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-drawgraphic.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/2d-drawline.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-drawline.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/2d-drawline.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-drawline.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/2d-drawpoint.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-drawpoint.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/2d-drawpoint.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-drawpoint.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/2d-line.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-line.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/2d-line.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-line.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/2d-snap-to-pixel.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-snap-to-pixel.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/2d-snap-to-pixel.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-snap-to-pixel.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/2d-transform.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-transform.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/2d-transform.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-transform.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-circle-next.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-circle-next.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-circle-next.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-circle-next.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-line-next.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-line-next.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-line-next.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-line-next.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-next.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-next.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-next.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-next.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-point-next.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-point-next.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-point-next.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-point-next.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/rasters.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/rasters.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/rasters.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/rasters.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/sword.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/sword.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/sword.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/sword.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/test.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/test.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/test.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/test.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/webgl-circle-with-opacity.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-circle-with-opacity.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/webgl-circle-with-opacity.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-circle-with-opacity.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/webgl-circle.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-circle.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/webgl-circle.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-circle.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/webgl-drawline.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-drawline.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/webgl-drawline.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-drawline.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/webgl-drawpoint.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-drawpoint.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/webgl-drawpoint.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-drawpoint.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/webgl-line.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-line.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/webgl-line.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-line.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/webgl-rect.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-rect.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/webgl-rect.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-rect.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/webgl-solid-rect.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-solid-rect.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/webgl-solid-rect.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-solid-rect.png diff --git a/src/spec/images/ExcaliburGraphicsContextSpec/webgl-transform.png b/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-transform.png similarity index 100% rename from src/spec/images/ExcaliburGraphicsContextSpec/webgl-transform.png rename to src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-transform.png diff --git a/src/spec/images/FadeInOutSpec/fadein.png b/src/spec/assets/images/FadeInOutSpec/fadein.png similarity index 100% rename from src/spec/images/FadeInOutSpec/fadein.png rename to src/spec/assets/images/FadeInOutSpec/fadein.png diff --git a/src/spec/images/FadeInOutSpec/fadeout.png b/src/spec/assets/images/FadeInOutSpec/fadeout.png similarity index 100% rename from src/spec/images/FadeInOutSpec/fadeout.png rename to src/spec/assets/images/FadeInOutSpec/fadeout.png diff --git a/src/spec/images/GifSpec/frame1.png b/src/spec/assets/images/GifSpec/frame1.png similarity index 100% rename from src/spec/images/GifSpec/frame1.png rename to src/spec/assets/images/GifSpec/frame1.png diff --git a/src/spec/images/GifSpec/frame2.png b/src/spec/assets/images/GifSpec/frame2.png similarity index 100% rename from src/spec/images/GifSpec/frame2.png rename to src/spec/assets/images/GifSpec/frame2.png diff --git a/src/spec/images/GifSpec/loading-frame-20.png b/src/spec/assets/images/GifSpec/loading-frame-20.png similarity index 100% rename from src/spec/images/GifSpec/loading-frame-20.png rename to src/spec/assets/images/GifSpec/loading-frame-20.png diff --git a/src/spec/images/GifSpec/loading-screen.gif b/src/spec/assets/images/GifSpec/loading-screen.gif similarity index 100% rename from src/spec/images/GifSpec/loading-screen.gif rename to src/spec/assets/images/GifSpec/loading-screen.gif diff --git a/src/spec/images/GifSpec/stoplight-frame-1.png b/src/spec/assets/images/GifSpec/stoplight-frame-1.png similarity index 100% rename from src/spec/images/GifSpec/stoplight-frame-1.png rename to src/spec/assets/images/GifSpec/stoplight-frame-1.png diff --git a/src/spec/images/GifSpec/stoplight-frame-2.png b/src/spec/assets/images/GifSpec/stoplight-frame-2.png similarity index 100% rename from src/spec/images/GifSpec/stoplight-frame-2.png rename to src/spec/assets/images/GifSpec/stoplight-frame-2.png diff --git a/src/spec/images/GifSpec/stoplight-frame-3.png b/src/spec/assets/images/GifSpec/stoplight-frame-3.png similarity index 100% rename from src/spec/images/GifSpec/stoplight-frame-3.png rename to src/spec/assets/images/GifSpec/stoplight-frame-3.png diff --git a/src/spec/images/GifSpec/stoplight.gif b/src/spec/assets/images/GifSpec/stoplight.gif similarity index 100% rename from src/spec/images/GifSpec/stoplight.gif rename to src/spec/assets/images/GifSpec/stoplight.gif diff --git a/src/spec/images/GifSpec/sword.gif b/src/spec/assets/images/GifSpec/sword.gif similarity index 100% rename from src/spec/images/GifSpec/sword.gif rename to src/spec/assets/images/GifSpec/sword.gif diff --git a/src/spec/images/GpuParticlesSpec/clear.png b/src/spec/assets/images/GpuParticlesSpec/clear.png similarity index 100% rename from src/spec/images/GpuParticlesSpec/clear.png rename to src/spec/assets/images/GpuParticlesSpec/clear.png diff --git a/src/spec/images/GpuParticlesSpec/particles-wrapped.png b/src/spec/assets/images/GpuParticlesSpec/particles-wrapped.png similarity index 100% rename from src/spec/images/GpuParticlesSpec/particles-wrapped.png rename to src/spec/assets/images/GpuParticlesSpec/particles-wrapped.png diff --git a/src/spec/images/GpuParticlesSpec/particles.png b/src/spec/assets/images/GpuParticlesSpec/particles.png similarity index 100% rename from src/spec/images/GpuParticlesSpec/particles.png rename to src/spec/assets/images/GpuParticlesSpec/particles.png diff --git a/src/spec/images/GraphicSpec/base.png b/src/spec/assets/images/GraphicSpec/base.png similarity index 100% rename from src/spec/images/GraphicSpec/base.png rename to src/spec/assets/images/GraphicSpec/base.png diff --git a/src/spec/images/GraphicSpec/debug.png b/src/spec/assets/images/GraphicSpec/debug.png similarity index 100% rename from src/spec/images/GraphicSpec/debug.png rename to src/spec/assets/images/GraphicSpec/debug.png diff --git a/src/spec/images/GraphicSpec/flipped.png b/src/spec/assets/images/GraphicSpec/flipped.png similarity index 100% rename from src/spec/images/GraphicSpec/flipped.png rename to src/spec/assets/images/GraphicSpec/flipped.png diff --git a/src/spec/images/GraphicSpec/opacity.png b/src/spec/assets/images/GraphicSpec/opacity.png similarity index 100% rename from src/spec/images/GraphicSpec/opacity.png rename to src/spec/assets/images/GraphicSpec/opacity.png diff --git a/src/spec/images/GraphicSpec/rotated.png b/src/spec/assets/images/GraphicSpec/rotated.png similarity index 100% rename from src/spec/images/GraphicSpec/rotated.png rename to src/spec/assets/images/GraphicSpec/rotated.png diff --git a/src/spec/images/GraphicSpec/scaled.png b/src/spec/assets/images/GraphicSpec/scaled.png similarity index 100% rename from src/spec/images/GraphicSpec/scaled.png rename to src/spec/assets/images/GraphicSpec/scaled.png diff --git a/src/spec/images/GraphicsAnimationSpec/frame-1.png b/src/spec/assets/images/GraphicsAnimationSpec/frame-1.png similarity index 100% rename from src/spec/images/GraphicsAnimationSpec/frame-1.png rename to src/spec/assets/images/GraphicsAnimationSpec/frame-1.png diff --git a/src/spec/images/GraphicsAnimationSpec/frame-2.png b/src/spec/assets/images/GraphicsAnimationSpec/frame-2.png similarity index 100% rename from src/spec/images/GraphicsAnimationSpec/frame-2.png rename to src/spec/assets/images/GraphicsAnimationSpec/frame-2.png diff --git a/src/spec/images/GraphicsAnimationSpec/frame-3.png b/src/spec/assets/images/GraphicsAnimationSpec/frame-3.png similarity index 100% rename from src/spec/images/GraphicsAnimationSpec/frame-3.png rename to src/spec/assets/images/GraphicsAnimationSpec/frame-3.png diff --git a/src/spec/images/GraphicsCanvasSpec/centered.png b/src/spec/assets/images/GraphicsCanvasSpec/centered.png similarity index 100% rename from src/spec/images/GraphicsCanvasSpec/centered.png rename to src/spec/assets/images/GraphicsCanvasSpec/centered.png diff --git a/src/spec/images/GraphicsCanvasSpec/draw.png b/src/spec/assets/images/GraphicsCanvasSpec/draw.png similarity index 100% rename from src/spec/images/GraphicsCanvasSpec/draw.png rename to src/spec/assets/images/GraphicsCanvasSpec/draw.png diff --git a/src/spec/images/GraphicsCircleSpec/circle.png b/src/spec/assets/images/GraphicsCircleSpec/circle.png similarity index 100% rename from src/spec/images/GraphicsCircleSpec/circle.png rename to src/spec/assets/images/GraphicsCircleSpec/circle.png diff --git a/src/spec/images/GraphicsCircleSpec/line-width.png b/src/spec/assets/images/GraphicsCircleSpec/line-width.png similarity index 100% rename from src/spec/images/GraphicsCircleSpec/line-width.png rename to src/spec/assets/images/GraphicsCircleSpec/line-width.png diff --git a/src/spec/images/GraphicsGroupSpec/graphics-group-without-anchor.png b/src/spec/assets/images/GraphicsGroupSpec/graphics-group-without-anchor.png similarity index 100% rename from src/spec/images/GraphicsGroupSpec/graphics-group-without-anchor.png rename to src/spec/assets/images/GraphicsGroupSpec/graphics-group-without-anchor.png diff --git a/src/spec/images/GraphicsGroupSpec/graphics-group.png b/src/spec/assets/images/GraphicsGroupSpec/graphics-group.png similarity index 100% rename from src/spec/images/GraphicsGroupSpec/graphics-group.png rename to src/spec/assets/images/GraphicsGroupSpec/graphics-group.png diff --git a/src/spec/images/GraphicsImageSourceSpec/arrows.svg b/src/spec/assets/images/GraphicsImageSourceSpec/arrows.svg similarity index 100% rename from src/spec/images/GraphicsImageSourceSpec/arrows.svg rename to src/spec/assets/images/GraphicsImageSourceSpec/arrows.svg diff --git a/src/spec/images/GraphicsImageSourceSpec/big-image.png b/src/spec/assets/images/GraphicsImageSourceSpec/big-image.png similarity index 100% rename from src/spec/images/GraphicsImageSourceSpec/big-image.png rename to src/spec/assets/images/GraphicsImageSourceSpec/big-image.png diff --git a/src/spec/images/GraphicsImageSourceSpec/canvas-image.png b/src/spec/assets/images/GraphicsImageSourceSpec/canvas-image.png similarity index 100% rename from src/spec/images/GraphicsImageSourceSpec/canvas-image.png rename to src/spec/assets/images/GraphicsImageSourceSpec/canvas-image.png diff --git a/src/spec/images/GraphicsNineSliceSpec/InputTile.png b/src/spec/assets/images/GraphicsNineSliceSpec/InputTile.png similarity index 100% rename from src/spec/images/GraphicsNineSliceSpec/InputTile.png rename to src/spec/assets/images/GraphicsNineSliceSpec/InputTile.png diff --git a/src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_stretch_h_stretch.aseprite b/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_stretch_h_stretch.aseprite similarity index 100% rename from src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_stretch_h_stretch.aseprite rename to src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_stretch_h_stretch.aseprite diff --git a/src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_stretch_h_stretch.png b/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_stretch_h_stretch.png similarity index 100% rename from src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_stretch_h_stretch.png rename to src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_stretch_h_stretch.png diff --git a/src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_tile_h_tile.aseprite b/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_tile_h_tile.aseprite similarity index 100% rename from src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_tile_h_tile.aseprite rename to src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_tile_h_tile.aseprite diff --git a/src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_tile_h_tile.png b/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_tile_h_tile.png similarity index 100% rename from src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_tile_h_tile.png rename to src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_tile_h_tile.png diff --git a/src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_tilefit_h_tilefit.aseprite b/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_tilefit_h_tilefit.aseprite similarity index 100% rename from src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_tilefit_h_tilefit.aseprite rename to src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_tilefit_h_tilefit.aseprite diff --git a/src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_tilefit_h_tilefit.png b/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_tilefit_h_tilefit.png similarity index 100% rename from src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_tilefit_h_tilefit.png rename to src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_tilefit_h_tilefit.png diff --git a/src/spec/images/GraphicsNineSliceSpec/resultImage_64_64_noCenter.png b/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_64_64_noCenter.png similarity index 100% rename from src/spec/images/GraphicsNineSliceSpec/resultImage_64_64_noCenter.png rename to src/spec/assets/images/GraphicsNineSliceSpec/resultImage_64_64_noCenter.png diff --git a/src/spec/images/GraphicsPolygonSpec/poly.png b/src/spec/assets/images/GraphicsPolygonSpec/poly.png similarity index 100% rename from src/spec/images/GraphicsPolygonSpec/poly.png rename to src/spec/assets/images/GraphicsPolygonSpec/poly.png diff --git a/src/spec/images/GraphicsRasterSpec/raster-quality.png b/src/spec/assets/images/GraphicsRasterSpec/raster-quality.png similarity index 100% rename from src/spec/images/GraphicsRasterSpec/raster-quality.png rename to src/spec/assets/images/GraphicsRasterSpec/raster-quality.png diff --git a/src/spec/images/GraphicsRasterSpec/raster.png b/src/spec/assets/images/GraphicsRasterSpec/raster.png similarity index 100% rename from src/spec/images/GraphicsRasterSpec/raster.png rename to src/spec/assets/images/GraphicsRasterSpec/raster.png diff --git a/src/spec/images/GraphicsRectSpec/clone-rect.png b/src/spec/assets/images/GraphicsRectSpec/clone-rect.png similarity index 100% rename from src/spec/images/GraphicsRectSpec/clone-rect.png rename to src/spec/assets/images/GraphicsRectSpec/clone-rect.png diff --git a/src/spec/images/GraphicsRectSpec/rect.png b/src/spec/assets/images/GraphicsRectSpec/rect.png similarity index 100% rename from src/spec/images/GraphicsRectSpec/rect.png rename to src/spec/assets/images/GraphicsRectSpec/rect.png diff --git a/src/spec/images/GraphicsSpriteSpec/change-size-and-scale.png b/src/spec/assets/images/GraphicsSpriteSpec/change-size-and-scale.png similarity index 100% rename from src/spec/images/GraphicsSpriteSpec/change-size-and-scale.png rename to src/spec/assets/images/GraphicsSpriteSpec/change-size-and-scale.png diff --git a/src/spec/images/GraphicsSpriteSpec/change-size.png b/src/spec/assets/images/GraphicsSpriteSpec/change-size.png similarity index 100% rename from src/spec/images/GraphicsSpriteSpec/change-size.png rename to src/spec/assets/images/GraphicsSpriteSpec/change-size.png diff --git a/src/spec/images/GraphicsSpriteSpec/dest-size.png b/src/spec/assets/images/GraphicsSpriteSpec/dest-size.png similarity index 100% rename from src/spec/images/GraphicsSpriteSpec/dest-size.png rename to src/spec/assets/images/GraphicsSpriteSpec/dest-size.png diff --git a/src/spec/images/GraphicsSpriteSpec/dest-view.png b/src/spec/assets/images/GraphicsSpriteSpec/dest-view.png similarity index 100% rename from src/spec/images/GraphicsSpriteSpec/dest-view.png rename to src/spec/assets/images/GraphicsSpriteSpec/dest-view.png diff --git a/src/spec/images/GraphicsSpriteSpec/icon-tint.png b/src/spec/assets/images/GraphicsSpriteSpec/icon-tint.png similarity index 100% rename from src/spec/images/GraphicsSpriteSpec/icon-tint.png rename to src/spec/assets/images/GraphicsSpriteSpec/icon-tint.png diff --git a/src/spec/icon.png b/src/spec/assets/images/GraphicsSpriteSpec/icon.png similarity index 100% rename from src/spec/icon.png rename to src/spec/assets/images/GraphicsSpriteSpec/icon.png diff --git a/src/spec/images/GraphicsSpriteSpec/source-view.png b/src/spec/assets/images/GraphicsSpriteSpec/source-view.png similarity index 100% rename from src/spec/images/GraphicsSpriteSpec/source-view.png rename to src/spec/assets/images/GraphicsSpriteSpec/source-view.png diff --git a/src/spec/images/GraphicsSystemSpec/graphics-context-opacity.png b/src/spec/assets/images/GraphicsSystemSpec/graphics-context-opacity.png similarity index 100% rename from src/spec/images/GraphicsSystemSpec/graphics-context-opacity.png rename to src/spec/assets/images/GraphicsSystemSpec/graphics-context-opacity.png diff --git a/src/spec/images/GraphicsSystemSpec/graphics-system.png b/src/spec/assets/images/GraphicsSystemSpec/graphics-system.png similarity index 100% rename from src/spec/images/GraphicsSystemSpec/graphics-system.png rename to src/spec/assets/images/GraphicsSystemSpec/graphics-system.png diff --git a/src/spec/images/GraphicsSystemSpec/sword-flip-both-offset.png b/src/spec/assets/images/GraphicsSystemSpec/sword-flip-both-offset.png similarity index 100% rename from src/spec/images/GraphicsSystemSpec/sword-flip-both-offset.png rename to src/spec/assets/images/GraphicsSystemSpec/sword-flip-both-offset.png diff --git a/src/spec/images/GraphicsSystemSpec/sword-flip-both.png b/src/spec/assets/images/GraphicsSystemSpec/sword-flip-both.png similarity index 100% rename from src/spec/images/GraphicsSystemSpec/sword-flip-both.png rename to src/spec/assets/images/GraphicsSystemSpec/sword-flip-both.png diff --git a/src/spec/images/GraphicsSystemSpec/sword-flip-horizontal.png b/src/spec/assets/images/GraphicsSystemSpec/sword-flip-horizontal.png similarity index 100% rename from src/spec/images/GraphicsSystemSpec/sword-flip-horizontal.png rename to src/spec/assets/images/GraphicsSystemSpec/sword-flip-horizontal.png diff --git a/src/spec/images/GraphicsSystemSpec/sword-flip-vertical.png b/src/spec/assets/images/GraphicsSystemSpec/sword-flip-vertical.png similarity index 100% rename from src/spec/images/GraphicsSystemSpec/sword-flip-vertical.png rename to src/spec/assets/images/GraphicsSystemSpec/sword-flip-vertical.png diff --git a/src/spec/images/GraphicsSystemSpec/sword.png b/src/spec/assets/images/GraphicsSystemSpec/sword.png similarity index 100% rename from src/spec/images/GraphicsSystemSpec/sword.png rename to src/spec/assets/images/GraphicsSystemSpec/sword.png diff --git a/src/spec/assets/images/GraphicsTextSpec/bold-linux.png b/src/spec/assets/images/GraphicsTextSpec/bold-linux.png new file mode 100644 index 0000000000000000000000000000000000000000..6fc990da9f718813b5e25a2dd031601699aa3cf5 GIT binary patch literal 2298 zcmeAS@N?(olHy`uVBq!ia0y~yU`PRB4mJh`hJr^^Ll_ts7>k44ofy`glX=O&z_G>C z#WAEJ?(LlHaFKAaw)?NVzb=&uX~_@~5nj(&DC6pSP;iciOK+N6-O)drFRDzQ+9)An zy6A{TSD@t76}B@Tm}({6U%&a=y9*`CStmc9S;fEG?(3@3Z+5%yJ%8hUH7Y^p*KzyL z6HXg)NiZET)Ugm?e551CbR^M+rGuex7875$dsPQR;S44|Zg(S>1`8j?_Eu#{B?p;h z4Tld+~z~>``xhkshyj?Hc>*8}}3D-dZnv{fsTEN9U83qKiAqWF4!HYOI;}?mzd0nbrG* zC&VZ;9a-jhWcysVvX2&@_OT@R{GYko@)pPH?*>L&|GTEV51e5>Tj0k==9#w)grd(K z=mmT=zJX6Kp9}FMe{yp(Vh1||loD!Pyd$wO!{Bbzl;QbnH>zONm1s*B?rnt3= zrLvx9T?T8-;b=jN@8K2mYEEPe`-%&^wK}!`ulTJAt7o`8I^TSPJ-NVswcCR`c|Y{G z9TMd~TlMPl*Zm5+p2vIC8SzvY9W|ZzyL3arr#1NePe;}B|;~5PW=18?!mc3dp0)8pYxb0Q?lu0l4QWA$2-3pI_+(L zxO?A9g)hGp?Y7R`^+DU|*SZ|n70adPv7hd8FzPx~)QP9}+OxGDjMt7hRUBUZK>8-f z=jm)mW}i2RQGVX^|BxRGoArdqPufXuZQmFhIQ-kqm_O^UN|fKhuUps-Hu}vlpEV)I zzNI4DKArpOuY~`M``jmJTK9UerZ4-SBzsIru;t`g=U{WRGw*_|D2vO%vZ&9}nBa5whxpf6{CI8Cr$U-uh1{PyMO5 zXm0$$J+4dF&o-WTZCUuehWZW7#>Z^~dwsqhKD6&FbIi6E1xu#i*JIK=JLe4h_n%wT z%;qm9;N4sClsE5Q$)d9#UNL>O_Y(Wd zS6eP|@N(>BhpfX#|2Zx_`gf0%+p%c13BNzKbNso{7h@14koZz!y6yMRT2|?)*`6s; zvm^gR3wnHbQg<#X+~~u z_PNFVeY2EACqs?-Y=_j7wmTE5CYv*yJXasJV*Tyk|1&S^r zfi=SH2`Oh@P72+${H*b&gBd?HeP`P^PE5G6=RRA@>`(XfEgyT`PhK{MtzZ60 zRQ?j*C1Je=HnXOs#hGLU`!0L=x;BO5`^j4OQ{RegS0^$uKfj%O)akwT(V(ZEhhNzr z=(XAT?s*cwmToM_B9+Y5^M<<*P2?574? zJ{!cjG49Zwt@D;Ee13Opr>j!fng(5kEfeh6FRZrT+kGLO@7D&8$1-Q{d`Ww=d(+dc z$}2N+;~8%|yxBcvsumZAfaq6~8(adsi&pIrQP6soxj|Gx$|bZ=(;?)_y~o3>Otvb$K%`S~QO>nsJe1i0E`C7gt-}ZA>oBE41`j qJG!c*a#%aq0z+fChL{EanfG`H2(5S`Db2vZz~JfX=d#Wzp$P#0w^A_x literal 0 HcmV?d00001 diff --git a/src/spec/assets/images/GraphicsTextSpec/bold-win.png b/src/spec/assets/images/GraphicsTextSpec/bold-win.png new file mode 100644 index 0000000000000000000000000000000000000000..592ae75f2d988507ee34e5470e04931160f93f59 GIT binary patch literal 2253 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

Ou)E{q7e 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 O7(8A5T-G@yGywqA!Rqq> literal 0 HcmV?d00001 diff --git a/src/spec/assets/images/GraphicsTextSpec/font-text-wrap-win.png b/src/spec/assets/images/GraphicsTextSpec/font-text-wrap-win.png new file mode 100644 index 0000000000000000000000000000000000000000..f5353bfcb19573d672df3733893996dfd431f714 GIT binary patch literal 6407 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 B+(Q5W literal 0 HcmV?d00001 diff --git a/src/spec/assets/images/GraphicsTextSpec/line-height-win.png b/src/spec/assets/images/GraphicsTextSpec/line-height-win.png new file mode 100644 index 0000000000000000000000000000000000000000..d6312ed57db776c209ae669470c31c7d8aa9502a GIT binary patch literal 3996 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 literal 0 HcmV?d00001 diff --git a/src/spec/images/GraphicsTextSpec/line-height.png b/src/spec/assets/images/GraphicsTextSpec/line-height.png similarity index 100% rename from src/spec/images/GraphicsTextSpec/line-height.png rename to src/spec/assets/images/GraphicsTextSpec/line-height.png diff --git a/src/spec/assets/images/GraphicsTextSpec/long-text-linux.png b/src/spec/assets/images/GraphicsTextSpec/long-text-linux.png new file mode 100644 index 0000000000000000000000000000000000000000..b087d18df62ca52f33d1598fc8050514df75d642 GIT binary patch literal 476399 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

JS9rKna7p7VB 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%0AoiJA-R7ri^7}rV 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

you9zWyUkRSHXL)e7bYi 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 z zo!pOXy94|RTmN%DS#)r3k8Q_~h!5K=e2+0$HC>ZPz9@BhMMm%1Ki3ltUgZ8bbNjd3 zo!s-&-wXUp-@X2#`8TC^jwY9z?(N^vC-u(eaMkq$yAKu@{w~@-srTE1-`oCf-7omf z;oXnUkZorJr<^$JJ$oJZg3q;E zhRyBG4{Eh-t?pIL*!6t>)48+XrUfb8ugiO&+xXYX#Np@G)$AGP{=C>Z+hRNG6tkk` zvtRQ{u6TZWr_bU;SGO%_nrhZ@N9e)XSb3ZCpA_b8|Ku{UQOfT5?o(>aH|<)!p4Qa( z_OtMYt%O;?hi~)NKM%}1$uiA*!~N3Nzdo?O`t^dr<>2enj17%nq8RAz2JM@SGleG zzj9o3xb)ajdyVk)BR1(Dvgbr=R4?V4e%9f{>yHmV>y%H;tCeVf^{VuM^LA;AuGtfqFz;laTGs#be_JAc zHF;(mmu-3&_V>{OhN{PVp9?fRJu>;-BA-)}b~5}rq`h4D&aBT`>cUT-1jZk(k$ZeZ z_`OfE(hZiUyXX1o{{JH!FHw1Qb-??k%0D?b%iM!MvdweoxMuL%=iTy(S9v^rg`P>y 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

_Q|fYE^x#wl}j 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

|*@yZ4(2ZR2MCObIOTpHsg23 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

rf6C)R0^mxCk)sHilNq>@Qbs}Qh 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

)h*-MGtW%ezsFx(%~7F860bCq1Yp$RVnPI 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

!^rvifd5j((56sM5kG| z%B_zx^p1>J?X%qU&Y~}ux43M|W)Lk~p8dyy!KSGxiG}SM3xfa`<7d0Wrz~s)nguT; z8@y*Lj@&ZOq=IoVPe7W%EQSXSLL5Ag83QB@!&w$HF?k!@W;9J?ut}fBD7(gCVdXsb zmsd(ovEN}4(Wu&SdaLwG`Rx+T%7Wiz683iVx3`K-_7;%$`5)Y+p|VP?bLyNGZ$Th44hH}T|p znfsG+LqC08>HPoy$A5hH|L<^{{2f#`yx+pOY?jL^AJNr&4nzp>)SmiqX@!}O$iW8; z#>+xebW*=CG#uE#C-Io6fkTKT(ZSh(g-Myw;Wjh3HDf_b0@LX$+a@V3mvmK&;Ym$u zkmdCaX?LB#W6?81ocrbS*^E33W(u6tcK78f!enq+E|t0~(Q=*9V;jYVTkdG^$0|8M`$7c>8-rE6HlXe3}}AjlD{uNrF8B$X_E zz|FuhcCxK0gT*{nX6^+y%rXm&I3^hF;WW5WX*?s@uyd;A9!8cnHHM}If;w&-O>Nu$ z9Qcr9Aewzndf$;;;|T>aHcZ>TOv;M>kUiJxzgvW%(JBR9@m}wgMY|d2?8;E*P)VP1 zM^B#X(UbP2hnrSRP+v1k*}$e}i%p*@DE+_f_}U(P*!U*A{UbcnThw1A95()$JZ1Uy z)QT%P-fZ{cTYs%{i}4oR`AbUqvs3kqeOtU-lCGFol|{aszxrd&shcxr&fIeL>x|E{ zXU;tF^)kl;?#Lqz9f@*F*`6QDQe+Eeef-dHp15-S0uuvUQRm_-JS%DpUT83J8lDI_ z+c*Q39gQXm2#G02lOCt3z_VecvC|}uohfrB>AKvF5-AW^lN#0T;?&Zs7H1JUiEV1GljwA>6pssE zJ|{V>G5`Jl_{Ns~)=GX$859^CRc7!s3an_FId`At@q#Kz;fBH%#ecKf_+}n`5He#O z@4=mh%feh3-I-Sg%eL|C2(Y&ZkPzizl28dsV6>3fsA+H^qe5oyHEnLc+lGw-jLnG* zF$T3(*Sn84amHG9YD}r{(pFf-f4tH2lv1M7v*jGA!4k2?0a`vDfszYvz6PIv_@)1w zNzg&&yYTZrMHmIS_zU6be}ki8qvjQMm4C`xTJHMI)Q#8_Zf&FcN@{AlTGpMIeamwW z^}H>Ki!1EA{rRo)l-!gvXWj%G8|N49*;aGrXQqR|HBVABK42L3Dy+>Xd^R=G!`D$lxeOh$!knPIu<c;s$d2^*(?tReq zQ9hw@th_Kmqon1?1?CIlK5A>se|Q-1B`)INh+txxY%CqYNM=W`17B8&K$1LWIb)Ax$nYFUskK98b{jpB^U;6y!q~9 zty=Zg<(rl_JUi3-s$|Nkl8>PD|DOMwcGyAfJ4q?f@<*WLw*Y_6N!a?I&srPB%R-U^ zPxpxPx+OH-*)Tb}bjR(OjY(-L+QkRg#NK+JRR1sc?}GpL9Is6M|NsC0jYmH$mI!80 zXkhf=bO^X|;v4T~#+-vO3O+n1Bu;V0pLy93acBc?k4cNdfg_v_SC;WN6t7Q9<}>}W z34eMmjym1u%c_hw%r*PHN_~k86T$mJV6<;FiPhx@C8g zlH#(Haybo4=LeQ{&NAfAov^O!;tZo!$;xe)f@1PKl(wh7j&gi-_DQMgqf;}ve7#oP zzqJ0;^AG=jsK@{PH~;@X`TsYsG8izlC5kYf+HoL&*_Xkk;o<`RGdc$u4s0mk;SMM{ zaf1Dfrena#SRY@J%ms(t*#8``P}dS`a^VRSk()KmWSgzpxz!HSmd%{#q1PlIiZKUW*p|5C}3p6a?KE|w=x%PHuF>8dkg7ExuNe%L?X{FU9utzoHk zOF~|rjlpv_#uZ6l*w~ns_N2&tQFCyZl-R)C-ee)kI*m(hYJ}QC2g$&H)f--Luq1qB zY+z1PWasCX31;L}^w+j&o?kUXUL~a~UY3uKYpKZ-!Hzcnw0w7)W%F}PRKs{1)st+-P4t4W?5R4rIlUFOYNIE)!5kLaF@X=#sm$f8GE}RP>yhq|B`|r=3w?)-*hEko9vh2Tx3hHHTodz@vnOmkkHK zT`zDqh%(A<7_t9FBGr?LzpxV){z?lSi!>%}Se&xpVw0oH zW{ut`*W}#QE@}dcezV%SHlJVl?B}F+fp^?3+YdkDEaqms%*^U6%CI?Z>*d$Y&0+@* z^Efw~#C~WwaY$gn@dlC2j~y)&n8dVw6qFcGL>jO~Fkj?Vp0nIhHo;)+C+Wf&GHb1k zW75_(C9j!zoKfe`L3g`-Y`UEq=^JmharkWL?}Xucx8RTch2vN4~2cdzGUwq6<3SBhkRA`n3i(>|NsA!;B+ks zo>LA2oxUa?Et-~`I=bnPM2JN~LuEt9GB3^sCpJwsEw?ClIk!J-5}ZQIC#}qm&eq;$ zvvck(wvfN>u{YM3ypO0~`1;d~vL_iD4+H`i2rgyLFyK1ql)xeq5#-hoz{aSOsdUg| z3XkQ9b&e^IJiUzEyi_)wI4Gp!p`GTZ)Gc(`raRd>}*eL}03?vz|IU1dvO@g$wT=oPDuhxY#e|LFh!Pp87> zeT(Atns_L2x^KeANr{{LOhTSkG&bDh$P6%3RitoQ_}r|Ns9_DTYZ73~WqJf06_oA0NocaN-q6^(6~7s~y_p-27S5YboPB z*Y=2-B_av)T|Ope2`yqOa5@rkGp})~NyG}*?#CZzJezUZ$oKTgnUazLdJAGrlupc4 zYs#2D^M%@RL63Qw(vyukl_CvHHnCswy|pEz$tNLeqD@LpQp&8ms@EpXo7f$-`{c}0 zDb>e)g~BhsrB0Xk`8Rt>ZO*5Lf1wNw4GhfO3(QO-_=OJamYhBzv+;uTjED)0T@HN` zyp4se8M`H%8&5XeSU01TWn<$EjT!EZ3mZDPXSgspHm(5gzx&d__P)VsT^T6Ac@;qW zk1|U|cD`f)?f(MpKavn(=GJwX5GVMMWhRf|_CAO1U#Xi9d|a{S&!#ojMUz852gy8t zay`S~aJ+w#?yBwi7cW1~64v^)>DK2jm)3f(4@%71d-G?l>aW~d(?5p$!`immp1S!| zV`@-h`pY$WOMl&2GUJr1e|62V^Z(Z5@6Ugq{rms_@a?9X#ujqATN+9~&~ zj*E`}|Nq}o&J_n=F70eP^3*8o+HR4Qeo!j=v-fuPw|9qsI=t-IDwpnAyHDWKFHqa$ z|6!gD&tLz3C&O=P9saTfl>W~)u;qq3ud7yo?>}0p8oYC_fCO~^5d#Cmf&+7Sdjt+v z9O5zL@ef#VoX6x0=RubPCA>Wvu1Aje2=cHuh#a`U+;E^H!HQwQ0c8Ur#$+}HKLZ6O z*X5dWB5l%s9G->(oJoys%b1v14>>4G^*KzqWV&nJo7UyZ*}Wde?oG>@;d}6R`JCr> z56LgDbm>ZswJ2*{->H>E5Dg%Xa_xyme>xp8uzHET^0Q`1k!@-Om5N zj_d61v%MDm{;mYCy!QA1Tx~6(%x#PcOl%Cv%nHGV>57MCHzXKHvkEgR1nX!-_9Y88 zA806CA)r2E6`RB~MhOXhDWRn@XRIXbIA(BhOYoRT{NbJbDYm)iGy8$ZLW~=n3O(2g z9bPF*a8}NkaB{_yov9(q927g%4qTXU=gPy(1tKY4B3ne;E8~Avsg(1{n;lUVQ{A4q z?%wvZx9(TBntGSn&-%T2?*6r@*{?tIMxIPE+hZi^vSKPr!xMh4ZczBIg{NU=;nb*T}!z9ajHtKKo_!oK*~r2NUvD8Il5g4Sq>F>lbV{IKURn9N=KU6crrK ztn^57jgW+moWwQOcJ?+w=4WZ2)E_W5GFp8zuvuZCFxiMxhowD@n`>#}0ZT3e9ub2d z`UVYZ1~J--tUa3|dseY`G>Um7a1;q^_D|lx+o5=kfzem@q@(;?gYHLsb7!~$bIq<@ZLj|lNhZa-o*5)G;8De`mGzo ziZ}TRoKQUY>&N?Kn7Gx}$Q@1BJ1zZT7ux5#_T4;z10u$C>95C4D7ex;3A z?LI#S2B8HO`VFF%%_k;4dvdc~F|q4`gK<2gTVsO8Nrw*y3RfJN;3zQfv%tK7z9j|> z5z4F_$t=yn&IcP6d}M@~IuElre92?vR9GN#U_phO!c5V)8GJ$=4eD?GytkN!SXoY# zoLI2I^UJyJE3fAN?@nZkSW+b6`@&A^`Taw8Sv)K*oLWT4uS`b&LI8{xf4){q+C?gUSQCqZDQ#**m5D@yQHGNM6TV?wvp96>BEKV6(;NC|EPtt znjb4tDmtwAqyFuG#~|`_p=jWVBMc3T-Hj3w9Z$0*7(R~gl;Gf0{5SV~IcD!OdAINT;Zs_TGqcL?b%=V z^^be2#XdN+uFZeRQsMlgVoeD1viY;WeLgX7N5AC9rPkW79?h1x{LVD-_=)QkC%dZ+ zPUbG(_58Kvs>*GN4_`Mh2r$L$Zf2G=c%aPdV%7Yhyuwji&|pfz6OK%Ci6gDkmP;&A zTh()*wljxUx{=B1@5(c(n;jgS)?}q0V)4np*T{Uq>GJ26`rmb#x~6=0E}qU>ePI4f zqs-7L{@y29><=q$kn!V?GwA8L7;x)hlfj)wxss2&loT6xuZ-HgalO>u^w6`RURBi^ zhh}=e;c}TY6+SJGwyOv`7gRjYE@u{G3k_OX_~DS$2}4H1jcfIGVuQMm@;@o#BLGroN{e4e5Oj!Fi^+|YlO0JzXBf?JWmIY&S>y3xc zLE(Rb;qwdkAn8gc*!jbPZ*4<;A8O8krvD35o>jhZ{irTN=*=ATOtQUAU2?gZM2i1O4uQl2 z3M{PM>k>qd-#1ElkQB-$mLRsnuwiOZlEN|;j!Vv*J_4$z>$)eb6S28GD`XFkq`_)6 zg_4gEtc8}02P$IPq;I;az5cO;FJJT=LyvLvo4okOJA&(atJ42S&3T!&AVtU z%*UnO?N=wn9N2V~^zaqR+t9eN{<6ze0p|M7hC@NY7hlOHU2bM&YGPP&Ky87F73;Bs zi%%?RZe{(T_x*=Vr}l*h2Pe(Rkm#vAYW3E-O{^$G%4 zl$mcO5BEpDG7@<6Ol8rzE|<1bPOAkcT+jAd3+{j2X!-oxKP0%qDGi$b1^0Zl%X^az zEB|jgZqF~@d0)!^`}10jr!P6UY~IHjFfiyHP|;jg*m!W}VH3|SDLb1VM>bt<+;O49 zYNH?nQ%iyfBO5atn|9j9)yLF4*ls9_7|v00Sggpd#%%adFle!o0G|ejGS|DgvX`7@ zByi4t+iy3+V^WpG24!c14J}fEn;Dss)9jqZ+7_)nBO%Cqzg=->LDZLhn!H+K8`|L@;i^l_;!Qkya9%uvccqP$%VGu_~5k7vtrNLpZIz)Fx>6bpKT=^%=7trZur-`7R>|SfAON_ zi?`p!;90`3@i&nvf6d;#ISUJahB?fPJF9va8Y-^2H1jNTGB})|#AAA_qAU4KGJ{Hr z?3uTc#wR-5^bN%oF3q1TG|TsbuZ+RWpn&3lg*_~fmIRAT@M;MbY-n6~@ZpDUlk}B0 zT6C5-gncmh5D_#}%}r3;Mu?4_b<#y{cSctii3=`{0ZIn03I-n>6LrM`d1aR!W7cDL z;S=dr-mT=Pm)VYP(+tk?Q$xx8+&e6`n9wXO5o>9aJ{ ze*ITG>kly&Bw`U@V0nM&aS3;W|Ic=-ooh}y7_-kimy~AWpmKQ8Vj)3+DP7C-h2>q+ zl5)~im^>1cisU}CG0cbvU|>wLZDDXe=*G9B`!o)M8E zZk?xg; z*ft+M*^;oaiy`6!Lqb3<|czsVL5fj$1_EI&8jk! zIGFuUNK{j(`?eD4@8BhCncjtZ$?RJryV5}47uQ+XI zy{Fg4jZ^9?x-VU>bEpvut^WUFHTL}%=&2mUXJAQXWcPGnaM+Yq-Y0u4hT)8`v2SY-VOSBP4I&z>qPe;EH6^q0!5Z0qi=Zq-@xw{h{F#EJdtvv%&D^Wu@7dEdKvZ+5+W z^sU?fq)zC|g=FtPVqlodIB%I@6T{6NWtrPlW;Q?4oGf^8pJU{u*S4lB}8LWPVmyFb>JvpSd;lQMqvg4~B()k0HiQSxyrQgi| zg=xiPC$ko5pE|KMYVlHzRHMxcC+e^KQo7Me`OK}qE3b4gI5e;vyr}TD>CQV74G&I( zwhQJa_8K>NSY%i^jd>0nF%jbQy}@!Ov*x0sPlJbm5WkZ^GaHj=qw*pnb|y&!&X&r# zN)8&L3ujI&_$>VCFR!V0%qq#5DK-LruTCl1z4m_Cb?wc?yE}TfeeIJ>KeXkaVnW*q z%m0T@EuFs1)hFf5*_Wv^Kc(ad6ek~*U;TggI(YeyrF4M`F^DlHs5(^|@JZfk6P$4( zY=#fR&DNj7QekZZh5rt^F{?_L@FX3uY?#9y=g>F#tP!Wc2KGj4`iJZ4SBf?@|RJjf8K;L~7L<=$~NV}VSf%fjc)8a(A^Sa@8zDm@s4 z4$h5=s53j}s9<5O@j9(9yliRYrGra47S*5Xbd_43x#osqHJ6CT$Ip+dbXHp|kITIt zzjcb#-pbAwPY>}<7W)6~@7+?CMn{hXKK3+j$Bg{#N80YE6(mj)VUyOC%2Atq?9zcr z2?cU)b!=|IENSvg$2i*6;M%# zTHWN{xQTCF#@gy|VEMkxbA0QkEcwvJ;V?0{dEpg~0FBC4e}j|Z3JJH?mKmyVc)0iD zp$8!g_8Xsnwm7)>vsHKA-i+C^>mSbEbnkiVotIC|szKrZj^)cM+tb2#qG0E53#a_o z_xs2VD}R2b=f}4f?+vcro*w!&I%a3x^@8)Z{~j;#maWw;pOU|5juE5EN)7=A7X=Y9 zPGdQ>->g;>8y_f3mvO2WD|_G`RjXoWXH)z0=GM6Hb=QaFDZN&b;*C;giZM&GR#jU8GptS0C^R zoqgVGso09w>4DMjZ=IHW_it77{Y_gw?!Pwc=Ku8C>Br8+9V`EKchC3NXKf&ERdA z*%X*3na{)7*V%ab!Nmz3oUMH)dlET%)){9c8@v!Qa0!WSljnFQ$-rjN%zmYdVc}m! zHtFfEj9JnvFE%f%=FiKN@!?##$e2a;?bBT$KLhestYxiaG1T7B&T((K-QAl>DZa6hxyYOuzW>|%-z!-JoB0;#8d$R=b2D5v_kAFo^D)=Jne{W@;|`+(uAi$MP8mEB zSsZ$yS@KA+D3dVT&*n9kf`!x<*EvoWI=5Irx+u*?V1h&i+l*-p49x}y3Jx?JIhv4j zc-x%Efj<^B#V(M3HbGJ$@$xcPhl0x@Vj^d*tym!Jp~+Ek|Jc<#xxX6cTWPx5`HEfb z^8R2t@A~X(Wt-Mcx4Qc-@>%iTt^QwMoyyBQ+jr}C`0sV^YuEm|`sedCiOc`Zr@q-; zm-dW7Sh3AseNpWuE&o{tMT`ywYBMxi4sI8EDLs3#V9N!;87|X5u2^|}Rxk6+#tst+ z367nO9NLpvG@CMxO3rKGob~CzhQNltWdha>bJDbRr9<=*9-LrU|C8tI1zWe~yWX(+SK`1=3IB3W z*!Y{tXXn5JlBXpMDz@_e2vM5otYjSN(;d{^Cl?hG^D5}gU5Q5wJM1_cdFA*acJyPvHYy3xwk>1qd|<@)8W%Y)&s#&hn-dP82uSr zeRO&hOje1dJmy%T!mzM&fkY6`PLn07i-iq@LZd#N3VCM9bYP-xv`=>4<3+FSHz+T^ zy+g*;>Hfy(IM2P)C0tFOJb1Nc^EZtfB{6Z?D>WT+TAuyfG)436{<7VY)0U(M2Dl{L z{Au!Q<-JFBwJd3$6ePjb{LI$9+0a{=zw1D|gaC&`S=NjLQZpF185jZr$_zLqjJTN?lGz!8`M5UEWqj~Z zRq%`wpIh@wnF0|B*STdAg>#ja9M;To*G%$PS#MSIzQdh|Q~~OspXU0 zc4~=sJZMx~^y|O9#r6Lm?{!cRNVvmvNI;T_EpgM`5^05Y$HoQ1th271WLWNVi|NSG zJ(A4KTMi2dJ8>BcvIJYQ2lI+P)SPozN#^jAI}u9^WRk=Lc=%X(xVe~H8axDav?U^1 zWm$Y?_%P^xTHz2TyW}PZgE(i<+Mp}7vJ#IvZ}*)wUN$|?*u3ax;uLSr?5{^sCA}(+ zT%D~Sp>n*~vm|Sq&*TYbcSdVgg@%0J%xb?y$1D8L=6gxo!#@7r^RaT?mEV804CXLz zNKliI@5x+lerE2pPRX_gA&Femm5&cv&-}|Yvqxc}L=(%z)&uf0l1yee@z2ew?|At* z;9!FzPm;pB)C92vj|x7kGqOxf4`wzruHbMod?I9UEWmKhWA5e?vl1k9CiyJnIpfYL zbs>hqQ?uhTpMed-zMB!jQPr=#7F-9V|F1n?Z-*QgM(jTlbNDNPwEyna-czrfZ^b_S zR`9eod}Xmzu<*f4OMlGFI(EmVQSs00HGO{`r@x#!Yn}7F#b-86OgeV%?1bt2FMC_2 zJQEFr?5@SL!m+xh+;?d7J8iWUc6dgx_)%qn`4GhxdamB~hDqGmtcYONsY z=H9#1YtvPO{hKZ3guPbGi`GuPutI(7w|#Ci&%CYQ9<@IC-}Mt$8G6(kLJpL$_OLU^ zT%E>!HsYwpAram)zM>Jg9&9-?zoFrPh7ZH(2PXqgG#sAyx!941lg)SrPe5Cm$%(5A zJkl}?e}u>+FdTA`h+tP#la{mD5&uI_KKNA^@0OF2TUP(`niMuUs{!2qdei@n)BZ^F z-6YufvzQ{I2>(}2SpDnr>dPHLt_cs9MeUw!=^o2Jr?ax!JE$*x%GDm_wVNfby!<=W zEV!!mhJ>J$aKn`H?-%3$F5`75NU&jj#{H!;=2fcp)RcaSDd6_71bBEsr$!PhNlatwc)xRZ^cSWEM~7(=iVTI#D+=ap6la|H!%aerVP#K7{yf7L z%_#~>61$i$b}HD;kZTTXoWL-{tSNB*4cl3EKhhZ=HZm`m^1&*Ak$=_>I~5KQ_D-go z3oL{Zm}hQlYHJaKT6@|c`)RDb?IMF$jL8fF z?gkO;%w6AGjKq02vpk40c$gc!#bAZ88=tXML9szSS22%*f`JN%3lpzwdw^Oe!=C^J&{mwXiQ zFE|S;|GnqftXj42q2FS&ZFyIW4Q+Osa_u%(d++jmff!SRQ&oZyn;X-@f0;`zrd25% zONbF;liSFbS|!ZBT>2TKj@w45XEB`5IGEX7w4VQxZj%z=nz>0r&7!eOkHFI!jzU}P*>;G=~E8<_O4l94wE#0kNc64dZG2Vo)W(1sk z(4fW1;q#!e;b7vP0|zD?SYR_nFprm4s)O}Fpuv9C)VEQeFQ>lguq`ov{$kFJONKjy z%p6>tCaWwinawpN*3n5sTfpW@pJva?wt2B8R!*CyTn;>3bR@sL>X^*LZA(4gwix7| zas9Prqs7Vo^3R}V!G{0;S9~*n?DPL+M<$;FGb4k)L9FQEMR`@GrNYY02XzgNv>rb@ zw$=C#^I`dfDFzy%%1jqF8t^k8<`+0%{7@*F^Anq40Yig;s?1u$)2d7&=YQ}tC>&^L zTrm}UsboW*?B5{vzQA1)+6pZ z1_wi>TAzOF|7-Yl`lgt=T`v|*-0)N7p{yJz{QvNMt#NP>z71c0E9U7c;9sf<3xC!5 zd!nqBb^Wy!kHznb3q|UwH%_9!Ur^d~6OVotM9T=gNp3GjdyJ zb_jRL95FpHX~Myn9j> zdInr@-7R+G{-f4-CLX3m8)sZ<3_e*c`ex<3#z*Imd~S@>=CynGQqodTYehj++BxAx za(XRu_9wLEs>N|%SI-G#T71@2QCRzi81FRguGy1?6K)<|YH)d0rqkrVJ2b7M%=c~n zb^rfgnehL23QcGIi~lwK|Nl!zuL?ReDatZ4ayD8B%k0u%oDso3L#0`=c~+@}sJi80 zhDANj>PveLG4Lo#yyB>TQrXVNc29DKNLE51H=AI46WfaqQ@TSV!ZKbQIrv~jTB7BW z>nhquA1pe0!`;w}Ien_I@|#U%7ghw=RD|_D4LsC)Q%z;t$*qZEh7~av@7xN^*yIli z|DSwcS2#E$?Y|T6jO5WT)P=48EY!NWGIg`XDerTEeX*5wbBrEJoPNIk|NU2z-TOEGZ>rr8HVgMIA&)y*WQF-n%m|+;i$Grc?|a~KL-db zoG;MObUH@I#E4Z2dVk?7?LQbC1T+ zy;c_rGgMp*HgK%Tiex+`!DeK%##Lo^wD3P!VTX361tM`j4{zxaYS|KS(WPsa$;{RlAz^30|Vm{1_lNN1_to?GlSFR!^2eohaUgp literal 0 HcmV?d00001 diff --git a/src/spec/images/SoundSpec/preview.ogg b/src/spec/assets/images/SoundSpec/preview.ogg similarity index 100% rename from src/spec/images/SoundSpec/preview.ogg rename to src/spec/assets/images/SoundSpec/preview.ogg diff --git a/src/spec/images/SoundSpec/test.mp3 b/src/spec/assets/images/SoundSpec/test.mp3 similarity index 100% rename from src/spec/images/SoundSpec/test.mp3 rename to src/spec/assets/images/SoundSpec/test.mp3 diff --git a/src/spec/images/SpriteFontSpec/ExpectedFont.png b/src/spec/assets/images/SpriteFontSpec/ExpectedFont.png similarity index 100% rename from src/spec/images/SpriteFontSpec/ExpectedFont.png rename to src/spec/assets/images/SpriteFontSpec/ExpectedFont.png diff --git a/src/spec/images/SpriteFontSpec/IndividualSprites.png b/src/spec/assets/images/SpriteFontSpec/IndividualSprites.png similarity index 100% rename from src/spec/images/SpriteFontSpec/IndividualSprites.png rename to src/spec/assets/images/SpriteFontSpec/IndividualSprites.png diff --git a/src/spec/images/SpriteFontSpec/SpriteFont.png b/src/spec/assets/images/SpriteFontSpec/SpriteFont.png similarity index 100% rename from src/spec/images/SpriteFontSpec/SpriteFont.png rename to src/spec/assets/images/SpriteFontSpec/SpriteFont.png diff --git a/src/spec/images/SpriteFontSpec/TextShadow.png b/src/spec/assets/images/SpriteFontSpec/TextShadow.png similarity index 100% rename from src/spec/images/SpriteFontSpec/TextShadow.png rename to src/spec/assets/images/SpriteFontSpec/TextShadow.png diff --git a/src/spec/images/SpriteSheetSpec/NewSpriteSpacing.png b/src/spec/assets/images/SpriteSheetSpec/NewSpriteSpacing.png similarity index 100% rename from src/spec/images/SpriteSheetSpec/NewSpriteSpacing.png rename to src/spec/assets/images/SpriteSheetSpec/NewSpriteSpacing.png diff --git a/src/spec/images/SpriteSheetSpec/PlayerRun.png b/src/spec/assets/images/SpriteSheetSpec/PlayerRun.png similarity index 100% rename from src/spec/images/SpriteSheetSpec/PlayerRun.png rename to src/spec/assets/images/SpriteSheetSpec/PlayerRun.png diff --git a/src/spec/images/SpriteSheetSpec/PlayerRun0.png b/src/spec/assets/images/SpriteSheetSpec/PlayerRun0.png similarity index 100% rename from src/spec/images/SpriteSheetSpec/PlayerRun0.png rename to src/spec/assets/images/SpriteSheetSpec/PlayerRun0.png diff --git a/src/spec/images/SpriteSheetSpec/PlayerRun20.png b/src/spec/assets/images/SpriteSheetSpec/PlayerRun20.png similarity index 100% rename from src/spec/images/SpriteSheetSpec/PlayerRun20.png rename to src/spec/assets/images/SpriteSheetSpec/PlayerRun20.png diff --git a/src/spec/images/SpriteSheetSpec/SpriteSheetSpacing.png b/src/spec/assets/images/SpriteSheetSpec/SpriteSheetSpacing.png similarity index 100% rename from src/spec/images/SpriteSheetSpec/SpriteSheetSpacing.png rename to src/spec/assets/images/SpriteSheetSpec/SpriteSheetSpacing.png diff --git a/src/spec/images/SpriteSheetSpec/SpriteSheetSpacingCustom.png b/src/spec/assets/images/SpriteSheetSpec/SpriteSheetSpacingCustom.png similarity index 100% rename from src/spec/images/SpriteSheetSpec/SpriteSheetSpacingCustom.png rename to src/spec/assets/images/SpriteSheetSpec/SpriteSheetSpacingCustom.png diff --git a/src/spec/images/SpriteSheetSpec/SpriteSheetSpacingSingle.png b/src/spec/assets/images/SpriteSheetSpec/SpriteSheetSpacingSingle.png similarity index 100% rename from src/spec/images/SpriteSheetSpec/SpriteSheetSpacingSingle.png rename to src/spec/assets/images/SpriteSheetSpec/SpriteSheetSpacingSingle.png diff --git a/src/spec/images/SpriteSheetSpec/drillandcup.png b/src/spec/assets/images/SpriteSheetSpec/drillandcup.png similarity index 100% rename from src/spec/images/SpriteSheetSpec/drillandcup.png rename to src/spec/assets/images/SpriteSheetSpec/drillandcup.png diff --git a/src/spec/images/SpriteSheetSpec/genericItems_spriteSheet_License.txt b/src/spec/assets/images/SpriteSheetSpec/genericItems_spriteSheet_License.txt similarity index 100% rename from src/spec/images/SpriteSheetSpec/genericItems_spriteSheet_License.txt rename to src/spec/assets/images/SpriteSheetSpec/genericItems_spriteSheet_License.txt diff --git a/src/spec/images/SpriteSheetSpec/genericItems_spritesheet_colored.png b/src/spec/assets/images/SpriteSheetSpec/genericItems_spritesheet_colored.png similarity index 100% rename from src/spec/images/SpriteSheetSpec/genericItems_spritesheet_colored.png rename to src/spec/assets/images/SpriteSheetSpec/genericItems_spritesheet_colored.png diff --git a/src/spec/images/SpriteSheetSpec/genericItems_spritesheet_colored.xml b/src/spec/assets/images/SpriteSheetSpec/genericItems_spritesheet_colored.xml similarity index 100% rename from src/spec/images/SpriteSheetSpec/genericItems_spritesheet_colored.xml rename to src/spec/assets/images/SpriteSheetSpec/genericItems_spritesheet_colored.xml diff --git a/src/spec/images/SpriteSheetSpec/kenny-cards-license.txt b/src/spec/assets/images/SpriteSheetSpec/kenny-cards-license.txt similarity index 100% rename from src/spec/images/SpriteSheetSpec/kenny-cards-license.txt rename to src/spec/assets/images/SpriteSheetSpec/kenny-cards-license.txt diff --git a/src/spec/images/SpriteSheetSpec/kenny-cards.png b/src/spec/assets/images/SpriteSheetSpec/kenny-cards.png similarity index 100% rename from src/spec/images/SpriteSheetSpec/kenny-cards.png rename to src/spec/assets/images/SpriteSheetSpec/kenny-cards.png diff --git a/src/spec/images/SpriteSpec/icon-colorized.png b/src/spec/assets/images/SpriteSpec/icon-colorized.png similarity index 100% rename from src/spec/images/SpriteSpec/icon-colorized.png rename to src/spec/assets/images/SpriteSpec/icon-colorized.png diff --git a/src/spec/images/SpriteSpec/icon-darkened.png b/src/spec/assets/images/SpriteSpec/icon-darkened.png similarity index 100% rename from src/spec/images/SpriteSpec/icon-darkened.png rename to src/spec/assets/images/SpriteSpec/icon-darkened.png diff --git a/src/spec/images/SpriteSpec/icon-desaturated.png b/src/spec/assets/images/SpriteSpec/icon-desaturated.png similarity index 100% rename from src/spec/images/SpriteSpec/icon-desaturated.png rename to src/spec/assets/images/SpriteSpec/icon-desaturated.png diff --git a/src/spec/images/SpriteSpec/icon-horiz-flip.png b/src/spec/assets/images/SpriteSpec/icon-horiz-flip.png similarity index 100% rename from src/spec/images/SpriteSpec/icon-horiz-flip.png rename to src/spec/assets/images/SpriteSpec/icon-horiz-flip.png diff --git a/src/spec/images/SpriteSpec/icon-inverted.png b/src/spec/assets/images/SpriteSpec/icon-inverted.png similarity index 100% rename from src/spec/images/SpriteSpec/icon-inverted.png rename to src/spec/assets/images/SpriteSpec/icon-inverted.png diff --git a/src/spec/images/SpriteSpec/icon-lightened.png b/src/spec/assets/images/SpriteSpec/icon-lightened.png similarity index 100% rename from src/spec/images/SpriteSpec/icon-lightened.png rename to src/spec/assets/images/SpriteSpec/icon-lightened.png diff --git a/src/spec/images/SpriteSpec/icon-saturated.png b/src/spec/assets/images/SpriteSpec/icon-saturated.png similarity index 100% rename from src/spec/images/SpriteSpec/icon-saturated.png rename to src/spec/assets/images/SpriteSpec/icon-saturated.png diff --git a/src/spec/images/SpriteSpec/icon-vert-flip.png b/src/spec/assets/images/SpriteSpec/icon-vert-flip.png similarity index 100% rename from src/spec/images/SpriteSpec/icon-vert-flip.png rename to src/spec/assets/images/SpriteSpec/icon-vert-flip.png diff --git a/src/spec/images/GraphicsSpriteSpec/icon.png b/src/spec/assets/images/SpriteSpec/icon.png similarity index 100% rename from src/spec/images/GraphicsSpriteSpec/icon.png rename to src/spec/assets/images/SpriteSpec/icon.png diff --git a/src/spec/images/SpriteSpec/iconrotate.png b/src/spec/assets/images/SpriteSpec/iconrotate.png similarity index 100% rename from src/spec/images/SpriteSpec/iconrotate.png rename to src/spec/assets/images/SpriteSpec/iconrotate.png diff --git a/src/spec/images/SpriteSpec/iconscale.png b/src/spec/assets/images/SpriteSpec/iconscale.png similarity index 100% rename from src/spec/images/SpriteSpec/iconscale.png rename to src/spec/assets/images/SpriteSpec/iconscale.png diff --git a/src/spec/images/SpriteSpec/opacity.png b/src/spec/assets/images/SpriteSpec/opacity.png similarity index 100% rename from src/spec/images/SpriteSpec/opacity.png rename to src/spec/assets/images/SpriteSpec/opacity.png diff --git a/src/spec/images/TileMapSpec/Blocks.png b/src/spec/assets/images/TileMapSpec/Blocks.png similarity index 100% rename from src/spec/images/TileMapSpec/Blocks.png rename to src/spec/assets/images/TileMapSpec/Blocks.png diff --git a/src/spec/images/TileMapSpec/TileMap.png b/src/spec/assets/images/TileMapSpec/TileMap.png similarity index 100% rename from src/spec/images/TileMapSpec/TileMap.png rename to src/spec/assets/images/TileMapSpec/TileMap.png diff --git a/src/spec/images/TileMapSpec/TileMapCulling.png b/src/spec/assets/images/TileMapSpec/TileMapCulling.png similarity index 100% rename from src/spec/images/TileMapSpec/TileMapCulling.png rename to src/spec/assets/images/TileMapSpec/TileMapCulling.png diff --git a/src/spec/images/TileMapSpec/TileMapGraphicCircle.png b/src/spec/assets/images/TileMapSpec/TileMapGraphicCircle.png similarity index 100% rename from src/spec/images/TileMapSpec/TileMapGraphicCircle.png rename to src/spec/assets/images/TileMapSpec/TileMapGraphicCircle.png diff --git a/src/spec/images/TileMapSpec/TileMapGraphicSquare.png b/src/spec/assets/images/TileMapSpec/TileMapGraphicSquare.png similarity index 100% rename from src/spec/images/TileMapSpec/TileMapGraphicSquare.png rename to src/spec/assets/images/TileMapSpec/TileMapGraphicSquare.png diff --git a/src/spec/images/TileMapSpec/tilemap-from-bottom.png b/src/spec/assets/images/TileMapSpec/tilemap-from-bottom.png similarity index 100% rename from src/spec/images/TileMapSpec/tilemap-from-bottom.png rename to src/spec/assets/images/TileMapSpec/tilemap-from-bottom.png diff --git a/src/spec/images/TileMapSpec/tilemap-from-top.png b/src/spec/assets/images/TileMapSpec/tilemap-from-top.png similarity index 100% rename from src/spec/images/TileMapSpec/tilemap-from-top.png rename to src/spec/assets/images/TileMapSpec/tilemap-from-top.png diff --git a/src/spec/images/TileMapSpec/tilemap-scaled.png b/src/spec/assets/images/TileMapSpec/tilemap-scaled.png similarity index 100% rename from src/spec/images/TileMapSpec/tilemap-scaled.png rename to src/spec/assets/images/TileMapSpec/tilemap-scaled.png diff --git a/src/spec/images/TiledAnimationSpec/kenny-cards.png b/src/spec/assets/images/TiledAnimationSpec/kenny-cards.png similarity index 100% rename from src/spec/images/TiledAnimationSpec/kenny-cards.png rename to src/spec/assets/images/TiledAnimationSpec/kenny-cards.png diff --git a/src/spec/images/TiledAnimationSpec/tiled-2.png b/src/spec/assets/images/TiledAnimationSpec/tiled-2.png similarity index 100% rename from src/spec/images/TiledAnimationSpec/tiled-2.png rename to src/spec/assets/images/TiledAnimationSpec/tiled-2.png diff --git a/src/spec/images/TiledAnimationSpec/tiled.png b/src/spec/assets/images/TiledAnimationSpec/tiled.png similarity index 100% rename from src/spec/images/TiledAnimationSpec/tiled.png rename to src/spec/assets/images/TiledAnimationSpec/tiled.png diff --git a/src/spec/images/TiledSpriteSpec/from-spritesheet.png b/src/spec/assets/images/TiledSpriteSpec/from-spritesheet.png similarity index 100% rename from src/spec/images/TiledSpriteSpec/from-spritesheet.png rename to src/spec/assets/images/TiledSpriteSpec/from-spritesheet.png diff --git a/src/spec/images/TiledSpriteSpec/ground.png b/src/spec/assets/images/TiledSpriteSpec/ground.png similarity index 100% rename from src/spec/images/TiledSpriteSpec/ground.png rename to src/spec/assets/images/TiledSpriteSpec/ground.png diff --git a/src/spec/images/TiledSpriteSpec/tiled.png b/src/spec/assets/images/TiledSpriteSpec/tiled.png similarity index 100% rename from src/spec/images/TiledSpriteSpec/tiled.png rename to src/spec/assets/images/TiledSpriteSpec/tiled.png diff --git a/src/spec/images/DebugSpec/lines.png b/src/spec/images/DebugSpec/lines.png deleted file mode 100644 index addc4cad027ab5ea62437b4b7ac6c9a2f163bf07..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 165 zcmeAS@N?(olHy`uVBq!ia0y~yU;weXIM^5%7!`jV9vR8i>Hb4D^E|(rCa|Ud2+fEyXx$BA3Jd3z=03) zY7J{7B71zJxEBeesBU8E=+EKqkJNBd+>|6BeY50~h)}9&;5o{Kk diff --git a/src/spec/images/GraphicsTextSpec/bold-linux.png b/src/spec/images/GraphicsTextSpec/bold-linux.png deleted file mode 100644 index 9d22c1f2da23cb29fdcc520398d744b1923d9916..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2094 zcmeAS@N?(olHy`uVBq!ia0y~yU`PRB4mJh`hJr^^Ll_v?zk0ejhE&A8on4s|5-QSO z|2ggT8*ldsyB2e3<*j(o^;_&HuVe3{zNV=ftf|2~t~vqci`-bvT^27=oTacx$k$Xt zFfgEyH@a8U+xqf3pXo2p>`8w&_e_eF?3aCQckbAq`OCtEGyd3WT-^$V5nq<)0oVZPp0yoBTAa}`C^9lW~T(^w}j z_HOJ;=Ti=!^@#hXSJiim>F(r)X&eW3ma^EaK7M!>$2X~P6SMi( zuNH8|#LsPi5}L1M`@>uzx4riH#1Cs{F+>+%jZ3fDl_f4@uH*b`!~Ne!T%Or+XO}b- zyq%j~-*RL}c;%kgr@0^2rz`!RW0#=5$T*E@7GLz`gE3V}f3#cYENj_v|Buct_c}%i zF^g?|4RZIIeL|J}Q~v&T*kLx0^}Kqxc*~7)p2Yv3cTG66GgYPO^fG1Po4qf-SQ_l% z{I^Cml=1M*xzfv16%KX3T2NZ~bN|^R&ssBb6YU~-%H8!hM6D5;cx!p0r}b&CllJlN z(&9QYY};Jjb6zR$KyrJ-=Ns%-H<9d93q~kE}1O{u5Ja3t6I`` znoSBN-aT(L6)ypX{yoacAEDzCWj>i#PqbT5q0dtbf{r_>8$<6%xFgef_Tg;uhHd zveK^a_hs#ezaO|wc_tz@X23E?Yz!ERz}U})Sb)m@A~`J*RwCyyt(qh zH)Hmej{0x=>V<7yuhY<8VzR9y*gTqFTEFt6R!L8#^>qDY<{Zh0|0|tR?x1w}Ydyie(@D$YgQSKl4UelFg{ANQ zR7_^%uEy=qz#O{|$&TjrEm6zD_oxdE6{IfazYw3q|vbXgW(_SZf-e{AZ zYq@yCmd*QH=dEc?{=LD8_pi{Qd44gQW#&GwopIZ_&Qk7XfcB>5e=H^1PUp`wKJI^5 z+v1X@`*y46XS2Ert^UimoHra(s(r9wtKE+x-ZMw0adn=l6TDWDai7aDu==0(%XKPI z&;6b*-}Wc;&fdT81imR)^Sa8<=*`)|YQUiTvVCu%flc=DL;GHLI30Slbx%mg!xwJF ze{*-LzCJ!#pr-IxT>9#nH|(6c)S6cESw6Gg;v07&`_q0y$#v_`>t0FUCigAjcgyn& zwyPTblguuDDd5(TjoZL?ZoXQut7YqS9kYttN2-?e-9KS&b$*xO9^(mH58aY`Ra*2@ zU-9VU4NA4|?{;$_@ub&$UEKjl8P^zw>|G$$}lI| zud)2=*Ar|>8%$-7SfBH;UAfq7@!DU8c4EoTqU!DJD>pU=epFmxv0PK}6FM75G+Qwuk*-y(PSV(+!~tRmTqPu)`P37uPZ!SKzI??Jp;X7f++>;If{$f=}U=%iu(;@4Zw z|1?~8=V+Q^g6r4+Tn`u2=DyhTf_X{bU$L7B+Vf3w{0sk7$?TDjy`7ye*n3ypDI)i! z^Zy6>n`bhYef-Y)kLi1rX^!si=W3k}Z$Ez2U!48rxXr!q?{W*wW1=di$!76~{^9e^t+r>*U)W{d_haq(50AB~Kdy|KVjXwssy)*o zr&;3n4&Gn$S-b-eE0g-4DXQgy61 ztlV&?W!|jtjO<6ZLE3qurQWb_emD8La`a7}#f!M7P2s*)&vx+V=gtE27@oC<@9)=o zv66`~QSpcmAES^``{n{MA*CKKKLyT-ha)YxIR)KR)hD!^c&Ia{wS{BxBw-JyCk0~X zoSa$$Pjad#7FlqoD=HpZ@q}fPfaRRl%@YI?LyDL@J7mrsiuC9((6Ve)ap6mUsH5T{ iF?Ei^P%{1>>)I(ZLO-3qDa^pYz~JfX=d#Wzp$PygQ_}tb diff --git a/src/spec/images/GraphicsTextSpec/flipped-linux.png b/src/spec/images/GraphicsTextSpec/flipped-linux.png deleted file mode 100644 index 3a643ffc93d3d208f6f70d5afd85d9fdb02241b3..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1874 zcmeAS@N?(olHy`uVBq!ia0y~yU`PRB4mJh`hJr^^Ll_v?B|TjnLn`9l&dJOP36(i| zzS`Jl`R0;cfrr*DVB%_1P+&7ra4BmNiezDCR1{LkN!8wx!KkaSNo#?CFo)LEP!_?a zghR_Vc{p--+(_YEYCJb{x$)(j^D4!yx1_Qy$DweaN9h)!_`EImHI3@HvQB zGL#=@{;;Qr<=?LVPM#%>MUo5mUgl_Pwq2;7As;xk@d#tb-)7YhX8H|<@%1nCwzh=K zQdv-OOSWzGYrTklr+PSA8*Ne*_EniDoIcf(dROGd|5qO_yt%fyMcb$PUN5gl;5QYPOYa<$&o*Q}7YMXu z<$Cj2Twy|;c;SQl>tluVkXT4n0?#p#QUf*w6^woLWa;N%b zwmsEs4rQ~C)IKzkn;L%d!TO_@Cj7g2s=e)Qtf|1Vw}%sKF8J4o_15_w3l&?lM$}~5 zf)|fDFWk%OIr4a};!d9iCXFh7n_Pb9i@PW8sZvYXZfK_P^z3V%%~mhIAxpI$v! zUoX4Pyxe))Qsu9kStpzp7W7mWnlg)_)6G6={?)%B?eA;f+06O7uX+DHUd9EFE{R-o z&AR7wVyfJoSH)K=PJS}o!FBtLq{lxcZcg#2`}MzW$+?~UFx4Z{PJGvC{X=$XhBdtF zIHSbNlXJwzp^_`;ETy92NKgcZ=k_Xgw%h_CN4YgwoRko~jUoHQ3$EkRim7#rymc9?Sbm-7oc3wz&d*x@16RKhr z^X>VMcT6>qdBgg7o#IFKM{hQ=uFKoK!2Y7=95olyTuG;hTBmnUd)r2T%FI{h;MX{f#!oI5OiKl0^ zO*vn@aQ7t}lRJiQynoD!ajAOu=?BwC(>+RN>Bav%RODVW-R_B;aEEQk~ai+mN86UPvRx?>Drn3G-8w;o1)eB!Dze|7oU)`|$YoUdkZtK4Y@fZH( z4i{dyME0+3kl~SKRnE+iS(&)MVgEVbh|S9uUh7@PwCc(AL$}|^oQj_3q;Qk%vOjb7 zlJ#9Kk1yYSsBq=4+h0wWZOadSf1@f<_gd}}*DISxp$?Bd+AQN^H%)q2`%uQKZQaiK zC)d{|vlqR;e34_8EWg?(wT}B)B73>tnSWEv{Ws}?&{DplZ@(B{wawjTz<Hi%f&#(P(eJ|(9#qNi0ZacJKnMq`goaf;!tC5Jd|LHadPedy>&&_>3U%Z|bRs`q={Op1^S)L|;Z@y4yY#Qhp2w4- zScUR?BmNxyd{2tGbGhWa+5b7!cBVH-JMnNbQ@y07xTwczz>$VO>_O^oxw`WIH#0CW OFnGH9xvXk44ofy`glX=O&!2Ze8 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 RDgy%pgQu&X%Q~loCIBAirt<&* diff --git a/src/spec/images/GraphicsTextSpec/line-height-linux.png b/src/spec/images/GraphicsTextSpec/line-height-linux.png deleted file mode 100644 index 43db22a13e30f695b7e0a08c544570e9554e272e..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 3357 zcmeAS@N?(olHy`uVBq!ia0y~yU`PRB4mJh`hJr^^Ll_ts7>k44ofy`glX=O&z;oTx z#WAEJ?rm&lNraf<*Xm*kjn2-<< z$#V4I#l~j#84e;38#Zb1b!l|$=&|Cm>S}6edzZ6!+2zx7R^9O5b$NaK*RTSgujlu? zzq)qU_t4s}MX&bxU;XxPmBtbNK$nMeEZM$U`a1+aKf$f6BcY|}Vf_7|Uv;4ML&GUP zkyFeaBMgj$S~TA7Pg1Vgd(Umh6Y&KK65m}S!|pOZt`0wZyIhv(ZutSb^)mAoYCrh@ z*t$Wh%dCGNOXv!QL~mIeXRV7B=ki>>GG_2^Z_j+p@xp$;#yZ<+7G0$e%WlNY;P}2l zlw;mc$)lI#>?EIE&u@7*d)+4gz3B(CDt@nLE$I#Fxs|*0uZq3upMc%W1-@F%FV8MC z$lu|ZrJS?AE&CLU#I~>PS_wX#g1a@99ruK${NTA?|c#pQ}Yt`y_e>pcg4S_|$-(O%Pi z-1+~_qg!~dSu{P}xs7Xn34^Wr44E&I3lYkA#>YCiV4 z{7~)RAd&O48B3daS9M6unsw>RhxU*||Gwym$h`5GeqdMOQ;z6Y4=Y}Iy7=Tp_AIuZ zI#FR=XX=Hp`5dn=6$V8g4F2DJi(S6G_S)qw&W4UQho?Dz|GIO7u2!?wqKS`end29x zSjxpS^xjtcySFUI^3YMgDQ6-a{vVTaXO-M0^K7g6;VnBuJL8>M1y=e zJ!@|!+k5VRU$E*<(+T^tLd)s6yy=gG`Yf?O({oy@p9syG%*9u-Y)6qqB=@5^zZAIk z*~?yg`u(q($8*~ie_w~(&`w+Y;DTmhlgRm*oOk(`AD#G6Yc@ykX5F0sa|FJZ=l?e? z`LbAe#rdvV3>3U4Bp<7>;*NZr)HJ1Ub(3=zN^2JSZ+iDS&tUz3VH4h?mlhlPZU{-AnDWiyx;Q*!0Qo$FH@E zHy_!SQuB|Mv*dQ`FY9@Yi~mT@Vh;&WRW%j$oaeauf$WE<;!D3bcCXP`Q+Si>QpL0M z6}$H{eN&(BbkKk9l7AZ>xqq?yH9_pp6~S%d@{Su$hnt)f-)ke*c6a)vZ%+(1`Muh> zHe<(^4OgaVB{X~sV4rdQF3a8j=ekZSo}9MEW1+k$zrWj&cP$_9H!rZQ;99gx!Abp{ z`;ixoU*o@DGK+Y;NwnqNu{0ZoyWf`|-jZpt=$4wuJIm>k`|GZJ&an9{Y%y)MI1+3A%u|5zM4prAg=U`#D=sqsKl)ywNXuo)#mWsb+_zbajfd0 zzO0Ox+<+jv{XZ85yhwjAr$3B39S1-`W$+nz65P_Vux&vT|p)X$?^SXb_^6m(iX!Ti3Z z?h5WX+l9ZDpKIQm#K*-~n(_2Xn%SQ%tP45+zOyvgXS?HPyked5qG@a_{=X;vTi^EP zyKwwBqt{Wd_h{!jCS|W(f8MR-)?4>0FP1KvQ2*$q{X5pfziXrS%-HIeWh`Cl)|A4g z`YtKaf#c92q2m&Y9PXPU7qlqo=oIz{HWjGMX7!@B#Edyyi%Q<8-+yd%?Z-}u`2s59 zI?p!r_OML+eCp|A&eV@jkN!BpUdOjHElW$;@yVW|p9(EUr(a*i>iP8e;wGNh#z~pn z59PM;95l9Lw@hDUTVk|T>&Ur3LQI{HJLWW~q{ko5apI}e z{4Mf^rU9#EEVp~t7#yiuZhL`q+1bMjZkO+R6RiJJ`?-Jn@3y5JbM`ZHWG}pbmwVcE zH^x~8cMeYvg|eeB`2NgcjuH0;_O{L#cJA$^Zvq3?^k`zc=f^7>(ukW z`*Cl=t<%J|R*Sx|7Ujr%_)XhH|BqLRqrYX=lCu><-ntVz#Z{lv@ zgPZMIKdybP@_JrO{D~c%bNlDKRZUiDziitae(1wHh8BMdkMsPmzs+mz*xC4LS=N>1 z`W%eYH>dr5_IWq!GF|5-bwUS}MavKGc_ubvTb%aqkcq)x-P8KpQqO8g+~3)DY~zgs zLeq6V-@5Z)a{J1ve`hy@++%&r9&Y%w;mE#-Re9}&w;5i>onN3;u|AIZ@owgX$iLz* z-~a30w(#M#)}Mkd*Pef$-yQJf)r%?2%5@G!OqVu&o7Tg6Qgz?wjcJE_zdrpPxFP=D z@ku2=Wwz~U?VO?$dn7t|Pl8m*{du}~uU)B=FI8Q>H)Z1)0kQe=Cl!xKNWR#}{IHCD zMed9r&I|Z17avZUmSW{x)G41;EWx|@U*EEG)eHZA4jX!=l_{5yrksK zsfzgz*QYN|mOFK$_DRIL>`#Y(3aZSMSGoAy-R~m1UJd`U?QKrquU1~Ta%<(zd!}z4 ztsdmCoK&sr*|4nd{-N@pYO`88Pfw5dXtGsRb8?kYzR#NtyOMuxzF_4);hp`mrU3Pe zYj)4xU$fz#+REU-QjV+VO`iAHa82T?Q+m8`8++jI3nef1z2SS^Wq7<@p(xHWOg#9; zvqkb%8}}GV9V=(|YUV2W&+v8o`Tpol5jB;aogtZROPc5R6mGIsk$2qiH~G;=#f~}Q zeW3zIT+gR`G)bReYkBiF`|dZ5|2LTnhPo&G*s$HiIijZWCD)-Yf1S*&k58@Scl-R= z(akmn=`M9_mR%%#TYNX_`!O?tXz(NGX2)+O&d!8-*8>} zIP}c6={FO$N;zKosFkMeVHRO2tP&Zw&~CR$7Pr<_ZWWi*M?Zr%i%9KRF*C%Cd&dkj z{`O;$T>-!4Grr0vT~M@}5HWFcN{SlSq;>j68_)jXJ`@o>VQE}~**ts8^-60k%CA~Y znNZc`E*T_!{)bE{{~4Eyn|@!idpfUA|I-YPLqX9Kw#Fqan`du1DdVDkxMo-Uj4Me@ z6RLWbM8)i~oA5YJKJ<)(UUj>ksfzOJ2{yz4jJsl3Cz z=t+js;?%X_63J?@=jX3c*qq<|@9@2otUK2?T|4F#=Bsh7|NdHqmshxLeif#E{d1D@ z(JYhBI)Mch7ZFWc3xb};&UQId>Qx>VywBd^OnPZ>TpNIBjHLs{lF{=GdLZC3HhC5nRqyB$4Av4`qis%&foF))RM}VI|N(yebKzaedgF__gmA~ z21mSTFAor1``j<<@MZDC{ndx|Oxz=JOgz*t#c=9$gNoOBFfN4^4g0qTt0-xKEGe zq0bJXIRY-7is!DkD$L;wZxU|OFg)^emq3g0L$3lS0o68(c=4tJwHQu6jzvcVp1*by gIM48Du6JYis9U@Q)DcVbv~PUa;8g93x6 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

w%oAF^ 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 diff --git a/src/spec/images/GraphicsTextSpec/multi-text-linux.png b/src/spec/images/GraphicsTextSpec/multi-text-linux.png deleted file mode 100644 index 87a7fc4dcd291656c7a4d7e3ea369fb0de4097dd..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2823 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 diff --git a/src/spec/images/GraphicsTextSpec/reuse-font-linux.png b/src/spec/images/GraphicsTextSpec/reuse-font-linux.png deleted file mode 100644 index d42d5abdcc3addb422231a8d2987d3dfa7cf7238..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1711 zcmeAS@N?(olHy`uVBq!ia0y~yU`PRB4mJh`hJr^^Ll_ts7>k44ofy`glX=O&z?SLh z;uum9_jXogPDrT4(eu@tORRF!^<7=2d1VRkuJE`rVS$jCxX4n0#ubJWH3Y>~b~vo! z;L=J`I5Hz4hC_>KQMSxbCmS#oE~qcNOz>{o*@$YvUU$%U55k4W|g?PWr07{BZDJE}y0M z^e*1GC-KrnW})n9LHjy}m)Bc#*R?IL64ZJ6cY&_|L0#?%J#7!>e$fir zsCL)zoT-|iO>0~Kyo_>wLG#8ZyVkWNXPoT%`%%^@UT=5CNv`*i?JpYFe(;NA3+~ij zY`vk9ani%8AItQF|9dYF=E$kyd|46VkZHF?*mw6m;p$0C_XJ&e(R3PmH}di{^Nm|NRkO@;LJtdC?~(qNeQe>EU$1tJG`$nczMra*vE9M!dw)&C&OJi&UbQB@%-${0A)@g8@U8Dw8xzxapPA>q zaE8vz{#j+~UA`Q69`H7=LVZ8u)v#j@Ju(3=@9zD&I{jcu`N7(9-}Z{f>U>HYGVM;e z+4Q{lr)%(A>!FnO^(TUN-R3~qQJQ|vlw5ihA&8YvDZUAD)36W z!IpHE|I3Rfa$P@c_k(XnZS6u^U3IBGWl`?Km9G~s+J51B{=%m>>?+jt1v@XTJC=W6 zboTD=`&134RxL1RW4^fae6suZj(opc+f{=jEo*|OcX^%t;c>SrWBzibIt?}BGxO{; zC_KuSeTMPt}_yi^&=1f$WTdXiQ$Mv&*{KB6f z^i=-*ci1R$@X_o3Nr}RVZzI3nFYbM^>)gt7d$%rZDS1A#s^E6g5&wT|ze5)%zKm=w z*&}&z{`SRRzXVJdQa6`?*#h?K^X3>*Q0v_|p&E z`kl4I&0h1L{_b_fX3y_g$Ol{+i;Bx1~GO_te}wR=1FM z)9a$`mfyWrI&jr4Tjv|>y{7)|=M8aYEaxU(E=||ltykXtdG!>oB^T0P-FofR*!y`w z#M?(xf()ZKpNlJttrL45t}E&B@Z6QH#o}+jDy`7EQ-0M!chlA>K z@mDj6TMws~&A2Ma6IuH6_Uw9YXNO&%eQcQzCyD0kth)B7Z1O^nRj2PqCF}AqzFcQq zn!Ud9!}|4(n?8zo<2)Wd`$+Ck0NJaSbaf2e|?NSdXS%t5NybP|v`?z~JfX=d#Wz Gp$P!`Bo`w9 diff --git a/src/spec/images/GraphicsTextSpec/rotated-linux.png b/src/spec/images/GraphicsTextSpec/rotated-linux.png deleted file mode 100644 index 962130c3698a6628ac92b022c85fda145ce72486..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1975 zcmeAS@N?(olHy`uVBq!ia0y~yU`PRB4mJh`hJr^^Ll_ts7>k44ofy`glX=O&z+UL- z;uum9_jYb&L9naL@%@#aRZB82Y3qJhII%Q|k>7!Du3(#>ql=4%dnn7&DT^JRPT1VR z;d*775|2Vr=mNf`CS#=_8IdPJjsY?SIzb{H{VKV)RC4*A=PsC*nQ?hp?ai}qe!utq z_V)evee>_0{k`}5?byheqCW0F3)~nb*`0W~A91idiSzTd7|G=@Z9F=^aqa8K6TF52 zPx;!;2)WH($NQ~)r=oXD;+!o~r|NGXkW6da6VcwWhIPe@8pc!EZxv=JCCE);j{ZJ* zLZq``(Kh~&oz4u?*Bn&xtW+#^;4!|m;7mUI*XNHJcQPM4x%xrJPFD94#*}RWEdQ_Z zUi)Fp@pGrS!uG?r{;FL0ecZ9MWW$tQW;eu&9k{}LT~e+wX?%LGY@S>DN5ZEwvcvOq zi*giy@+Yng^Yd;Wejd;J|IhXm+dKC!*4a`zlctCpvAgUqGg)-mNI}0x+3K$3p-0Q! zDjuF>m&{Z0+1xSg-M{$4EMAQmE8dO9mnhUSDcQ~9e|nW~d*ht8!b{a1 zvu8P<v+BO|nkg>gM(jr>Y!W#*{n0`zlRLI5wiCNA z3Eo~XdvEWY={sH(|hgqu}BY)L0f8OA~@a9aGqrKNy7*h0H z)>ZD#>M&AU>yo|C%=%_ub1=G>s&?S_Ul>aF8vp9>gUbMnl81p?%6+Qsi*5S z*R@nCJZ0vqP+kA(_QJTSpUV}WHQqT@wK9zNsD0_dHLfAQxazatPOW{`Sh44{g0xn2 zob%1imJ_C~TzGdP&kfNy&PVT^8abczt!iR!n_{BzKac`?|Ot|?*hq6*7a6KQ)<)`pC-t4c!#z2!^Cg4*>9Eh>hnGgW!_v(=f8g8 zShDDJrNn&?_Z%-XcBNLPU*Cln-n11|T>iV7MX63-u-f;^s;NOc9&hG-)~@6H%1Pt@ z8y_R@Rs4|;*@XfwzEsk(ifbtg&I-NMe7?)Hko64n#&5s)MBn~zP^)`QYVLs#6 z>71d5BZaeXYFstuU(&|aX3o1o7$YjJYcvGGFMj>*3wq za-qIlOAoHURg+M6LMzJZ?&H5ZManF;9&PY;aJd$(vU(yY?3Z%Rwt4+VL}7-KV9`4D zC+2s%IW`m+@VBr|eEnFNJxG45ipJ?i4~3#yp8|!if! zt&I6}lJB$ak>$IWe|XfuaOin^z?Dru{s?p>bgcXEQ*jF8!_Uqd%!i)0UtnuF&%dyn zW4^qTIKQ2Ji;Pp;_4PLP4lfug2nw1$+ z`}wB6)l+_Rp`fMK^iq0sP{@HAe#J-avjeQslyBY+xYO%fw^{UzevW!|dq$a08Qpz2}UFp~3t~-p^bp*J7`2D+2=qgQu&X%Q~lo FCIHuwgQ5Tc diff --git a/src/spec/images/GraphicsTextSpec/rotated-right-linux.png b/src/spec/images/GraphicsTextSpec/rotated-right-linux.png deleted file mode 100644 index a098f41d48a1434e7cb434f76ce566cd7a2dbf66..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1438 zcmeAS@N?(olHy`uVBq!ia0y~yU`PRB4mJh`hJr^^Ll_ts7>k44ofy`glX=O&z#8G{ z;uum9_jYb>PH?EqvH7?2vUiuh-PUKgNKMCa5u2=Air}9Giw?R3bP5_U&w0U-QoPUg zii_j152cNb7FT{u+i5Ag=$K@$ps=b$WWXbr<_0O@fW*|-x7NjOU$=JW^^6&>PseVL z`zJr|cjjr^=k@b!_S<~FQ~ZACN~5jIl-cBxWCA!`c({Ez8c#fOR5(;2z|rVY>@Y*_ zoFa?T8OFq-83Ig#&l(IYeK;C9iXCRisI@q>SStAN2|Fnqk`YjA=TsC()zpIMAfI{3Yh z>3ZaAolrLY*jkx+g)H-Ku}!&i-%Vlio4+fHE;hxztuH@pC6c?k-O|r#(N8;`JD1u# z67^$dZx{4XYn*d)lbB$7{3*pL8(7bozfO3$Z<0gMF4Ku@UOW#sC4abco8h;6`GGgZ zeJhvoJX3t_BI)yQ#geXXjM>?eP9LrZbw#c9`vR zP;g`D+;!(e*gL0+W9Lu&{$lo|b{mUfG{e59>yuu5V&3pJn&Wr-)POc!mLwK|Tprc7 zgFmYm#_c;}ds(2g%7meB+tw3yb)G?zbFLV>o|I{x*X`VY*?m*bc8JVx`};SvW6C_254ZdiEN$3-=C6O4`~HWn?|%0O%kFaM{9(Ac z|7^?WwX^=u%WT#E!+CG&*^bDz2NmD*BKTsDTB_8}{`&n*=Bk#zkDs3Sn{;u;R<|=& zD{LcV*8C6(&bH=o*}wMX_8uQ=#?SHMD!K+GHytDD9xR^xCDw0qy2<_Sh`a~$*?T#~ zy8i2*^|bZfJh@bQ*4@^|*|!aYJ}tj?=Ifc_6IPb7zi)^C6e_CQ%W;kQ`iDtV8Q&kD zBBN!`kzcA@)OXhD+{MTb`g!uKDG#oNhiu)3b4H*9+s}IVp2YT zTb6$1hE|6jhDG;MMfdEHvvfc8m?=;{{oYkyjg{Hz0?G|L=I>?yxqEfO-*2yWI52fv z8CZPR7Rj%e=+MLPD0(CJ!%dGh?(Ab!i$A!+``U>w@efw6Zh!llb;J9elfkCGs*=0W zv0|~jrMtfCiap%doIeX}{%vUU*?orp-1bFlXD?*=%yEQ6;gy7;H^)KNxdHEYCGqtN*_7gTFH-y|V8AcWXI=D%a%g9H%_O?j*+gzf%xUZm5u}a;jBkdali{e)sTf z5ANp^JeNJmThp|-R95GH_>$0>4wp9R7OH>$y!v6r%EqT3L^DIxCTz*^zH_qrdfD5c zssH0bqo#7I=-w78?-KiVsQA8GZhGg}-IWGk#Tf%PzYFAW*&g~!>YMGhxZ9VdPs{n; zYMih9;&bt#wN2N{U#(jB&aSiEKylX_<8^|KDHpQq{69}k{&zrE-9TAuB5Uwl`r aXAZhw?EmVOb_D|i1B0ilpUXO@geCyr&XGz0 diff --git a/src/spec/images/GraphicsTextSpec/shadow-linux.png b/src/spec/images/GraphicsTextSpec/shadow-linux.png deleted file mode 100644 index 65a52bc42c9a8cff116021424ffc45dcbdbbb412..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 3853 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 { let actor: ex.Actor; @@ -9,7 +8,6 @@ describe('Action', () => { let scene: ex.Scene; beforeEach(async () => { - jasmine.addMatchers(ExcaliburMatchers); engine = TestUtils.engine({ width: 100, height: 100 }); actor = new ex.Actor(); @@ -21,7 +19,7 @@ describe('Action', () => { const clock = engine.clock as ex.TestClock; clock.step(100); - spyOn(scene, 'draw').and.callThrough(); + vi.spyOn(scene, 'draw'); engine.stop(); }); @@ -106,11 +104,11 @@ describe('Action', () => { expect(actor.pos).toBeVector(ex.vec(0, 0)); scene.update(engine, 0); - expect(sequence.isComplete()).toBeTrue(); + expect(sequence.isComplete()).toBe(true); // Can re-run a sequence actor.actions.runAction(sequence); - expect(sequence.isComplete()).toBeFalse(); + expect(sequence.isComplete()).toBe(false); }); it('can be stopped', () => { @@ -162,7 +160,7 @@ describe('Action', () => { expect(actor2.pos).toBeVector(ex.vec(0, 0)); scene.update(engine, 0); - expect(clonedSequence.isComplete()).toBeTrue(); + expect(clonedSequence.isComplete()).toBe(true); }); }); @@ -182,10 +180,10 @@ describe('Action', () => { const blink = new ex.Blink(actor, 200, 200); blink.update(200); blink.update(200); - expect(blink.isComplete()).toBeTrue(); + expect(blink.isComplete()).toBe(true); blink.reset(); - expect(blink.isComplete()).toBeFalse(); + expect(blink.isComplete()).toBe(false); }); it('can blink at a frequency forever', () => { @@ -222,7 +220,7 @@ describe('Action', () => { const color = ex.Color.Azure; const sut = new ex.Actor({ color }); - expect(sut.color).not.toBe(color, 'Color is not expected to be same instance'); + expect(sut.color, 'Color is not expected to be same instance').not.toBe(color); }); it('is cloned from property setter', () => { @@ -231,7 +229,7 @@ describe('Action', () => { sut.color = color; - expect(sut.color).not.toBe(color, 'Color is not expected to be same instance'); + expect(sut.color, 'Color is not expected to be same instance').not.toBe(color); }); }); @@ -241,7 +239,7 @@ describe('Action', () => { expect(scene.actors.length).toBe(1); actor.actions.die(); scene.update(engine, 100); - expect(actor.active).toBeFalse(); + expect(actor.active).toBe(false); expect(scene.actors.length).toBe(0); }); @@ -285,10 +283,10 @@ describe('Action', () => { const delay = new ex.Delay(1000); delay.update(1000); - expect(delay.isComplete()).toBeTrue(); + expect(delay.isComplete()).toBe(true); delay.reset(); - expect(delay.isComplete()).toBeFalse(); + expect(delay.isComplete()).toBe(false); }); it('can be stopped', () => { @@ -304,18 +302,19 @@ describe('Action', () => { expect(actor.pos.x).toBe(0); }); - it('can be a promise', (done) => { - const spy = jasmine.createSpy(); - actor.actions.delay(1000); - actor.actions.callMethod(spy); - actor.actions.toPromise().then(() => { - expect(spy).toHaveBeenCalled(); - done(); - }); - scene.update(engine, 1000); - scene.update(engine, 0); - scene.update(engine, 0); - }); + it('can be a promise', () => + new Promise((done) => { + const spy = vi.fn(); + actor.actions.delay(1000); + actor.actions.callMethod(spy); + actor.actions.toPromise().then(() => { + expect(spy).toHaveBeenCalled(); + done(); + }); + scene.update(engine, 1000); + scene.update(engine, 0); + scene.update(engine, 0); + })); }); describe('moveBy', () => { @@ -323,22 +322,22 @@ describe('Action', () => { const moveBy = new ex.MoveBy(actor, 100, 0, 100); actor.actions.runAction(moveBy); scene.update(engine, 1000); - expect(moveBy.isComplete(actor)).toBeTrue(); + expect(moveBy.isComplete(actor)).toBe(true); moveBy.reset(); actor.pos = ex.vec(0, 0); - expect(moveBy.isComplete(actor)).toBeFalse(); + expect(moveBy.isComplete(actor)).toBe(false); }); it('(with options) can be reset', () => { const moveBy = new ex.MoveByWithOptions(actor, { offset: ex.vec(100, 0), duration: 100 }); actor.actions.runAction(moveBy); scene.update(engine, 1000); - expect(moveBy.isComplete(actor)).toBeTrue(); + expect(moveBy.isComplete(actor)).toBe(true); moveBy.reset(); actor.pos = ex.vec(0, 0); - expect(moveBy.isComplete(actor)).toBeFalse(); + expect(moveBy.isComplete(actor)).toBe(false); }); it('can be moved to a location by a certain time (x,y) overload', () => { @@ -424,11 +423,11 @@ describe('Action', () => { const moveTo = new ex.MoveToWithOptions(actor, { pos: ex.vec(100, 0), duration: 500 }); actor.actions.runAction(moveTo); scene.update(engine, 1000); - expect(moveTo.isComplete(actor)).toBeTrue(); + expect(moveTo.isComplete(actor)).toBe(true); moveTo.reset(); actor.pos = ex.vec(0, 0); - expect(moveTo.isComplete(actor)).toBeFalse(); + expect(moveTo.isComplete(actor)).toBe(false); }); it('can be moved to a location at a speed (x,y) overload', () => { @@ -529,11 +528,11 @@ describe('Action', () => { it('can be reset', () => { const easeTo = new ex.EaseBy(actor, 100, 0, 100, ex.EasingFunctions.EaseInOutCubic); easeTo.update(1000); - expect(easeTo.isComplete()).toBeTrue(); + expect(easeTo.isComplete()).toBe(true); easeTo.reset(); actor.pos = ex.vec(0, 0); - expect(easeTo.isComplete()).toBeFalse(); + expect(easeTo.isComplete()).toBe(false); }); it('can be eased to a location given an easing function (x,y) overload', () => { actor.pos = ex.vec(100, 100); @@ -596,11 +595,11 @@ describe('Action', () => { it('can be reset', () => { const easeTo = new ex.EaseTo(actor, 100, 0, 100, ex.EasingFunctions.EaseInOutCubic); easeTo.update(1000); - expect(easeTo.isComplete()).toBeTrue(); + expect(easeTo.isComplete()).toBe(true); easeTo.reset(); actor.pos = ex.vec(0, 0); - expect(easeTo.isComplete()).toBeFalse(); + expect(easeTo.isComplete()).toBe(false); }); it('can be eased to a location given an easing function (x,y) overload', () => { expect(actor.pos).toBeVector(ex.vec(0, 0)); @@ -676,7 +675,7 @@ describe('Action', () => { describe('repeat', () => { it('can repeat X times', () => { - const repeatCallback = jasmine.createSpy('repeat'); + const repeatCallback = vi.fn(); actor.actions.repeat((ctx) => { ctx.callMethod(repeatCallback); }, 11); @@ -688,7 +687,7 @@ describe('Action', () => { }); it('recalls the builder every repeat', () => { - const repeatCallback = jasmine.createSpy('repeat'); + const repeatCallback = vi.fn(); actor.actions.repeat((ctx) => { ctx.delay(200); repeatCallback(); @@ -702,7 +701,7 @@ describe('Action', () => { }); it('can repeat moveBy X times', () => { - const repeatCallback = jasmine.createSpy('repeat'); + const repeatCallback = vi.fn(); actor.actions.repeat((ctx) => { ctx.moveBy(10, 0, 10); // move 10 pixels right at 10 px/sec ctx.callMethod(repeatCallback); @@ -719,7 +718,7 @@ describe('Action', () => { }); it('can repeat 1 time', () => { - const repeatCallback = jasmine.createSpy('repeat'); + const repeatCallback = vi.fn(); actor.actions.repeat((ctx) => { ctx.callMethod(repeatCallback); }, 1); @@ -835,7 +834,7 @@ describe('Action', () => { }); it('recalls the builder every repeat', () => { - const repeatCallback = jasmine.createSpy('repeat'); + const repeatCallback = vi.fn(); actor.actions.repeatForever((ctx) => { ctx.delay(200); repeatCallback(); @@ -1045,21 +1044,21 @@ describe('Action', () => { const rotateBy = new ex.RotateBy(actor, Math.PI / 2, Math.PI / 2); actor.actions.runAction(rotateBy); scene.update(engine, 1000); - expect(rotateBy.isComplete()).toBeTrue(); + expect(rotateBy.isComplete()).toBe(true); rotateBy.reset(); actor.rotation = 0; - expect(rotateBy.isComplete()).toBeFalse(); + expect(rotateBy.isComplete()).toBe(false); }); it('(with options) can be reset', () => { const rotateBy = new ex.RotateByWithOptions(actor, { angleRadiansOffset: Math.PI / 2, duration: 500 }); actor.actions.runAction(rotateBy); scene.update(engine, 1000); - expect(rotateBy.isComplete()).toBeTrue(); + expect(rotateBy.isComplete()).toBe(true); rotateBy.reset(); actor.rotation = 0; - expect(rotateBy.isComplete()).toBeFalse(); + expect(rotateBy.isComplete()).toBe(false); }); it('can be rotated to an angle by a certain time via ShortestPath (default)', () => { expect(actor.rotation).toBe(0); @@ -1218,21 +1217,21 @@ describe('Action', () => { const scaleTo = new ex.ScaleTo(actor, 2, 2, 1, 1); actor.actions.runAction(scaleTo); scene.update(engine, 1000); - expect(scaleTo.isComplete()).toBeTrue(); + expect(scaleTo.isComplete()).toBe(true); scaleTo.reset(); actor.scale = ex.vec(1, 1); - expect(scaleTo.isComplete()).toBeFalse(); + expect(scaleTo.isComplete()).toBe(false); }); it('(with options) can be reset', () => { const scaleTo = new ex.ScaleToWithOptions(actor, { scale: ex.vec(2, 2), duration: 500 }); actor.actions.runAction(scaleTo); scene.update(engine, 1000); - expect(scaleTo.isComplete()).toBeTrue(); + expect(scaleTo.isComplete()).toBe(true); scaleTo.reset(); actor.scale = ex.vec(1, 1); - expect(scaleTo.isComplete()).toBeFalse(); + expect(scaleTo.isComplete()).toBe(false); }); it('can be scaled at a speed (x,y) overload', () => { expect(actor.scale.x).toBe(1); @@ -1331,12 +1330,12 @@ describe('Action', () => { const scaleTo = new ex.ScaleTo(actor, 2, 1, 1, 1); actor.actions.runAction(scaleTo); - expect(scaleTo.isComplete()).toBeFalse(); + expect(scaleTo.isComplete()).toBe(false); scene.update(engine, 1000); expect(actor.scale.x).toBe(2); expect(actor.scale.y).toBe(1); - expect(scaleTo.isComplete()).toBeTrue(); + expect(scaleTo.isComplete()).toBe(true); }); }); @@ -1345,21 +1344,21 @@ describe('Action', () => { const scaleBy = new ex.ScaleBy(actor, 1, 1, 1); actor.actions.runAction(scaleBy); scene.update(engine, 1000); - expect(scaleBy.isComplete()).toBeTrue(); + expect(scaleBy.isComplete()).toBe(true); scaleBy.reset(); actor.scale = ex.vec(1, 1); - expect(scaleBy.isComplete()).toBeFalse(); + expect(scaleBy.isComplete()).toBe(false); }); it('(with options) can be reset', () => { const scaleBy = new ex.ScaleByWithOptions(actor, { scaleOffset: ex.vec(1, 1), duration: 500 }); actor.actions.runAction(scaleBy); scene.update(engine, 1000); - expect(scaleBy.isComplete()).toBeTrue(); + expect(scaleBy.isComplete()).toBe(true); scaleBy.reset(); actor.scale = ex.vec(1, 1); - expect(scaleBy.isComplete()).toBeFalse(); + expect(scaleBy.isComplete()).toBe(false); }); it('can be scaled by a certain time (x,y) overload', () => { @@ -1486,11 +1485,11 @@ describe('Action', () => { scene.update(engine, 1000); scene.update(engine, 1000); - expect(meet.isComplete()).toBeTrue(); + expect(meet.isComplete()).toBe(true); meet.reset(); actor.pos = ex.vec(0, 0); - expect(meet.isComplete()).toBeFalse(); + expect(meet.isComplete()).toBe(false); }); it('can meet another actor', () => { @@ -1519,11 +1518,11 @@ describe('Action', () => { it('can be reset', () => { const fade = new ex.Fade(actor, 0, 1000); fade.update(1000); - expect(fade.isComplete()).toBeTrue(); + expect(fade.isComplete()).toBe(true); fade.reset(); actor.graphics.opacity = 1; - expect(fade.isComplete()).toBeFalse(); + expect(fade.isComplete()).toBe(false); }); it('can go from 1 from 0', () => { @@ -1573,28 +1572,28 @@ describe('Action', () => { describe('events', () => { it('emits actionstart event', () => { - const spy = jasmine.createSpy(); + const spy = vi.fn(); actor.actions.moveTo(20, 0, 20); actor.on('actionstart', spy); scene.update(engine, 500); scene.update(engine, 500); expect(spy).toHaveBeenCalledTimes(1); - expect(spy).toHaveBeenCalledWith(jasmine.objectContaining({ target: actor, action: jasmine.any(ex.MoveTo) })); + expect(spy).toHaveBeenCalledWith(expect.objectContaining({ target: actor, action: expect.any(ex.MoveTo) })); }); it('emits actioncomplete event', () => { - const spy = jasmine.createSpy(); + const spy = vi.fn(); actor.actions.moveTo(20, 0, 20); actor.on('actioncomplete', spy); for (let i = 0; i < 10; i++) { scene.update(engine, 200); } expect(spy).toHaveBeenCalledTimes(1); - expect(spy).toHaveBeenCalledWith(jasmine.objectContaining({ target: actor, action: jasmine.any(ex.MoveTo) })); + expect(spy).toHaveBeenCalledWith(expect.objectContaining({ target: actor, action: expect.any(ex.MoveTo) })); }); it('emits actioncomplete with an action with ids', () => { - const spy = jasmine.createSpy(); + const spy = vi.fn(); // actor.actions.moveTo(20, 0, 20); const moveTo = new ex.MoveTo(actor, 20, 0, 20); const moveTo2 = new ex.MoveTo(actor, 20, 0, 20); @@ -1604,14 +1603,14 @@ describe('Action', () => { scene.update(engine, 200); } expect(spy).toHaveBeenCalledTimes(1); - expect(spy).toHaveBeenCalledWith(jasmine.objectContaining({ target: actor, action: moveTo })); + expect(spy).toHaveBeenCalledWith(expect.objectContaining({ target: actor, action: moveTo })); expect(moveTo.id).not.toEqual(moveTo2.id); expect(moveTo2.id).toEqual(moveTo.id + 1); }); it('emits actionstart and actioncomplete events for each action in a repeat', () => { - const startSpy = jasmine.createSpy(); - const completeSpy = jasmine.createSpy(); + const startSpy = vi.fn(); + const completeSpy = vi.fn(); actor.actions.repeat((ctx) => ctx.moveTo(20, 0, 20).moveTo(0, 0, 20), 1); actor.on('actionstart', startSpy); actor.on('actioncomplete', completeSpy); @@ -1620,17 +1619,17 @@ describe('Action', () => { scene.update(engine, 500); } - const startCalls = startSpy.calls.all(); + const startCalls = startSpy.mock.calls; expect(startSpy).toHaveBeenCalledTimes(3); - expect(startCalls[0].args[0]).toEqual(jasmine.objectContaining({ target: actor, action: jasmine.any(ex.Repeat) })); - expect(startCalls[1].args[0]).toEqual(jasmine.objectContaining({ target: actor, action: jasmine.any(ex.MoveTo) })); - expect(startCalls[2].args[0]).toEqual(jasmine.objectContaining({ target: actor, action: jasmine.any(ex.MoveTo) })); + expect(startCalls[0][0]).toEqual(expect.objectContaining({ target: actor, action: expect.any(ex.Repeat) })); + expect(startCalls[1][0]).toEqual(expect.objectContaining({ target: actor, action: expect.any(ex.MoveTo) })); + expect(startCalls[2][0]).toEqual(expect.objectContaining({ target: actor, action: expect.any(ex.MoveTo) })); - const completeCalls = completeSpy.calls.all(); + const completeCalls = completeSpy.mock.calls; expect(completeSpy).toHaveBeenCalledTimes(3); - expect(completeCalls[0].args[0]).toEqual(jasmine.objectContaining({ target: actor, action: jasmine.any(ex.MoveTo) })); - expect(completeCalls[1].args[0]).toEqual(jasmine.objectContaining({ target: actor, action: jasmine.any(ex.MoveTo) })); - expect(completeCalls[2].args[0]).toEqual(jasmine.objectContaining({ target: actor, action: jasmine.any(ex.Repeat) })); + expect(completeCalls[0][0]).toEqual(expect.objectContaining({ target: actor, action: expect.any(ex.MoveTo) })); + expect(completeCalls[1][0]).toEqual(expect.objectContaining({ target: actor, action: expect.any(ex.MoveTo) })); + expect(completeCalls[2][0]).toEqual(expect.objectContaining({ target: actor, action: expect.any(ex.Repeat) })); }); }); }); diff --git a/src/spec/ActorSpec.ts b/src/spec/vitest/ActorSpec.ts similarity index 89% rename from src/spec/ActorSpec.ts rename to src/spec/vitest/ActorSpec.ts index 00242b42..fce99ed1 100644 --- a/src/spec/ActorSpec.ts +++ b/src/spec/vitest/ActorSpec.ts @@ -1,6 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; -import { PhysicsWorld } from '../engine/Collision/PhysicsWorld'; + +import { PhysicsWorld } from '../../engine/Collision/PhysicsWorld'; import { TestUtils } from './util/TestUtils'; describe('A game actor', () => { @@ -12,11 +12,6 @@ describe('A game actor', () => { let collisionSystem: ex.CollisionSystem; let actionSystem: ex.ActionsSystem; - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - beforeEach(async () => { engine = TestUtils.engine({ width: 100, @@ -37,8 +32,8 @@ describe('A game actor', () => { engine.addScene('test', scene); await engine.goToScene('test'); - spyOn(scene, 'draw').and.callThrough(); - spyOn(scene, 'debugDraw').and.callThrough(); + vi.spyOn(scene, 'draw'); + vi.spyOn(scene, 'debugDraw'); await engine.start(); const clock = engine.clock as ex.TestClock; @@ -677,7 +672,7 @@ describe('A game actor', () => { it('can be removed from the scene', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); // attempt removing before adding new ex.Actor({ name: 'not-in-scene' }).kill(); expect(logger.warn).toHaveBeenCalledWith('Cannot kill actor named "not-in-scene", it was never added to the Scene'); @@ -707,10 +702,10 @@ describe('A game actor', () => { await engine.goToScene('test'); engine.screen.setCurrentCamera(engine.currentScene.camera); - spyOn(scene, 'draw').and.callThrough(); - spyOn(scene, 'debugDraw').and.callThrough(); + vi.spyOn(scene, 'draw'); + vi.spyOn(scene, 'debugDraw'); - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); scene.add(actor); actor.kill(); @@ -739,7 +734,7 @@ describe('A game actor', () => { it('is drawn on opacity 0', () => { scene.clear(false); const invisibleActor = new ex.Actor({ name: 'Invisible', pos: ex.vec(50, 50), width: 100, height: 100 }); - invisibleActor.graphics.onPostDraw = jasmine.createSpy('draw'); + invisibleActor.graphics.onPostDraw = vi.fn(); invisibleActor.graphics.opacity = 0; scene.add(invisibleActor); scene.update(engine, 100); @@ -780,14 +775,14 @@ describe('A game actor', () => { scene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/ActorSpec/zindex-blue-top.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/ActorSpec/zindex-blue-top.png'); green.z = 2; blue.z = 1; scene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/ActorSpec/zindex-green-top.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/ActorSpec/zindex-green-top.png'); }); it('can have a graphic drawn at an opacity', async () => { @@ -807,7 +802,8 @@ describe('A game actor', () => { const clock = engine.clock as ex.TestClock; clock.step(1); - const image = new ex.ImageSource('src/spec/images/SpriteSpec/icon.png'); + const image = new ex.ImageSource('/src/spec/assets/images/SpriteSpec/icon.png'); + await image.load(); const sprite = new ex.Sprite({ image, @@ -832,11 +828,11 @@ describe('A game actor', () => { scene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/SpriteSpec/opacity.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/SpriteSpec/opacity.png'); }); // it('will tick animations when drawing switched', async () => { - // const texture = new ex.ImageSource('src/spec/images/SpriteSpec/icon.png'); + // const texture = new ex.ImageSource('/src/spec/assets/images/SpriteSpec/icon.png'); // await texture.load(); // const sprite = new ex.Sprite({ // image: texture, @@ -859,7 +855,7 @@ describe('A game actor', () => { // height: 200 // }); - // spyOn(animation, 'tick').and.callThrough(); + // spyOn(animation, 'tick') // const actor = new ex.Actor({ // pos: new ex.Vector(engine.halfCanvasWidth, engine.halfCanvasHeight), @@ -874,7 +870,7 @@ describe('A game actor', () => { it('will tick animations on update', async () => { scene.clear(); - const texture = new ex.ImageSource('src/spec/images/SpriteSpec/icon.png'); + const texture = new ex.ImageSource('/src/spec/assets/images/SpriteSpec/icon.png'); await texture.load(); const sprite = new ex.Sprite({ image: texture, @@ -897,7 +893,7 @@ describe('A game actor', () => { height: 200 }); - spyOn(animation, 'tick').and.callThrough(); + vi.spyOn(animation, 'tick'); const actor = new ex.Actor({ name: 'Animation', @@ -912,8 +908,8 @@ describe('A game actor', () => { }); it('will receive predraw/postdraw', () => { - const predraw = jasmine.createSpy('predraw'); - const postdraw = jasmine.createSpy('postdraw'); + const predraw = vi.fn(); + const postdraw = vi.fn(); const actor = new ex.Actor({ name: 'events', @@ -929,8 +925,8 @@ describe('A game actor', () => { scene.add(actor); scene.draw(engine.graphicsContext, 100); - expect(predraw).toHaveBeenCalledOnceWith(new ex.PreDrawEvent(engine.graphicsContext, 100, actor)); - expect(postdraw).toHaveBeenCalledOnceWith(new ex.PostDrawEvent(engine.graphicsContext, 100, actor)); + expect(predraw).toHaveBeenCalledExactlyOnceWith(new ex.PreDrawEvent(engine.graphicsContext, 100, actor)); + expect(postdraw).toHaveBeenCalledExactlyOnceWith(new ex.PostDrawEvent(engine.graphicsContext, 100, actor)); }); it('can detect containment off of child actors', () => { @@ -942,19 +938,19 @@ describe('A game actor', () => { child.addChild(child2); // check reality - expect(parent.contains(550.01, 50.01)).withContext('(550.1, 50.1) is top-left of parent should be contained').toBeTruthy(); - expect(parent.contains(650, 150)).withContext('(650, 150) is bottom-right of parent should be contained').toBeTruthy(); + expect(parent.contains(550.01, 50.01), '(550.1, 50.1) is top-left of parent should be contained').toBeTruthy(); + expect(parent.contains(650, 150), '(650, 150) is bottom-right of parent should be contained').toBeTruthy(); // in world coordinates this should be false - expect(child.contains(50, 50)).withContext('(50, 50) world coords is outside child world pos').toBeFalsy(); + expect(child.contains(50, 50), '(50, 50) world coords is outside child world pos').toBeFalsy(); // in world coordinates this should be true - expect(child.contains(550.01, 50.01)).withContext('(550.1, 50.1) world should be top-left of of child').toBeTruthy(); - expect(child.contains(650, 150)).withContext('(650, 150) world should be bottom-right of child').toBeTruthy(); + expect(child.contains(550.01, 50.01), '(550.1, 50.1) world should be top-left of of child').toBeTruthy(); + expect(child.contains(650, 150), '(650, 150) world should be bottom-right of child').toBeTruthy(); // second order child shifted to the origin - expect(child2.contains(-49.99, -49.99)).withContext('(-50, -50) world should be top left of second order child').toBeTruthy(); - expect(child2.contains(50, 50)).withContext('(50, 50) world should be bottom right of second order child').toBeTruthy(); + expect(child2.contains(-49.99, -49.99), '(-50, -50) world should be top left of second order child').toBeTruthy(); + expect(child2.contains(50, 50), '(50, 50) world should be bottom right of second order child').toBeTruthy(); }); it('can recursively check containment', () => { @@ -1045,7 +1041,7 @@ describe('A game actor', () => { scene.add(parentActor); parentActor.addChild(childActor); - spyOn(childActor, 'update'); + vi.spyOn(childActor, 'update'); scene.update(engine, 100); @@ -1058,7 +1054,7 @@ describe('A game actor', () => { scene.add(parentActor); parentActor.addChild(childActor); - childActor.graphics.onPostDraw = jasmine.createSpy('draw'); + childActor.graphics.onPostDraw = vi.fn(); childActor.graphics.visible = true; scene.draw(engine.graphicsContext, 100); @@ -1071,7 +1067,7 @@ describe('A game actor', () => { scene.add(parentActor); parentActor.addChild(childActor); - childActor.graphics.onPostDraw = jasmine.createSpy('draw'); + childActor.graphics.onPostDraw = vi.fn(); childActor.graphics.visible = false; scene.draw(engine.graphicsContext, 100); @@ -1101,38 +1097,40 @@ describe('A game actor', () => { expect(actor.isKilled()).toBeFalsy(); }); - it('fires initialize event when before the first update', (done) => { - const actor = new ex.Actor(); - actor.on('initialize', () => { - expect(true).toBe(true); - done(); - }); + it('fires initialize event when before the first update', () => + new Promise((done) => { + const actor = new ex.Actor(); + actor.on('initialize', () => { + expect(true).toBe(true); + done(); + }); - scene.add(actor); - scene.update(engine, 100); - scene.update(engine, 100); - }); + scene.add(actor); + scene.update(engine, 100); + scene.update(engine, 100); + })); - it('fires preupdate event before update then postupdate', (done) => { - const actor = new ex.Actor(); - let preupdateFired = false; + it('fires preupdate event before update then postupdate', () => + new Promise((done) => { + const actor = new ex.Actor(); + let preupdateFired = false; - actor.on('preupdate', () => { - preupdateFired = true; - }); - actor.on('postupdate', () => { - expect(preupdateFired).toBe(true); - done(); - }); + actor.on('preupdate', () => { + preupdateFired = true; + }); + actor.on('postupdate', () => { + expect(preupdateFired).toBe(true); + done(); + }); - scene.add(actor); - scene.update(engine, 100); - }); + scene.add(actor); + scene.update(engine, 100); + })); it('can only be initialized once', async () => { const actor = new ex.Actor(); - const initializeSpy = jasmine.createSpy('initialize'); + const initializeSpy = vi.fn(); actor.on('initialize', initializeSpy); await actor._initialize(engine); @@ -1162,7 +1160,7 @@ describe('A game actor', () => { await actor._initialize(engine); await actor._initialize(engine); - expect(initializeCount).withContext('All child actors should be initialized').toBe(3); + expect(initializeCount, 'All child actors should be initialized').toBe(3); }); describe('should detect assigned events and', () => { @@ -1173,7 +1171,7 @@ describe('A game actor', () => { /* doesn't matter; */ } }; - const moveSpy = spyOn(callables, 'move').and.callThrough(); + const moveSpy = vi.spyOn(callables, 'move'); actor.on('pointermove', callables.move); scene.add(actor); @@ -1191,7 +1189,7 @@ describe('A game actor', () => { /* doesn't matter */ } }; - const enterSpy = spyOn(callables, 'enter').and.callThrough(); + const enterSpy = vi.spyOn(callables, 'enter'); actor.on('pointerenter', callables.enter); scene.add(actor); @@ -1206,7 +1204,7 @@ describe('A game actor', () => { it('should capture pointer leave event', () => { const actor = new ex.Actor({ x: 0, y: 0, width: 20, height: 20 }); - const leaveSpy = jasmine.createSpy('leave'); + const leaveSpy = vi.fn(); actor.on('pointerleave', leaveSpy); scene.add(actor); @@ -1224,7 +1222,7 @@ describe('A game actor', () => { /* doesn't matter */ } }; - const dragStartSpy = spyOn(callables, 'dragStart').and.callThrough(); + const dragStartSpy = vi.spyOn(callables, 'dragStart'); actor.on('pointerdragstart', callables.dragStart); scene.add(actor); @@ -1243,7 +1241,7 @@ describe('A game actor', () => { /* doesn't matter */ } }; - const dragEndSpy = spyOn(callables, 'dragEnd').and.callThrough(); + const dragEndSpy = vi.spyOn(callables, 'dragEnd'); actor.on('pointerdragend', callables.dragEnd); scene.add(actor); @@ -1262,7 +1260,7 @@ describe('A game actor', () => { /* doesn't matter */ } }; - const dragMoveSpy = spyOn(callables, 'dragMove').and.callThrough(); + const dragMoveSpy = vi.spyOn(callables, 'dragMove'); actor.on('pointerdragmove', callables.dragMove); scene.add(actor); @@ -1277,7 +1275,7 @@ describe('A game actor', () => { it('should capture pointer drag enter event', () => { const actor = new ex.Actor({ x: 0, y: 0, width: 20, height: 20 }); - const dragEnterSpy = jasmine.createSpy('dragenter'); + const dragEnterSpy = vi.fn(); actor.on('pointerdragenter', dragEnterSpy); scene.add(actor); @@ -1294,7 +1292,7 @@ describe('A game actor', () => { it('should capture pointer drag leave event', () => { const actor = new ex.Actor({ x: 0, y: 0, width: 20, height: 20 }); - const dragLeaveSpy = jasmine.createSpy('dragLeave'); + const dragLeaveSpy = vi.fn(); actor.on('pointerdragleave', dragLeaveSpy); scene.add(actor); @@ -1317,7 +1315,7 @@ describe('A game actor', () => { /* doesn't matter */ } }; - const bubblingSpy = spyOn(callables, 'pointerDown').and.callThrough(); + const bubblingSpy = vi.spyOn(callables, 'pointerDown'); actor.on('pointerdown', callables.pointerDown); child.on('pointerdown', callables.pointerDown); @@ -1343,12 +1341,12 @@ describe('A game actor', () => { scene.update(engine, 100); - expect(numPointerUps).toBe(1, 'Pointer up should be triggered once'); + expect(numPointerUps, 'Pointer up should be triggered once').toBe(1); }); }); it('when killed should not be killed again by the scene removing it', () => { - spyOn(actor, 'kill').and.callThrough(); + vi.spyOn(actor, 'kill'); scene.add(actor); actor.kill(); @@ -1376,13 +1374,13 @@ describe('A game actor', () => { scene.update(engine, 100); scene.draw(engine.graphicsContext, 100); - expect(actor.isOffScreen).withContext('Actor should be onscreen').toBe(false); + expect(actor.isOffScreen, 'Actor should be onscreen').toBe(false); actor.pos.x = 106; scene.update(engine, 100); scene.draw(engine.graphicsContext, 100); - expect(actor.isOffScreen).withContext('Actor should be offscreen').toBe(true); + expect(actor.isOffScreen, 'Actor should be offscreen').toBe(true); }); describe('lifecycle overrides', () => { @@ -1405,8 +1403,8 @@ describe('A game actor', () => { expect(engine).not.toBe(null); }; - spyOn(actor, 'onInitialize').and.callThrough(); - spyOn(actor, '_initialize').and.callThrough(); + vi.spyOn(actor, 'onInitialize'); + vi.spyOn(actor, '_initialize'); actor.update(engine, 100); actor.update(engine, 100); @@ -1422,8 +1420,8 @@ describe('A game actor', () => { expect(elapsedMs).toBe(100); }; - spyOn(actor, 'onPostUpdate').and.callThrough(); - spyOn(actor, '_postupdate').and.callThrough(); + vi.spyOn(actor, 'onPostUpdate'); + vi.spyOn(actor, '_postupdate'); actor.update(engine, 100); actor.update(engine, 100); @@ -1437,8 +1435,8 @@ describe('A game actor', () => { expect(elapsedMs).toBe(100); }; - spyOn(actor, 'onPreUpdate').and.callThrough(); - spyOn(actor, '_preupdate').and.callThrough(); + vi.spyOn(actor, 'onPreUpdate'); + vi.spyOn(actor, '_preupdate'); actor.update(engine, 100); actor.update(engine, 100); @@ -1452,8 +1450,8 @@ describe('A game actor', () => { expect(scene).not.toBe(null); }; - spyOn(actor, '_prekill').and.callThrough(); - spyOn(actor, 'onPreKill').and.callThrough(); + vi.spyOn(actor, '_prekill'); + vi.spyOn(actor, 'onPreKill'); actor.kill(); expect(actor._prekill).toHaveBeenCalledTimes(1); @@ -1466,8 +1464,8 @@ describe('A game actor', () => { expect(scene).not.toBe(null); }; - spyOn(actor, '_postkill').and.callThrough(); - spyOn(actor, 'onPostKill').and.callThrough(); + vi.spyOn(actor, '_postkill'); + vi.spyOn(actor, 'onPostKill'); actor.kill(); expect(actor._postkill).toHaveBeenCalledTimes(1); @@ -1483,8 +1481,8 @@ describe('A game actor', () => { expect(engine).not.toBe(null); }; - spyOn(actor, 'onAdd').and.callThrough(); - spyOn(actor, 'onRemove').and.callThrough(); + vi.spyOn(actor, 'onAdd'); + vi.spyOn(actor, 'onRemove'); engine.add(actor); engine.currentScene.update(engine, 100); engine.remove(actor); diff --git a/src/spec/AffineMatrixSpec.ts b/src/spec/vitest/AffineMatrixSpec.ts similarity index 66% rename from src/spec/AffineMatrixSpec.ts rename to src/spec/vitest/AffineMatrixSpec.ts index 0293d115..a086f3b0 100644 --- a/src/spec/AffineMatrixSpec.ts +++ b/src/spec/vitest/AffineMatrixSpec.ts @@ -1,11 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A AffineMatrix', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); - it('exists', () => { expect(ex.AffineMatrix).toBeDefined(); }); @@ -17,7 +12,7 @@ describe('A AffineMatrix', () => { it('can make an identity matrix', () => { const identity = ex.AffineMatrix.identity(); - expect(identity.isIdentity()).toBeTrue(); + expect(identity.isIdentity()).toBe(true); }); it('can make a translation matrix', () => { @@ -29,7 +24,7 @@ describe('A AffineMatrix', () => { it('can make a rotation matrix', () => { const mat = ex.AffineMatrix.rotation(Math.PI / 4); - expect(mat.getRotation()).toBe(Math.PI / 4); + expect(mat.getRotation()).toBeCloseTo(Math.PI / 4, 2); }); it('can make a scale matrix', () => { @@ -75,78 +70,78 @@ describe('A AffineMatrix', () => { it('can set scale with rotation in the mix', () => { const mat = ex.AffineMatrix.identity(); mat.setScale(ex.vec(-1, -1)); - expect(mat.getScaleX()).toBe(-1, 'getScaleX()'); - expect(mat.getScaleY()).toBe(-1, 'getScaleY()'); + expect(mat.getScaleX(), 'getScaleX()').toBe(-1); + expect(mat.getScaleY(), 'getScaleY()').toBe(-1); mat.setScale(ex.vec(-2, -5)); - expect(mat.getScaleX()).toBe(-2, 'getScaleX()'); - expect(mat.getScaleY()).toBe(-5, 'getScaleY()'); + expect(mat.getScaleX(), 'getScaleX()').toBe(-2); + expect(mat.getScaleY(), 'getScaleY()').toBe(-5); mat.setScale(ex.vec(5, 11)); - expect(mat.getScaleX()).toBe(5, 'getScaleX()'); - expect(mat.getScaleY()).toBe(11, 'getScaleY()'); + expect(mat.getScaleX(), 'getScaleX()').toBe(5); + expect(mat.getScaleY(), 'getScaleY()').toBe(11); expect(mat.data[0]).toBe(5); expect(mat.data[3]).toBe(11); mat.setScale(ex.vec(1, -1)); - expect(mat.getScaleX()).toBe(1, 'getScaleX()'); - expect(mat.getScaleY()).toBe(-1, 'getScaleY()'); + expect(mat.getScaleX(), 'getScaleX()').toBe(1); + expect(mat.getScaleY(), 'getScaleY()').toBe(-1); mat.setRotation(Math.PI / 3); - expect(mat.getScaleX()).toBeCloseTo(1, 2, 'rotated PI/3 getScaleX()'); - expect(mat.getScaleY()).toBeCloseTo(-1, 2, 'rotated PI/3 getScaleY()'); - expect(mat.getRotation()).toBeCloseTo(Math.PI / 3, 2, 'rotated PI/3 getRotation()'); + expect(mat.getScaleX(), 'rotated PI/3 getScaleX()').toBeCloseTo(1, 2); + expect(mat.getScaleY(), 'rotated PI/3 getScaleY()').toBeCloseTo(-1, 2); + expect(mat.getRotation(), 'rotated PI/3 getRotation()').toBeCloseTo(Math.PI / 3, 2); mat.setRotation(Math.PI); - expect(mat.getScaleX()).toBeCloseTo(1, 2, 'rotated PI getScaleX()'); - expect(mat.getScaleY()).toBeCloseTo(-1, 2, 'rotated PI getScaleY()'); - expect(mat.getRotation()).toBeCloseTo(Math.PI, 2, 'rotated PI getRotation()'); + expect(mat.getScaleX(), 'rotated PI getScaleX()').toBeCloseTo(1, 2); + expect(mat.getScaleY(), 'rotated PI getScaleY()').toBeCloseTo(-1, 2); + expect(mat.getRotation(), 'rotated PI getRotation()').toBeCloseTo(Math.PI, 2); mat.setRotation(Math.PI * 2); - expect(mat.getScaleX()).toBeCloseTo(1, 2, 'rotated 2 PI getScaleX()'); - expect(mat.getScaleY()).toBeCloseTo(-1, 2, 'rotated 2 PI getScaleY()'); - expect(mat.getRotation()).toBeCloseTo(Math.PI * 2, 2, 'rotated 2 PI getRotation()'); + expect(mat.getScaleX(), 'rotated 2 PI getScaleX()').toBeCloseTo(1, 2); + expect(mat.getScaleY(), 'rotated 2 PI getScaleY()').toBeCloseTo(-1, 2); + expect(mat.getRotation(), 'rotated 2 PI getRotation()').toBeCloseTo(Math.PI * 2, 2); mat.setRotation(Math.PI * 3); - expect(mat.getScaleX()).toBeCloseTo(1, 2, 'rotated 3 PI getScaleX()'); - expect(mat.getScaleY()).toBeCloseTo(-1, 2, 'rotated 3 PI getScaleY()'); - expect(mat.getRotation()).toBeCloseTo(Math.PI, 2, 'rotated 3 * PI getRotation()'); + expect(mat.getScaleX(), 'rotated 3 PI getScaleX()').toBeCloseTo(1, 2); + expect(mat.getScaleY(), 'rotated 3 PI getScaleY()').toBeCloseTo(-1, 2); + expect(mat.getRotation(), 'rotated 3 * PI getRotation()').toBeCloseTo(Math.PI, 2); }); it('can set the rotation', () => { const mat = ex.AffineMatrix.identity(); mat.setRotation(0); - expect(mat.getRotation()).toBeCloseTo(0, 2, 'rotation 0'); + expect(mat.getRotation(), 'rotation 0').toBeCloseTo(0, 2); mat.setRotation(Math.PI / 3); - expect(mat.getRotation()).toBeCloseTo(Math.PI / 3, 2, 'rotation PI/3'); + expect(mat.getRotation(), 'rotation PI/3').toBeCloseTo(Math.PI / 3, 2); mat.setRotation(Math.PI); - expect(mat.getRotation()).toBeCloseTo(Math.PI, 2, 'rotation PI'); + expect(mat.getRotation(), 'rotation PI').toBeCloseTo(Math.PI, 2); mat.setRotation(Math.PI * 2); - expect(mat.getRotation()).toBeCloseTo(Math.PI * 2, 2, 'rotation 2 PI'); + expect(mat.getRotation(), 'rotation 2 PI').toBeCloseTo(Math.PI * 2, 2); mat.setRotation(Math.PI * 3); - expect(mat.getRotation()).toBeCloseTo(Math.PI, 2, 'roation 3 PI'); + expect(mat.getRotation(), 'roation 3 PI').toBeCloseTo(Math.PI, 2); }); it('can find the affine inverse', () => { const mat = ex.AffineMatrix.identity().translate(100, -200).scale(2, 4); const inv = mat.inverse(); - expect(mat.multiply(inv).isIdentity()).toBeTrue(); - expect(inv.multiply(mat).isIdentity()).toBeTrue(); + expect(mat.multiply(inv).isIdentity()).toBe(true); + expect(inv.multiply(mat).isIdentity()).toBe(true); }); it('can find the affine inverse and store it into a target', () => { const target = ex.AffineMatrix.identity(); const mat = ex.AffineMatrix.identity().translate(100, -200).scale(2, 4); - spyOn(ex.AffineMatrix, 'identity'); + vi.spyOn(ex.AffineMatrix, 'identity'); const inv = mat.inverse(target); - expect(mat.multiply(inv).isIdentity()).toBeTrue(); - expect(inv.multiply(mat).isIdentity()).toBeTrue(); + expect(mat.multiply(inv).isIdentity()).toBe(true); + expect(inv.multiply(mat).isIdentity()).toBe(true); expect(target).toBe(inv); - expect(ex.AffineMatrix.identity).withContext('using a target doesnt create a new mat').not.toHaveBeenCalledWith(); + expect(ex.AffineMatrix.identity, 'using a target doesnt create a new mat').not.toHaveBeenCalledWith(); }); it('can clone into a target matrix', () => { diff --git a/src/spec/AlgebraSpec.ts b/src/spec/vitest/AlgebraSpec.ts similarity index 92% rename from src/spec/AlgebraSpec.ts rename to src/spec/vitest/AlgebraSpec.ts index 85fbbf0e..7330a2a0 100644 --- a/src/spec/AlgebraSpec.ts +++ b/src/spec/vitest/AlgebraSpec.ts @@ -1,11 +1,6 @@ -import { ExcaliburMatchers } from 'excalibur-jasmine'; import * as ex from '@excalibur'; describe('Vectors', () => { - beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); - it('should exists', () => { expect(ex.Vector).toBeDefined(); }); @@ -283,30 +278,30 @@ describe('Vectors', () => { const oneComponentInvalidTest3 = new ex.Vector(1, Infinity); const oneComponentInvalidTest4 = new ex.Vector(1, -Infinity); - expect(ex.Vector.isValid(invalidTest1)).toBe(false, 'Infinity vectors should be invalid'); - expect(ex.Vector.isValid(invalidTest2)).toBe(false, 'Infinity vectors should be invalid'); - expect(ex.Vector.isValid(invalidTest3)).toBe(false, 'Infinity vectors should be invalid'); - expect(ex.Vector.isValid(invalidTest4)).toBe(false, 'Infinity vectors should be invalid'); - expect(ex.Vector.isValid(oneComponentInvalidTest1)).toBe(false, 'Infinity vectors with one component at +/-Infinity should be invalid'); - expect(ex.Vector.isValid(oneComponentInvalidTest2)).toBe(false, 'Infinity vectors with one component at +/-Infinity should be invalid'); - expect(ex.Vector.isValid(oneComponentInvalidTest3)).toBe(false, 'Infinity vectors with one component at +/-Infinity should be invalid'); - expect(ex.Vector.isValid(oneComponentInvalidTest4)).toBe(false, 'Infinity vectors with one component at +/-Infinity should be invalid'); + expect(ex.Vector.isValid(invalidTest1), 'Infinity vectors should be invalid').toBe(false); + expect(ex.Vector.isValid(invalidTest2), 'Infinity vectors should be invalid').toBe(false); + expect(ex.Vector.isValid(invalidTest3), 'Infinity vectors should be invalid').toBe(false); + expect(ex.Vector.isValid(invalidTest4), 'Infinity vectors should be invalid').toBe(false); + expect(ex.Vector.isValid(oneComponentInvalidTest1), 'Infinity vectors with one component at +/-Infinity should be invalid').toBe(false); + expect(ex.Vector.isValid(oneComponentInvalidTest2), 'Infinity vectors with one component at +/-Infinity should be invalid').toBe(false); + expect(ex.Vector.isValid(oneComponentInvalidTest3), 'Infinity vectors with one component at +/-Infinity should be invalid').toBe(false); + expect(ex.Vector.isValid(oneComponentInvalidTest4), 'Infinity vectors with one component at +/-Infinity should be invalid').toBe(false); }); it('can be checked for validity on NaN vectors', () => { const invalid = new ex.Vector(NaN, NaN); const oneComponentInvalid = new ex.Vector(NaN, 2); - expect(ex.Vector.isValid(invalid)).toBe(false, 'NaN vectors should be invalid'); - expect(ex.Vector.isValid(oneComponentInvalid)).toBe(false, 'NaN vectors with one component should be invalid'); + expect(ex.Vector.isValid(invalid), 'NaN vectors should be invalid').toBe(false); + expect(ex.Vector.isValid(oneComponentInvalid), 'NaN vectors with one component should be invalid').toBe(false); }); it('can be checked for validity on null or undefined vectors', () => { const invalidNull: ex.Vector = null; const invalidUndef: ex.Vector = undefined; - expect(ex.Vector.isValid(invalidNull)).toBe(false, 'Null vectors should be invalid'); - expect(ex.Vector.isValid(invalidUndef)).toBe(false, 'undefined vectors should be invalid'); + expect(ex.Vector.isValid(invalidNull), 'Null vectors should be invalid').toBe(false); + expect(ex.Vector.isValid(invalidUndef), 'undefined vectors should be invalid').toBe(false); }); it('can be cloned', () => { diff --git a/src/spec/AnimationSpec.ts b/src/spec/vitest/AnimationSpec.ts similarity index 95% rename from src/spec/AnimationSpec.ts rename to src/spec/vitest/AnimationSpec.ts index 0890d9e2..c2077f0b 100644 --- a/src/spec/AnimationSpec.ts +++ b/src/spec/vitest/AnimationSpec.ts @@ -1,13 +1,7 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; -import { ExcaliburGraphicsContext2DCanvas } from '../engine/Graphics'; +import { ExcaliburGraphicsContext2DCanvas } from '../../engine/Graphics'; describe('A Graphics Animation', () => { - beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - it('exists', () => { expect(ex.Animation).toBeDefined(); }); @@ -199,12 +193,12 @@ describe('A Graphics Animation', () => { } }); const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); const invalidIndices = [-1, -2, 101, 102]; const anim = ex.Animation.fromSpriteSheet(ss, invalidIndices, 100, ex.AnimationStrategy.Freeze); expect(logger.warn).toHaveBeenCalledTimes(1); - expect(logger.warn).toHaveBeenCalledOnceWith( + expect(logger.warn).toHaveBeenCalledExactlyOnceWith( `Indices into SpriteSheet were provided that don\'t exist: ${invalidIndices.join(',')} no frame will be shown` ); expect(anim.strategy).toBe(ex.AnimationStrategy.Freeze); @@ -411,9 +405,9 @@ describe('A Graphics Animation', () => { ] }); - const onFrame = jasmine.createSpy('onFrame'); - const onEnd = jasmine.createSpy('onEnd'); - const onLoop = jasmine.createSpy('onLoop'); + const onFrame = vi.fn(); + const onEnd = vi.fn(); + const onLoop = vi.fn(); anim.events.on('frame', onFrame); anim.events.on('end', onEnd); looper.events.on('loop', onLoop); @@ -451,7 +445,7 @@ describe('A Graphics Animation', () => { ] }); - const onFrame = jasmine.createSpy('onFrame'); + const onFrame = vi.fn(); anim.events.on('frame', onFrame); anim.tick(100, 0); anim.pause(); @@ -506,17 +500,17 @@ describe('A Graphics Animation', () => { ctx.clear(); anim.draw(ctx, 0, 0); - await expectAsync(output).toEqualImage('src/spec/images/GraphicsAnimationSpec/frame-1.png'); + await expect(output).toEqualImage('/src/spec/assets/images/GraphicsAnimationSpec/frame-1.png'); ctx.clear(); anim.tick(100, 0); anim.draw(ctx, 0, 0); - await expectAsync(output).toEqualImage('src/spec/images/GraphicsAnimationSpec/frame-2.png'); + await expect(output).toEqualImage('/src/spec/assets/images/GraphicsAnimationSpec/frame-2.png'); ctx.clear(); anim.tick(100, 1); anim.draw(ctx, 0, 0); - await expectAsync(output).toEqualImage('src/spec/images/GraphicsAnimationSpec/frame-3.png'); + await expect(output).toEqualImage('/src/spec/assets/images/GraphicsAnimationSpec/frame-3.png'); }); it('calculate automatically the frame duration based on the animation total duration', () => { diff --git a/src/spec/ArcadeSolverSpec.ts b/src/spec/vitest/ArcadeSolverSpec.ts similarity index 96% rename from src/spec/ArcadeSolverSpec.ts rename to src/spec/vitest/ArcadeSolverSpec.ts index 242251c0..2f20b1d6 100644 --- a/src/spec/ArcadeSolverSpec.ts +++ b/src/spec/vitest/ArcadeSolverSpec.ts @@ -1,13 +1,9 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; + import { TestUtils } from './util/TestUtils'; -import { getDefaultPhysicsConfig } from '../engine/Collision/PhysicsConfig'; +import { getDefaultPhysicsConfig } from '../../engine/Collision/PhysicsConfig'; describe('An ArcadeSolver', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); - it('should exist', () => { expect(ex.ArcadeSolver).toBeDefined(); }); @@ -139,7 +135,7 @@ describe('An ArcadeSolver', () => { null ); arcadeSolver.solvePosition(contact2); - expect(contact2.isCanceled()).toBeTrue(); + expect(contact2.isCanceled()).toBe(true); }); it('should NOT cancel collisions where the bodies are moving away from the contact', () => { @@ -176,7 +172,7 @@ describe('An ArcadeSolver', () => { null ); arcadeSolver.solveVelocity(contact); - expect(contact.isCanceled()).toBeFalse(); + expect(contact.isCanceled()).toBe(false); expect(player.vel).toBeVector(ex.vec(0, -10)); // Velocity is not adjusted // Player moving towards contact @@ -193,7 +189,7 @@ describe('An ArcadeSolver', () => { ); arcadeSolver.solveVelocity(contact2); - expect(contact2.isCanceled()).toBeFalse(); + expect(contact2.isCanceled()).toBe(false); expect(player.vel).toBeVector(ex.Vector.Zero); // Velocity is adjusted }); diff --git a/src/spec/AssertSpec.ts b/src/spec/vitest/AssertSpec.ts similarity index 79% rename from src/spec/AssertSpec.ts rename to src/spec/vitest/AssertSpec.ts index a026c494..26787f0a 100644 --- a/src/spec/AssertSpec.ts +++ b/src/spec/vitest/AssertSpec.ts @@ -1,4 +1,5 @@ import * as ex from '@excalibur'; + describe('An assert', () => { it('exists', () => { expect(ex.assert).toBeDefined(); @@ -9,7 +10,7 @@ describe('An assert', () => { ex.assert('throws', () => false); }; - expect(action).toThrowError('throws'); + expect(() => action()).toThrowError('throws'); }); it('will not throw in dev when expression is true', () => { @@ -17,6 +18,6 @@ describe('An assert', () => { ex.assert('throws', () => true); }; - expect(action).not.toThrowError('throws'); + expect(() => action()).not.toThrowError('throws'); }); }); diff --git a/src/spec/BezierSpec.ts b/src/spec/vitest/BezierSpec.ts similarity index 94% rename from src/spec/BezierSpec.ts rename to src/spec/vitest/BezierSpec.ts index 7c885d5a..6b17f0da 100644 --- a/src/spec/BezierSpec.ts +++ b/src/spec/vitest/BezierSpec.ts @@ -1,10 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A BezierCurve', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); it('exists', () => { expect(ex.BezierCurve).toBeDefined(); }); diff --git a/src/spec/BodyComponentSpec.ts b/src/spec/vitest/BodyComponentSpec.ts similarity index 95% rename from src/spec/BodyComponentSpec.ts rename to src/spec/vitest/BodyComponentSpec.ts index cf7554af..4e73e690 100644 --- a/src/spec/BodyComponentSpec.ts +++ b/src/spec/vitest/BodyComponentSpec.ts @@ -1,11 +1,7 @@ import * as ex from '@excalibur'; import { BodyComponent } from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A body component', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); it('exists', () => { expect(ex.BodyComponent).toBeDefined(); }); diff --git a/src/spec/BoundingBoxSpec.ts b/src/spec/vitest/BoundingBoxSpec.ts similarity index 100% rename from src/spec/BoundingBoxSpec.ts rename to src/spec/vitest/BoundingBoxSpec.ts diff --git a/src/spec/BrowserEventsSpec.ts b/src/spec/vitest/BrowserEventsSpec.ts similarity index 66% rename from src/spec/BrowserEventsSpec.ts rename to src/spec/vitest/BrowserEventsSpec.ts index 6e0dcf4b..4cd13047 100644 --- a/src/spec/BrowserEventsSpec.ts +++ b/src/spec/vitest/BrowserEventsSpec.ts @@ -18,13 +18,14 @@ describe('The BrowserEvents facade', () => { expect(browser).toBeDefined(); }); - it('can register handlers on window', (done) => { - browser.window.on('someevent', () => { - done(); - }); + it('can register handlers on window', () => + new Promise((done) => { + browser.window.on('someevent', () => { + done(); + }); - window.dispatchEvent(new Event('someevent')); - }); + window.dispatchEvent(new Event('someevent')); + })); it('can pause handlers on window', () => { browser.window.on('somewindowevent', () => { @@ -35,13 +36,14 @@ describe('The BrowserEvents facade', () => { window.dispatchEvent(new Event('somewindowevent')); }); - it('can register handlers on document', (done) => { - browser.document.on('someevent', () => { - done(); - }); + it('can register handlers on document', () => + new Promise((done) => { + browser.document.on('someevent', () => { + done(); + }); - document.dispatchEvent(new Event('someevent')); - }); + document.dispatchEvent(new Event('someevent')); + })); it('can pause handlers on document', () => { browser.document.on('somedocumentevent', () => { @@ -70,20 +72,21 @@ describe('The BrowserEvents facade', () => { document.dispatchEvent(new Event('somedocevent2')); }); - it('can only have 1 handler per event name at a time', (done) => { - browser.window.on('couldfailevent', () => { - fail(); - }); + it('can only have 1 handler per event name at a time', () => + new Promise((done) => { + browser.window.on('couldfailevent', () => { + fail(); + }); - browser.window.on('couldfailevent', () => { - done(); - }); + browser.window.on('couldfailevent', () => { + done(); + }); - window.dispatchEvent(new Event('couldfailevent')); - }); + window.dispatchEvent(new Event('couldfailevent')); + })); it('can resume handlers', () => { - const spy = jasmine.createSpy(); + const spy = vi.fn(); browser.document.on('somedocumentevent', spy); browser.pause(); diff --git a/src/spec/CameraSpec.ts b/src/spec/vitest/CameraSpec.ts similarity index 90% rename from src/spec/CameraSpec.ts rename to src/spec/vitest/CameraSpec.ts index 7cef62e2..4fa29601 100644 --- a/src/spec/CameraSpec.ts +++ b/src/spec/vitest/CameraSpec.ts @@ -1,4 +1,3 @@ -import { ExcaliburMatchers, ensureImagesLoaded } from 'excalibur-jasmine'; import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; @@ -9,7 +8,6 @@ describe('A camera', () => { let scene: ex.Scene; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); actor = new ex.Actor({ width: 10, height: 10 @@ -39,6 +37,7 @@ describe('A camera', () => { engine.stop(); engine.dispose(); engine = null; + vi.restoreAllMocks(); }); it('should be center screen by default (when loading not complete)', () => { @@ -50,8 +49,8 @@ describe('A camera', () => { }); engine.screen.pushResolutionAndViewport(); engine.screen.resolution = { width: 100, height: 1000 }; - spyOnProperty(engine, 'loadingComplete', 'get').and.returnValue(false); - spyOn(engine.screen, 'peekResolution').and.callThrough(); + vi.spyOn(engine, 'loadingComplete', 'get').mockImplementation(() => false); + vi.spyOn(engine.screen, 'peekResolution'); const sut = new ex.Camera(); sut.zoom = 2; // zoom should not change the center position @@ -71,7 +70,7 @@ describe('A camera', () => { const sut = new ex.Camera(); - spyOn(sut, 'runStrategies').and.callThrough(); + vi.spyOn(sut, 'runStrategies'); sut._initialize(engine); expect(sut.runStrategies).toHaveBeenCalledTimes(1); @@ -87,7 +86,7 @@ describe('A camera', () => { const sut = new ex.Camera(); expect(sut.viewport).toEqual(new ex.BoundingBox()); - spyOn(sut, 'updateViewport').and.callThrough(); + vi.spyOn(sut, 'updateViewport'); sut._initialize(engine); expect(sut.viewport).toEqual(ex.BoundingBox.fromDimension(1000, 1200, ex.Vector.Zero)); @@ -102,8 +101,8 @@ describe('A camera', () => { resolution: { width: 1000, height: 1200 } }); - spyOnProperty(engine, 'loadingComplete', 'get').and.returnValue(true); - spyOn(engine.screen, 'peekResolution').and.callThrough(); + vi.spyOn(engine, 'loadingComplete', 'get').mockImplementation(() => true); + vi.spyOn(engine.screen, 'peekResolution'); const sut = new ex.Camera(); sut.zoom = 2; // zoom should not change the center position sut._initialize(engine); @@ -372,22 +371,23 @@ describe('A camera', () => { expect(engine.currentScene.camera.pos.y).toBe(750); }); - it('can lerp over time', (done) => { - engine.currentScene.camera.move(new ex.Vector(100, 100), 1000, ex.EasingFunctions.EaseOutCubic).then(() => { - engine.currentScene.camera.move(new ex.Vector(200, 200), 1000, ex.EasingFunctions.Linear).then(() => { - expect(engine.currentScene.camera.pos.x).toBe(200); - expect(engine.currentScene.camera.pos.y).toBe(200); - done(); + it('can lerp over time', () => + new Promise((done) => { + engine.currentScene.camera.move(new ex.Vector(100, 100), 1000, ex.EasingFunctions.EaseOutCubic).then(() => { + engine.currentScene.camera.move(new ex.Vector(200, 200), 1000, ex.EasingFunctions.Linear).then(() => { + expect(engine.currentScene.camera.pos.x).toBe(200); + expect(engine.currentScene.camera.pos.y).toBe(200); + done(); + }); + engine.currentScene.camera.update(engine, 999); + engine.currentScene.camera.update(engine, 1); + engine.currentScene.camera.update(engine, 1); }); + engine.currentScene.camera.update(engine, 999); engine.currentScene.camera.update(engine, 1); engine.currentScene.camera.update(engine, 1); - }); - - engine.currentScene.camera.update(engine, 999); - engine.currentScene.camera.update(engine, 1); - engine.currentScene.camera.update(engine, 1); - }); + })); describe('lifecycle overrides', () => { let camera: ex.Camera; @@ -412,7 +412,7 @@ describe('A camera', () => { initCalled = true; }); - spyOn(camera, 'onInitialize').and.callThrough(); + vi.spyOn(camera, 'onInitialize'); camera.update(engine, 100); @@ -426,8 +426,8 @@ describe('A camera', () => { expect(elapsedMs).toBe(100); }; - spyOn(camera, 'onPostUpdate').and.callThrough(); - spyOn(camera, '_postupdate').and.callThrough(); + vi.spyOn(camera, 'onPostUpdate'); + vi.spyOn(camera, '_postupdate'); camera.update(engine, 100); camera.update(engine, 100); @@ -442,8 +442,8 @@ describe('A camera', () => { expect(elapsedMs).toBe(100); }; - spyOn(camera, 'onPreUpdate').and.callThrough(); - spyOn(camera, '_preupdate').and.callThrough(); + vi.spyOn(camera, 'onPreUpdate'); + vi.spyOn(camera, '_preupdate'); camera.update(engine, 100); camera.update(engine, 100); diff --git a/src/spec/CanvasSpec.ts b/src/spec/vitest/CanvasSpec.ts similarity index 85% rename from src/spec/CanvasSpec.ts rename to src/spec/vitest/CanvasSpec.ts index b9b43d49..d62587eb 100644 --- a/src/spec/CanvasSpec.ts +++ b/src/spec/vitest/CanvasSpec.ts @@ -1,13 +1,7 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; import { TestUtils } from './util/TestUtils'; describe('A Canvas Graphic', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - it('exists', () => { expect(ex.Canvas).toBeDefined(); }); @@ -53,7 +47,7 @@ describe('A Canvas Graphic', () => { sut.draw(ctx, 0, 0); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsCanvasSpec/draw.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsCanvasSpec/draw.png'); }); it('can cache draws', () => { @@ -67,7 +61,7 @@ describe('A Canvas Graphic', () => { } }); - spyOn(sut, 'execute').and.callThrough(); + vi.spyOn(sut, 'execute'); const canvasElement = document.createElement('canvas'); canvasElement.width = 100; @@ -93,7 +87,7 @@ describe('A Canvas Graphic', () => { } }); - spyOn(sut, 'execute').and.callThrough(); + vi.spyOn(sut, 'execute'); const canvasElement = document.createElement('canvas'); canvasElement.width = 100; @@ -135,7 +129,7 @@ describe('A Canvas Graphic', () => { expect(sut.width).toBe(50); expect(sut.height).toBe(50); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GraphicsCanvasSpec/centered.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GraphicsCanvasSpec/centered.png'); engine.dispose(); }); }); diff --git a/src/spec/CircleSpec.ts b/src/spec/vitest/CircleSpec.ts similarity index 82% rename from src/spec/CircleSpec.ts rename to src/spec/vitest/CircleSpec.ts index 0e06e42c..bcd85937 100644 --- a/src/spec/CircleSpec.ts +++ b/src/spec/vitest/CircleSpec.ts @@ -1,12 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; describe('A Circle Graphic', () => { - beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - it('exists', () => { expect(ex.Circle).toBeDefined(); }); @@ -53,7 +47,7 @@ describe('A Circle Graphic', () => { ctx.clear(); sut.draw(ctx, 50, 50); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsCircleSpec/circle.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsCircleSpec/circle.png'); }); it('can set a lineWidth', async () => { @@ -72,7 +66,7 @@ describe('A Circle Graphic', () => { ctx.clear(); sut.draw(ctx, 0, 0); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsCircleSpec/line-width.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsCircleSpec/line-width.png'); }); it('can be cloned', () => { diff --git a/src/spec/ClockSpec.ts b/src/spec/vitest/ClockSpec.ts similarity index 85% rename from src/spec/ClockSpec.ts rename to src/spec/vitest/ClockSpec.ts index e2e70179..308eea4b 100644 --- a/src/spec/ClockSpec.ts +++ b/src/spec/vitest/ClockSpec.ts @@ -7,7 +7,7 @@ describe('Clocks', () => { }); it('can manually tick', () => { - const tickSpy = jasmine.createSpy('tick'); + const tickSpy = vi.fn(); const testClock = new ex.TestClock({ tick: tickSpy, defaultUpdateMs: 1000 @@ -45,7 +45,7 @@ describe('Clocks', () => { it('will log a warning if not started', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); const testClock = new ex.TestClock({ tick: () => { @@ -59,21 +59,22 @@ describe('Clocks', () => { expect(logger.warn).toHaveBeenCalledWith('The clock is not running, no step will be performed'); }); - it('works with delay()', (done) => { - const testClock = new ex.TestClock({ - tick: () => { - /* nothing */ - }, - defaultUpdateMs: 1000 - }); - testClock.start(); - ex.Util.delay(1000, testClock).then(() => { - done(); - }); - - testClock.step(500); - testClock.step(500); - }); + it('works with delay()', () => + new Promise((done) => { + const testClock = new ex.TestClock({ + tick: () => { + /* nothing */ + }, + defaultUpdateMs: 1000 + }); + testClock.start(); + ex.Util.delay(1000, testClock).then(() => { + done(); + }); + + testClock.step(500); + testClock.step(500); + })); it('can schedule a callbacks to fire', async () => { const testClock = new ex.TestClock({ @@ -84,8 +85,8 @@ describe('Clocks', () => { }); testClock.start(); - const scheduledCb = jasmine.createSpy('scheduled'); - const scheduledCb2 = jasmine.createSpy('scheduled2'); + const scheduledCb = vi.fn(); + const scheduledCb2 = vi.fn(); testClock.schedule(scheduledCb, 1000); testClock.schedule(scheduledCb2, 1500); @@ -106,7 +107,7 @@ describe('Clocks', () => { }); it('can limit fps', () => { - const tickSpy = jasmine.createSpy('tick'); + const tickSpy = vi.fn(); const clock = new ex.TestClock({ tick: tickSpy, maxFps: 15, @@ -129,7 +130,7 @@ describe('Clocks', () => { }); it('can tick', () => { - const tickSpy = jasmine.createSpy('tick'); + const tickSpy = vi.fn(); const clock = new ex.StandardClock({ tick: tickSpy }); @@ -145,14 +146,14 @@ describe('Clocks', () => { }); it('can handle exceptions and stop', () => { - const errorSpy = jasmine.createSpy('error'); + const errorSpy = vi.fn(); const clock = new ex.StandardClock({ tick: () => { throw new Error('some error'); }, onFatalException: errorSpy }); - spyOn(clock, 'stop'); + vi.spyOn(clock, 'stop'); clock.start(); diff --git a/src/spec/ColliderComponentSpec.ts b/src/spec/vitest/ColliderComponentSpec.ts similarity index 89% rename from src/spec/ColliderComponentSpec.ts rename to src/spec/vitest/ColliderComponentSpec.ts index e6858f65..751c2b8d 100644 --- a/src/spec/ColliderComponentSpec.ts +++ b/src/spec/vitest/ColliderComponentSpec.ts @@ -1,4 +1,5 @@ import * as ex from '@excalibur'; + describe('A ColliderComponent', () => { it('exists', () => { expect(ex.ColliderComponent).toBeDefined(); @@ -21,12 +22,12 @@ describe('A ColliderComponent', () => { const collider = new ex.ColliderComponent(ex.Shape.Circle(50)); const owner = new ex.Entity([collider]); - const originalCollisionHandler = jasmine.createSpy(); + const originalCollisionHandler = vi.fn(); owner.on('collisionstart', originalCollisionHandler); const clone = owner.clone(); - const cloneCollisionHandler = jasmine.createSpy(); + const cloneCollisionHandler = vi.fn(); clone.on('collisionstart', cloneCollisionHandler); const sut = clone.get(ex.ColliderComponent); @@ -62,20 +63,20 @@ describe('A ColliderComponent', () => { it('wires up collision events to the owner onAdd', () => { const comp = new ex.ColliderComponent(ex.Shape.Circle(50)); - spyOn(comp.events, 'on'); + vi.spyOn(comp.events, 'on'); const e = new ex.Entity(); e.addComponent(comp); - expect(comp.events.on).toHaveBeenCalledWith('precollision', jasmine.anything()); - expect(comp.events.on).toHaveBeenCalledWith('postcollision', jasmine.anything()); - expect(comp.events.on).toHaveBeenCalledWith('collisionstart', jasmine.anything()); - expect(comp.events.on).toHaveBeenCalledWith('collisionend', jasmine.anything()); + expect(comp.events.on).toHaveBeenCalledWith('precollision', expect.anything()); + expect(comp.events.on).toHaveBeenCalledWith('postcollision', expect.anything()); + expect(comp.events.on).toHaveBeenCalledWith('collisionstart', expect.anything()); + expect(comp.events.on).toHaveBeenCalledWith('collisionend', expect.anything()); }); it('clears out collision events on the owner onRemove', () => { const comp = new ex.ColliderComponent(ex.Shape.Circle(50)); - spyOn(comp.events, 'clear'); + vi.spyOn(comp.events, 'clear'); const e = new ex.Entity(); e.addComponent(comp); @@ -87,8 +88,8 @@ describe('A ColliderComponent', () => { it('clear a collider', () => { const collider = ex.Shape.Circle(50); const comp = new ex.ColliderComponent(collider); - spyOn(collider.events, 'unpipe'); - spyOn(comp.$colliderRemoved, 'notifyAll'); + vi.spyOn(collider.events, 'unpipe'); + vi.spyOn(comp.$colliderRemoved, 'notifyAll'); const e = new ex.Entity(); e.addComponent(comp); expect(collider.owner).not.toBeNull(); diff --git a/src/spec/CollisionContactSpec.ts b/src/spec/vitest/CollisionContactSpec.ts similarity index 81% rename from src/spec/CollisionContactSpec.ts rename to src/spec/vitest/CollisionContactSpec.ts index e5e31515..304ec0e6 100644 --- a/src/spec/CollisionContactSpec.ts +++ b/src/spec/vitest/CollisionContactSpec.ts @@ -1,9 +1,8 @@ import * as ex from '@excalibur'; import { TransformComponent } from '@excalibur'; -import { EulerIntegrator } from '../engine/Collision/Integrator'; -import { MotionComponent } from '../engine/EntityComponentSystem/Components/MotionComponent'; -import { getDefaultPhysicsConfig } from '../engine/Collision/PhysicsConfig'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; +import { EulerIntegrator } from '../../engine/Collision/Integrator'; +import { MotionComponent } from '../../engine/EntityComponentSystem/Components/MotionComponent'; +import { getDefaultPhysicsConfig } from '../../engine/Collision/PhysicsConfig'; describe('A CollisionContact', () => { let actorA: ex.Actor; @@ -13,7 +12,6 @@ describe('A CollisionContact', () => { let colliderB: ex.Collider; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); actorA = new ex.Actor({ x: 0, y: 0, width: 20, height: 20 }); actorA.collider.useCircleCollider(10); actorA.body.collisionType = ex.CollisionType.Active; @@ -70,8 +68,8 @@ describe('A CollisionContact', () => { }); it('emits a collision event on both actors in the Arcade solver', () => { - const actorAPreCollide = jasmine.createSpy('precollision A'); - const actorBPreCollide = jasmine.createSpy('precollision B'); + const actorAPreCollide = vi.fn(); + const actorBPreCollide = vi.fn(); actorA.on('precollision', actorAPreCollide); actorB.on('precollision', actorBPreCollide); @@ -96,12 +94,12 @@ describe('A CollisionContact', () => { }); it('can resolve in the Realistic solver', () => { - expect(actorA.pos.x).toBe(0, 'Actor A should be y=10'); - expect(actorA.pos.y).toBe(0, 'Actor A should be y=0'); - expect(actorB.pos.x).toBe(20, 'Actor B should be x=20'); - expect(actorB.pos.y).toBe(0, 'Actor B should be y=0'); - expect(actorA.vel.x).toBe(0, 'Actor A should not be moving in x'); - expect(actorB.vel.x).toBe(0, 'Actor B should not be moving in x'); + expect(actorA.pos.x, 'Actor A should be y=10').toBe(0); + expect(actorA.pos.y, 'Actor A should be y=0').toBe(0); + expect(actorB.pos.x, 'Actor B should be x=20').toBe(20); + expect(actorB.pos.y, 'Actor B should be y=0').toBe(0); + expect(actorA.vel.x, 'Actor A should not be moving in x').toBe(0); + expect(actorB.vel.x, 'Actor B should not be moving in x').toBe(0); actorA.vel.x = 10; actorB.vel.x = -10; actorB.pos.x = 19; @@ -141,12 +139,12 @@ describe('A CollisionContact', () => { }); it('can resolve perfectly elastic collisions in the Realistic solver', () => { - expect(actorA.pos.x).toBe(0, 'Actor A should be y=10'); - expect(actorA.pos.y).toBe(0, 'Actor A should be y=0'); - expect(actorB.pos.x).toBe(20, 'Actor B should be x=20'); - expect(actorB.pos.y).toBe(0, 'Actor B should be y=0'); - expect(actorA.vel.x).toBe(0, 'Actor A should not be moving in x'); - expect(actorB.vel.x).toBe(0, 'Actor B should not be moving in x'); + expect(actorA.pos.x, 'Actor A should be y=10').toBe(0); + expect(actorA.pos.y, 'Actor A should be y=0').toBe(0); + expect(actorB.pos.x, 'Actor B should be x=20').toBe(20); + expect(actorB.pos.y, 'Actor B should be y=0').toBe(0); + expect(actorA.vel.x, 'Actor A should not be moving in x').toBe(0); + expect(actorB.vel.x, 'Actor B should not be moving in x').toBe(0); actorA.vel.x = 10; actorB.vel.x = -10; actorB.pos.x = 19; @@ -184,12 +182,12 @@ describe('A CollisionContact', () => { }); it('can limit the rotation degree of freedom', () => { - expect(actorA.pos.x).toBe(0, 'Actor A should be y=10'); - expect(actorA.pos.y).toBe(0, 'Actor A should be y=0'); - expect(actorB.pos.x).toBe(20, 'Actor B should be x=20'); - expect(actorB.pos.y).toBe(0, 'Actor B should be y=0'); - expect(actorA.vel.x).toBe(0, 'Actor A should not be moving in x'); - expect(actorB.vel.x).toBe(0, 'Actor B should not be moving in x'); + expect(actorA.pos.x, 'Actor A should be y=10').toBe(0); + expect(actorA.pos.y, 'Actor A should be y=0').toBe(0); + expect(actorB.pos.x, 'Actor B should be x=20').toBe(20); + expect(actorB.pos.y, 'Actor B should be y=0').toBe(0); + expect(actorA.vel.x, 'Actor A should not be moving in x').toBe(0); + expect(actorB.vel.x, 'Actor B should not be moving in x').toBe(0); actorA.vel.x = 10; actorB.vel.x = -10; actorB.pos.x = 19; @@ -221,12 +219,12 @@ describe('A CollisionContact', () => { }); it('can limit the y degree of freedom', () => { - expect(actorA.pos.x).toBe(0, 'Actor A should be y=10'); - expect(actorA.pos.y).toBe(0, 'Actor A should be y=0'); - expect(actorB.pos.x).toBe(20, 'Actor B should be x=20'); - expect(actorB.pos.y).toBe(0, 'Actor B should be y=0'); - expect(actorA.vel.x).toBe(0, 'Actor A should not be moving in x'); - expect(actorB.vel.x).toBe(0, 'Actor B should not be moving in x'); + expect(actorA.pos.x, 'Actor A should be y=10').toBe(0); + expect(actorA.pos.y, 'Actor A should be y=0').toBe(0); + expect(actorB.pos.x, 'Actor B should be x=20').toBe(20); + expect(actorB.pos.y, 'Actor B should be y=0').toBe(0); + expect(actorA.vel.x, 'Actor A should not be moving in x').toBe(0); + expect(actorB.vel.x, 'Actor B should not be moving in x').toBe(0); actorA.vel.x = 10; actorB.vel.x = -10; actorB.pos.x = 19; @@ -261,12 +259,12 @@ describe('A CollisionContact', () => { }); it('can limit the x degree of freedom', () => { - expect(actorA.pos.x).toBe(0, 'Actor A should be y=10'); - expect(actorA.pos.y).toBe(0, 'Actor A should be y=0'); - expect(actorB.pos.x).toBe(20, 'Actor B should be x=20'); - expect(actorB.pos.y).toBe(0, 'Actor B should be y=0'); - expect(actorA.vel.x).toBe(0, 'Actor A should not be moving in x'); - expect(actorB.vel.x).toBe(0, 'Actor B should not be moving in x'); + expect(actorA.pos.x, 'Actor A should be y=10').toBe(0); + expect(actorA.pos.y, 'Actor A should be y=0').toBe(0); + expect(actorB.pos.x, 'Actor B should be x=20').toBe(20); + expect(actorB.pos.y, 'Actor B should be y=0').toBe(0); + expect(actorA.vel.x, 'Actor A should not be moving in x').toBe(0); + expect(actorB.vel.x, 'Actor B should not be moving in x').toBe(0); actorA.vel.x = 10; actorB.pos.x = 19; actorB.pos.y = 10; diff --git a/src/spec/CollisionGroupSpec.ts b/src/spec/vitest/CollisionGroupSpec.ts similarity index 86% rename from src/spec/CollisionGroupSpec.ts rename to src/spec/vitest/CollisionGroupSpec.ts index 2d067e0b..14c63cbe 100644 --- a/src/spec/CollisionGroupSpec.ts +++ b/src/spec/vitest/CollisionGroupSpec.ts @@ -15,9 +15,9 @@ describe('A Collision Group', () => { }); it('should not collide with itself', () => { - expect(groupA.canCollide(groupA)).toBe(false, 'Group groupA should not collide with itself'); - expect(groupB.canCollide(groupB)).toBe(false, 'Group groupB should not collide with itself'); - expect(groupC.canCollide(groupC)).toBe(false, 'Group groupC should not collide with itself'); + expect(groupA.canCollide(groupA), 'Group groupA should not collide with itself').toBe(false); + expect(groupB.canCollide(groupB), 'Group groupB should not collide with itself').toBe(false); + expect(groupC.canCollide(groupC), 'Group groupC should not collide with itself').toBe(false); }); it('should collide with other groups', () => { @@ -61,10 +61,10 @@ describe('A Collision Group', () => { }); it('should collide with the All collision group', () => { - expect(ex.CollisionGroup.All.canCollide(groupA)).toBe(true, 'All should collide with groupA'); - expect(ex.CollisionGroup.All.canCollide(groupB)).toBe(true, 'All should collide with groupB'); - expect(ex.CollisionGroup.All.canCollide(groupC)).toBe(true, 'All should collide with groupC'); - expect(ex.CollisionGroup.All.canCollide(ex.CollisionGroup.All)).toBe(true, 'All collision group should collide with itself'); + expect(ex.CollisionGroup.All.canCollide(groupA), 'All should collide with groupA').toBe(true); + expect(ex.CollisionGroup.All.canCollide(groupB), 'All should collide with groupB').toBe(true); + expect(ex.CollisionGroup.All.canCollide(groupC), 'All should collide with groupC').toBe(true); + expect(ex.CollisionGroup.All.canCollide(ex.CollisionGroup.All), 'All collision group should collide with itself').toBe(true); }); it('should be accessible by name', () => { diff --git a/src/spec/CollisionShapeSpec.ts b/src/spec/vitest/CollisionShapeSpec.ts similarity index 91% rename from src/spec/CollisionShapeSpec.ts rename to src/spec/vitest/CollisionShapeSpec.ts index 431aab76..43d48a04 100644 --- a/src/spec/CollisionShapeSpec.ts +++ b/src/spec/vitest/CollisionShapeSpec.ts @@ -1,14 +1,9 @@ import * as ex from '@excalibur'; import { CollisionJumpTable } from '@excalibur'; -import { ExcaliburMatchers, ensureImagesLoaded, ExcaliburAsyncMatchers } from 'excalibur-jasmine'; + import { TestUtils } from './util/TestUtils'; describe('Collision Shape', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - describe('a Circle', () => { let engine: ex.Engine; let scene: ex.Scene; @@ -83,7 +78,7 @@ describe('Collision Shape', () => { sut.radius = 20; actor.transform.scale = ex.vec(1, 3); sut.update(actor.transform.get()); - expect(sut.radius).withContext('Uneven scale take the smallest').toBe(10); + expect(sut.radius, 'Uneven scale take the smallest').toBe(10); }); it('calculates correct bounds when transformed', () => { @@ -170,7 +165,7 @@ describe('Collision Shape', () => { expect(pointTangent.y).toBe(10); expect(pointNoHit).toBe(null); - expect(pointTooFar).toBe(null, 'The circle should be too far away for a hit'); + expect(pointTooFar, 'The circle should be too far away for a hit').toBe(null); }); it('can be raycast against only positive time of impact (toi)', () => { @@ -387,7 +382,7 @@ describe('Collision Shape', () => { ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/CollisionShapeSpec/circle-debug.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/CollisionShapeSpec/circle-debug.png'); }); it('can be drawn with actor when in constructor', async () => { @@ -400,7 +395,7 @@ describe('Collision Shape', () => { scene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/CollisionShapeSpec/circle.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/CollisionShapeSpec/circle.png'); }); it('can calculate the distance to another circle', () => { @@ -417,7 +412,7 @@ describe('Collision Shape', () => { const line = circle.getClosestLineBetween(circle2); expect(line.getLength()).toBe(40); - expect(line.getEdge().dot(ex.Vector.Right)).toBeGreaterThan(0, 'Line from circle to other circle should be away from this'); + expect(line.getEdge().dot(ex.Vector.Right), 'Line from circle to other circle should be away from this').toBeGreaterThan(0); }); it('can calculate the distance to another polygon', () => { @@ -431,7 +426,7 @@ describe('Collision Shape', () => { const line = circle.getClosestLineBetween(box); expect(line.getLength()).toBe(70); - expect(line.getEdge().dot(ex.Vector.Right)).toBeGreaterThan(0, 'Line from circle to polygon should be away from polygon'); + expect(line.getEdge().dot(ex.Vector.Right), 'Line from circle to polygon should be away from polygon').toBeGreaterThan(0); }); it('can calculate the distance to another edge', () => { @@ -445,7 +440,7 @@ describe('Collision Shape', () => { const line = circle.getClosestLineBetween(edge); expect(line.getLength()).toBe(70); - expect(line.getEdge().dot(ex.Vector.Right)).toBeGreaterThan(0, 'Line from circle to edge should be away from circle'); + expect(line.getEdge().dot(ex.Vector.Right), 'Line from circle to edge should be away from circle').toBeGreaterThan(0); }); }); @@ -521,13 +516,13 @@ describe('Collision Shape', () => { const convex = new ex.PolygonCollider({ points: [ex.vec(0, 0), ex.vec(10, 10), ex.vec(10, 0)] }); - expect(convex.isConvex()).withContext('Triangles are always convex').toBe(true); + expect(convex.isConvex(), 'Triangles are always convex').toBe(true); const concave = new ex.PolygonCollider({ points: [ex.vec(0, 0), ex.vec(5, 5), ex.vec(0, 10), ex.vec(10, 10), ex.vec(10, 0)] }); - expect(concave.isConvex()).withContext('Should be concave').toBe(false); + expect(concave.isConvex(), 'Should be concave').toBe(false); }); it('can triangulate', () => { @@ -543,7 +538,7 @@ describe('Collision Shape', () => { expect(colliders[1].points).toEqual([ex.vec(0, 10), ex.vec(5, 5), ex.vec(10, 0)]); expect(colliders[2].points).toEqual([ex.vec(10, 0), ex.vec(10, 10), ex.vec(0, 10)]); - expect(concave.isConvex()).withContext('Should be concave').toBe(false); + expect(concave.isConvex(), 'Should be concave').toBe(false); }); it('can tesselate', () => { @@ -592,7 +587,7 @@ describe('Collision Shape', () => { const contact = polyA.collide(polyB)[0]; // there should be a collision - expect(contact).withContext('there should be a collision').not.toBeFalsy(); + expect(contact, 'there should be a collision').not.toBeFalsy(); // normal and mtv should point away from bodyA expect(directionOfBodyB.dot(contact.mtv)).toBeGreaterThan(0); @@ -625,7 +620,7 @@ describe('Collision Shape', () => { const contact = polyA.collide(polyB)[0]; // there should be a collision - expect(contact).withContext('There should be a collision').not.toBeFalsy(); + expect(contact, 'There should be a collision').not.toBeFalsy(); // normal and mtv should point away from bodyA expect(directionOfBodyB.dot(contact.mtv)).toBeGreaterThan(0); @@ -813,12 +808,12 @@ describe('Collision Shape', () => { expect(point.x).toBeCloseTo(-5, 0.001); expect(point.y).toBeCloseTo(0, 0.001); expect(hit.normal.x).toBe(-1); - expect(hit.normal.y).toBe(0); + expect(hit.normal.y).toBe(-0); // should this be 0? expect(hit.collider).toBe(polyA); expect(hit.body).toBe(actor.body); expect(hit.distance).toBe(95); expect(noHit).toBe(null); - expect(tooFar).toBe(null, 'The polygon should be too far away for a hit'); + expect(tooFar, 'The polygon should be too far away for a hit').toBe(null); }); it('can be debug drawn', async () => { @@ -834,13 +829,12 @@ describe('Collision Shape', () => { engine.graphicsContext.restore(); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/CollisionShapeSpec/triangle.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/CollisionShapeSpec/triangle.png'); }); it('can be drawn with actor', async () => { const polygonActor = new ex.Actor({ pos: new ex.Vector(150, 100), - color: ex.Color.Blue, collider: ex.Shape.Polygon([new ex.Vector(0, -100), new ex.Vector(-100, 50), new ex.Vector(100, 50)]) }); @@ -848,7 +842,7 @@ describe('Collision Shape', () => { scene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/CollisionShapeSpec/triangle.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/CollisionShapeSpec/triangle.png'); }); it('can calculate the distance to another circle', () => { @@ -862,7 +856,7 @@ describe('Collision Shape', () => { const line = poly.getClosestLineBetween(circle); expect(line.getLength()).toBe(50); - expect(line.getEdge().dot(ex.Vector.Right)).toBeGreaterThan(0, 'Line from polygon to other circle should be away from this'); + expect(line.getEdge().dot(ex.Vector.Right), 'Line from polygon to other circle should be away from this').toBeGreaterThan(0); }); it('can calculate the distance to another polygon', () => { @@ -873,7 +867,7 @@ describe('Collision Shape', () => { const line = poly.getClosestLineBetween(box); expect(line.getLength()).toBe(80); - expect(line.getEdge().dot(ex.Vector.Right)).toBeGreaterThan(0, 'Line from polygon to polygon should be away from polygon'); + expect(line.getEdge().dot(ex.Vector.Right), 'Line from polygon to polygon should be away from polygon').toBeGreaterThan(0); }); it('can calculate the distance to angled edge on polygon', () => { @@ -885,7 +879,7 @@ describe('Collision Shape', () => { const line = box.getClosestLineBetween(poly); expect(line.getLength()).toBe(10); - expect(line.getEdge().dot(ex.Vector.Right)).toBeGreaterThan(0, 'Line from polygon to polygon should be away from polygon'); + expect(line.getEdge().dot(ex.Vector.Right), 'Line from polygon to polygon should be away from polygon').toBeGreaterThan(0); }); it('can calculate the distance to another edge', () => { @@ -896,7 +890,7 @@ describe('Collision Shape', () => { const line = poly.getClosestLineBetween(edge); expect(line.getLength()).toBe(80); - expect(line.getEdge().dot(ex.Vector.Right)).toBeGreaterThan(0, 'Line from circle to edge should be away from circle'); + expect(line.getEdge().dot(ex.Vector.Right), 'Line from circle to edge should be away from circle').toBeGreaterThan(0); }); }); @@ -987,7 +981,7 @@ describe('Collision Shape', () => { expect(rightTan.x).toBeCloseTo(10, 0.001); expect(rightTan.y).toBeCloseTo(0, 0.001); - expect(tooFar).toBe(null, 'Ray should be too far for a hit'); + expect(tooFar, 'Ray should be too far for a hit').toBe(null); }); it('has 4 axes', () => { @@ -1071,13 +1065,12 @@ describe('Collision Shape', () => { engine.graphicsContext.restore(); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/CollisionShapeSpec/edge.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/CollisionShapeSpec/edge.png'); }); it('can be drawn with actor', async () => { const edgeActor = new ex.Actor({ pos: new ex.Vector(150, 100), - color: ex.Color.Blue, collider: ex.Shape.Edge(ex.Vector.Zero, new ex.Vector(300, 300)) }); @@ -1085,7 +1078,7 @@ describe('Collision Shape', () => { scene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/CollisionShapeSpec/edge.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/CollisionShapeSpec/edge.png'); }); it('can calculate the distance to another circle', () => { @@ -1099,7 +1092,7 @@ describe('Collision Shape', () => { const line = edge.getClosestLineBetween(circle); expect(line.getLength()).toBe(70); - expect(line.getEdge().dot(ex.Vector.Right)).toBeGreaterThan(0, 'Line from polygon to other circle should be away from this'); + expect(line.getEdge().dot(ex.Vector.Right), 'Line from polygon to other circle should be away from this').toBeGreaterThan(0); }); it('can calculate the distance to another polygon', () => { @@ -1110,7 +1103,7 @@ describe('Collision Shape', () => { const line = edge.getClosestLineBetween(box); expect(line.getLength()).toBe(100); - expect(line.getEdge().dot(ex.Vector.Right)).toBeGreaterThan(0, 'Line from polygon to polygon should be away from polygon'); + expect(line.getEdge().dot(ex.Vector.Right), 'Line from polygon to polygon should be away from polygon').toBeGreaterThan(0); }); it('can calculate the distance to another edge', () => { @@ -1121,27 +1114,27 @@ describe('Collision Shape', () => { const line = edge.getClosestLineBetween(edge2); expect(line.getLength()).toBe(100); - expect(line.getEdge().dot(ex.Vector.Right)).toBeGreaterThan(0, 'Line from circle to edge should be away from circle'); + expect(line.getEdge().dot(ex.Vector.Right), 'Line from circle to edge should be away from circle').toBeGreaterThan(0); }); it('can collide with a circle center edge', () => { const edge = ex.Shape.Edge(ex.vec(-100, 30), ex.vec(100, 30)); const circle = ex.Shape.Circle(30); const contact = circle.collide(edge)[0]; - expect(contact.normal).withContext('Circle/Edge normals point away from circle').toBeVector(ex.Vector.Down); + expect(contact.normal, 'Circle/Edge normals point away from circle').toBeVector(ex.Vector.Down); expect(contact.points[0]).toBeVector(ex.vec(0, 30)); expect(contact.info.collider).toBe(circle); expect(contact.info.point).toBeVector(ex.vec(0, 30)); const separation = CollisionJumpTable.FindContactSeparation(contact, ex.vec(0, 40)); - expect(separation).withContext('Negative separation means overlap').toBe(-10); + expect(separation, 'Negative separation means overlap').toBe(-10); }); it('can collide with a circle, left edge', () => { const edge = ex.Shape.Edge(ex.vec(30, 0), ex.vec(100, 0)); const circle = ex.Shape.Circle(30); const contact = circle.collide(edge)[0]; - expect(contact.normal).withContext('Circle/Edge normals point away from circle').toBeVector(ex.Vector.Right); + expect(contact.normal, 'Circle/Edge normals point away from circle').toBeVector(ex.Vector.Right); expect(contact.points[0]).toBeVector(ex.vec(30, 0)); expect(contact.info.collider).toBe(circle); expect(contact.info.point).toBeVector(ex.vec(30, 0)); @@ -1154,7 +1147,7 @@ describe('Collision Shape', () => { const edge = ex.Shape.Edge(ex.vec(-100, 0), ex.vec(-30, 0)); const circle = ex.Shape.Circle(30); const contact = circle.collide(edge)[0]; - expect(contact.normal).withContext('Circle/Edge normals point away from circle').toBeVector(ex.Vector.Left); + expect(contact.normal, 'Circle/Edge normals point away from circle').toBeVector(ex.Vector.Left); expect(contact.points[0]).toBeVector(ex.vec(-30, 0)); expect(contact.info.collider).toBe(circle); expect(contact.info.point).toBeVector(ex.vec(-30, 0)); @@ -1167,7 +1160,7 @@ describe('Collision Shape', () => { const edge = ex.Shape.Edge(ex.vec(-100, -30), ex.vec(100, -30)); const circle = ex.Shape.Circle(30); const contact = circle.collide(edge)[0]; - expect(contact.normal).withContext('Circle/Edge normals point away from circle').toBeVector(ex.Vector.Up); + expect(contact.normal, 'Circle/Edge normals point away from circle').toBeVector(ex.Vector.Up); expect(contact.points[0]).toBeVector(ex.vec(0, -30)); expect(contact.info.collider).toBe(circle); expect(contact.info.point).toBeVector(ex.vec(0, -30)); @@ -1180,7 +1173,7 @@ describe('Collision Shape', () => { const edge = ex.Shape.Edge(ex.vec(-100, 10), ex.vec(100, 10)); const rect = ex.Shape.Box(40, 20, ex.Vector.Half); const contact = rect.collide(edge)[0]; - expect(contact.normal).withContext('Rect/Edge normal point away from edge').toBeVector(ex.Vector.Down); + expect(contact.normal, 'Rect/Edge normal point away from edge').toBeVector(ex.Vector.Down); expect(contact.points[0]).toBeVector(ex.vec(20, 10)); expect(contact.points[1]).toBeVector(ex.vec(-20, 10)); @@ -1192,7 +1185,7 @@ describe('Collision Shape', () => { const edge = ex.Shape.Edge(ex.vec(10, 10), ex.vec(100, 10)); const rect = ex.Shape.Box(40, 20, ex.Vector.Half); const contact = rect.collide(edge)[0]; - expect(contact.normal).withContext('Rect/Edge normal point away from edge').toBeVector(ex.Vector.Down); + expect(contact.normal, 'Rect/Edge normal point away from edge').toBeVector(ex.Vector.Down); expect(contact.points[0]).toBeVector(ex.vec(20, 10)); expect(contact.points[1]).toBeVector(ex.vec(10, 10)); @@ -1204,7 +1197,7 @@ describe('Collision Shape', () => { const edge = ex.Shape.Edge(ex.vec(-100, 10), ex.vec(0, 10)); const rect = ex.Shape.Box(40, 20, ex.Vector.Half); const contact = rect.collide(edge)[0]; - expect(contact.normal).withContext('Rect/Edge normal point away from edge').toBeVector(ex.Vector.Down); + expect(contact.normal, 'Rect/Edge normal point away from edge').toBeVector(ex.Vector.Down); expect(contact.points[0]).toBeVector(ex.vec(-20, 10)); expect(contact.points[1]).toBeVector(ex.vec(0, 10)); @@ -1228,7 +1221,7 @@ describe('Collision Shape', () => { it('will warn if should use a circle', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); const sut = ex.Shape.Capsule(100, 100); expect(logger.warn).toHaveBeenCalledWith( 'A capsule collider with equal width and height is a circle, consider using a ex.Shape.Circle or ex.CircleCollider' diff --git a/src/spec/CollisionSpec.ts b/src/spec/vitest/CollisionSpec.ts similarity index 57% rename from src/spec/CollisionSpec.ts rename to src/spec/vitest/CollisionSpec.ts index 0bc956b8..47e09a73 100644 --- a/src/spec/CollisionSpec.ts +++ b/src/spec/vitest/CollisionSpec.ts @@ -1,6 +1,6 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; -import { getDefaultPhysicsConfig } from '../engine/Collision/PhysicsConfig'; +import { getDefaultPhysicsConfig } from '../../engine/Collision/PhysicsConfig'; describe('A Collision', () => { let actor1: ex.Actor = null; @@ -195,142 +195,145 @@ describe('A Collision', () => { expect(touching).toBe(true); }); - it('should not collide when active and passive', (done) => { - engine.stop(); - engine.dispose(); - engine = TestUtils.engine({ - width: 600, - height: 400, - physics: { - solver: ex.SolverStrategy.Realistic - } - }); - clock = engine.clock = engine.clock.toTestClock(); - - actor1 = new ex.Actor({ x: 0, y: 0, width: 10, height: 10 }); - actor2 = new ex.Actor({ x: 5, y: 5, width: 10, height: 10 }); - actor1.body.collisionType = ex.CollisionType.Active; - actor2.body.collisionType = ex.CollisionType.Active; - - engine.start().then(() => { - engine.add(actor1); - engine.add(actor2); - - const activeBlock = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); - activeBlock.body.collisionType = ex.CollisionType.Active; - activeBlock.vel.x = 100; - engine.add(activeBlock); - - const passiveBlock = new ex.Actor({ x: 400, y: 200, width: 50, height: 50, color: ex.Color.DarkGray.clone() }); - passiveBlock.body.collisionType = ex.CollisionType.Passive; - passiveBlock.vel.x = -100; - engine.add(passiveBlock); - - const collisionHandler = (ev: ex.PreCollisionEvent) => { - const timer = new ex.Timer({ - interval: 30, - fcn: () => { - expect(activeBlock.vel.x).toBeGreaterThan(0); - expect(passiveBlock.vel.x).toBeLessThan(0); - done(); - }, - repeats: false - }); - timer.start(); - engine.add(timer); - }; - - activeBlock.once('precollision', collisionHandler); - - clock.run(5, 1000); - }); - }); - - it('should emit a start collision once when objects start colliding', (done) => { - engine.stop(); - engine.dispose(); - engine = TestUtils.engine({ - width: 600, - height: 400, - physics: { - solver: ex.SolverStrategy.Realistic - } - }); - clock = engine.clock = engine.clock.toTestClock(); - - actor1 = new ex.Actor({ x: 0, y: 0, width: 10, height: 10 }); - actor2 = new ex.Actor({ x: 5, y: 5, width: 10, height: 10 }); - actor1.body.collisionType = ex.CollisionType.Active; - actor2.body.collisionType = ex.CollisionType.Active; - - engine.start().then(() => { - const activeBlock = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); - activeBlock.body.collisionType = ex.CollisionType.Active; - activeBlock.vel.x = 100; - engine.add(activeBlock); - - const passiveBlock = new ex.Actor({ x: 400, y: 200, width: 50, height: 50, color: ex.Color.DarkGray.clone() }); - passiveBlock.body.collisionType = ex.CollisionType.Passive; - passiveBlock.vel.x = -100; - engine.add(passiveBlock); - - let count = 0; - - const collisionStart = () => { - count++; - }; - - activeBlock.on('collisionstart', collisionStart); - - clock.run(5, 1000); - - expect(count).toBe(1); - done(); - }); - }); - - it('should emit a end collision once when objects stop colliding', (done) => { - engine.stop(); - engine.dispose(); - engine = TestUtils.engine({ - width: 600, - height: 400, - physics: { - solver: ex.SolverStrategy.Realistic - } - }); - clock = engine.clock = engine.clock.toTestClock(); - - actor1 = new ex.Actor({ x: 0, y: 0, width: 10, height: 10 }); - actor2 = new ex.Actor({ x: 5, y: 5, width: 10, height: 10 }); - actor1.body.collisionType = ex.CollisionType.Active; - actor2.body.collisionType = ex.CollisionType.Active; - - engine.start().then(() => { - const activeBlock = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); - activeBlock.body.collisionType = ex.CollisionType.Active; - activeBlock.vel.x = 100; - engine.add(activeBlock); - - const passiveBlock = new ex.Actor({ x: 400, y: 200, width: 50, height: 50, color: ex.Color.DarkGray.clone() }); - passiveBlock.body.collisionType = ex.CollisionType.Passive; - passiveBlock.vel.x = -100; - engine.add(passiveBlock); - - let count = 0; - - const collisionEnd = () => { - count++; - }; - - activeBlock.on('collisionend', collisionEnd); - - clock.run(5, 1000); - - expect(count).toBe(1); - done(); - }); - }); + it('should not collide when active and passive', () => + new Promise((done) => { + engine.stop(); + engine.dispose(); + engine = TestUtils.engine({ + width: 600, + height: 400, + physics: { + solver: ex.SolverStrategy.Realistic + } + }); + clock = engine.clock = engine.clock.toTestClock(); + + actor1 = new ex.Actor({ x: 0, y: 0, width: 10, height: 10 }); + actor2 = new ex.Actor({ x: 5, y: 5, width: 10, height: 10 }); + actor1.body.collisionType = ex.CollisionType.Active; + actor2.body.collisionType = ex.CollisionType.Active; + + engine.start().then(() => { + engine.add(actor1); + engine.add(actor2); + + const activeBlock = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); + activeBlock.body.collisionType = ex.CollisionType.Active; + activeBlock.vel.x = 100; + engine.add(activeBlock); + + const passiveBlock = new ex.Actor({ x: 400, y: 200, width: 50, height: 50, color: ex.Color.DarkGray.clone() }); + passiveBlock.body.collisionType = ex.CollisionType.Passive; + passiveBlock.vel.x = -100; + engine.add(passiveBlock); + + const collisionHandler = (ev: ex.PreCollisionEvent) => { + const timer = new ex.Timer({ + interval: 30, + fcn: () => { + expect(activeBlock.vel.x).toBeGreaterThan(0); + expect(passiveBlock.vel.x).toBeLessThan(0); + done(); + }, + repeats: false + }); + timer.start(); + engine.add(timer); + }; + + activeBlock.once('precollision', collisionHandler); + + clock.run(5, 1000); + }); + })); + + it('should emit a start collision once when objects start colliding', () => + new Promise((done) => { + engine.stop(); + engine.dispose(); + engine = TestUtils.engine({ + width: 600, + height: 400, + physics: { + solver: ex.SolverStrategy.Realistic + } + }); + clock = engine.clock = engine.clock.toTestClock(); + + actor1 = new ex.Actor({ x: 0, y: 0, width: 10, height: 10 }); + actor2 = new ex.Actor({ x: 5, y: 5, width: 10, height: 10 }); + actor1.body.collisionType = ex.CollisionType.Active; + actor2.body.collisionType = ex.CollisionType.Active; + + engine.start().then(() => { + const activeBlock = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); + activeBlock.body.collisionType = ex.CollisionType.Active; + activeBlock.vel.x = 100; + engine.add(activeBlock); + + const passiveBlock = new ex.Actor({ x: 400, y: 200, width: 50, height: 50, color: ex.Color.DarkGray.clone() }); + passiveBlock.body.collisionType = ex.CollisionType.Passive; + passiveBlock.vel.x = -100; + engine.add(passiveBlock); + + let count = 0; + + const collisionStart = () => { + count++; + }; + + activeBlock.on('collisionstart', collisionStart); + + clock.run(5, 1000); + + expect(count).toBe(1); + done(); + }); + })); + + it('should emit a end collision once when objects stop colliding', () => + new Promise((done) => { + engine.stop(); + engine.dispose(); + engine = TestUtils.engine({ + width: 600, + height: 400, + physics: { + solver: ex.SolverStrategy.Realistic + } + }); + clock = engine.clock = engine.clock.toTestClock(); + + actor1 = new ex.Actor({ x: 0, y: 0, width: 10, height: 10 }); + actor2 = new ex.Actor({ x: 5, y: 5, width: 10, height: 10 }); + actor1.body.collisionType = ex.CollisionType.Active; + actor2.body.collisionType = ex.CollisionType.Active; + + engine.start().then(() => { + const activeBlock = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); + activeBlock.body.collisionType = ex.CollisionType.Active; + activeBlock.vel.x = 100; + engine.add(activeBlock); + + const passiveBlock = new ex.Actor({ x: 400, y: 200, width: 50, height: 50, color: ex.Color.DarkGray.clone() }); + passiveBlock.body.collisionType = ex.CollisionType.Passive; + passiveBlock.vel.x = -100; + engine.add(passiveBlock); + + let count = 0; + + const collisionEnd = () => { + count++; + }; + + activeBlock.on('collisionend', collisionEnd); + + clock.run(5, 1000); + + expect(count).toBe(1); + done(); + }); + })); it('should cancel out velocity when objects collide', () => { engine.currentScene.clear(); @@ -364,79 +367,81 @@ describe('A Collision', () => { expect(activeBlock.vel.x).toBe(-100); }); - it('should have the actor as the handler context for collisionstart', (done) => { - engine.stop(); - engine.dispose(); - engine = TestUtils.engine({ - width: 600, - height: 400, - physics: { - solver: ex.SolverStrategy.Realistic - } - }); - clock = engine.clock = engine.clock.toTestClock(); - - actor1 = new ex.Actor({ x: 0, y: 0, width: 10, height: 10 }); - actor2 = new ex.Actor({ x: 5, y: 5, width: 10, height: 10 }); - actor1.body.collisionType = ex.CollisionType.Active; - actor2.body.collisionType = ex.CollisionType.Active; - - engine.start().then(() => { - const activeBlock = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); - activeBlock.body.collisionType = ex.CollisionType.Active; - activeBlock.vel.x = 100; - engine.add(activeBlock); - - const passiveBlock = new ex.Actor({ x: 400, y: 200, width: 50, height: 50, color: ex.Color.DarkGray.clone() }); - passiveBlock.body.collisionType = ex.CollisionType.Passive; - passiveBlock.vel.x = -100; - engine.add(passiveBlock); - - const collisionEnd = function (event: ex.GameEvent) { - expect((event as any).self.owner).toBe(activeBlock); - done(); - }; - - activeBlock.on('collisionstart', collisionEnd); - - clock.run(5, 1000); - }); - }); - - it('should have the actor as the handler context for collisionend', (done) => { - engine.stop(); - engine.dispose(); - engine = TestUtils.engine({ - width: 600, - height: 400, - physics: { - solver: ex.SolverStrategy.Realistic - } - }); - clock = engine.clock as ex.TestClock; - clock.start(); - clock.step(1); - - TestUtils.runToReady(engine).then(() => { - const activeBlock = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); - activeBlock.body.collisionType = ex.CollisionType.Active; - activeBlock.vel.x = 100; - engine.add(activeBlock); - - const passiveBlock = new ex.Actor({ x: 400, y: 200, width: 50, height: 50, color: ex.Color.DarkGray.clone() }); - passiveBlock.body.collisionType = ex.CollisionType.Passive; - passiveBlock.vel.x = -100; - engine.add(passiveBlock); - - const collisionEnd = function (event: ex.GameEvent) { - expect((event as any).self.owner).toBe(activeBlock); - done(); - }; - - activeBlock.on('collisionend', collisionEnd); - clock.run(5, 1000); - }); - }); + it('should have the actor as the handler context for collisionstart', () => + new Promise((done) => { + engine.stop(); + engine.dispose(); + engine = TestUtils.engine({ + width: 600, + height: 400, + physics: { + solver: ex.SolverStrategy.Realistic + } + }); + clock = engine.clock = engine.clock.toTestClock(); + + actor1 = new ex.Actor({ x: 0, y: 0, width: 10, height: 10 }); + actor2 = new ex.Actor({ x: 5, y: 5, width: 10, height: 10 }); + actor1.body.collisionType = ex.CollisionType.Active; + actor2.body.collisionType = ex.CollisionType.Active; + + engine.start().then(() => { + const activeBlock = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); + activeBlock.body.collisionType = ex.CollisionType.Active; + activeBlock.vel.x = 100; + engine.add(activeBlock); + + const passiveBlock = new ex.Actor({ x: 400, y: 200, width: 50, height: 50, color: ex.Color.DarkGray.clone() }); + passiveBlock.body.collisionType = ex.CollisionType.Passive; + passiveBlock.vel.x = -100; + engine.add(passiveBlock); + + const collisionEnd = function (event: ex.GameEvent) { + expect((event as any).self.owner).toBe(activeBlock); + done(); + }; + + activeBlock.on('collisionstart', collisionEnd); + + clock.run(5, 1000); + }); + })); + + it('should have the actor as the handler context for collisionend', () => + new Promise((done) => { + engine.stop(); + engine.dispose(); + engine = TestUtils.engine({ + width: 600, + height: 400, + physics: { + solver: ex.SolverStrategy.Realistic + } + }); + clock = engine.clock as ex.TestClock; + clock.start(); + clock.step(1); + + TestUtils.runToReady(engine).then(() => { + const activeBlock = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); + activeBlock.body.collisionType = ex.CollisionType.Active; + activeBlock.vel.x = 100; + engine.add(activeBlock); + + const passiveBlock = new ex.Actor({ x: 400, y: 200, width: 50, height: 50, color: ex.Color.DarkGray.clone() }); + passiveBlock.body.collisionType = ex.CollisionType.Passive; + passiveBlock.vel.x = -100; + engine.add(passiveBlock); + + const collisionEnd = function (event: ex.GameEvent) { + expect((event as any).self.owner).toBe(activeBlock); + done(); + }; + + activeBlock.on('collisionend', collisionEnd); + clock.run(5, 1000); + }); + })); it('should not fire onCollisionStart if the collision has been canceled', () => { const block1 = new ex.Actor({ x: 200, y: 200, width: 50, height: 50, color: ex.Color.Red.clone() }); @@ -448,11 +453,11 @@ describe('A Collision', () => { block2.body.collisionType = ex.CollisionType.Fixed; block2.vel.x = -100; - block1.onCollisionStart = jasmine.createSpy('onCollisionStart'); + block1.onCollisionStart = vi.fn(); block2.onPreCollisionResolve = (self, other, side, contact) => { contact.cancel(); }; - spyOn(block2, 'onPreCollisionResolve').and.callThrough(); + vi.spyOn(block2, 'onPreCollisionResolve'); engine.add(block1); engine.add(block2); @@ -490,8 +495,8 @@ describe('A Collision', () => { }); engine.add(fixedBlock); - const collisionStart = jasmine.createSpy('collisionstart'); - const collisionEnd = jasmine.createSpy('collisionend'); + const collisionStart = vi.fn(); + const collisionEnd = vi.fn(); activeBlock.on('collisionstart', collisionStart); activeBlock.on('collisionend', collisionEnd); diff --git a/src/spec/vitest/ColorBlindCorrectorSpec.ts b/src/spec/vitest/ColorBlindCorrectorSpec.ts new file mode 100644 index 00000000..41746d24 --- /dev/null +++ b/src/spec/vitest/ColorBlindCorrectorSpec.ts @@ -0,0 +1,133 @@ +import * as ex from '@excalibur'; +import { TestUtils } from './util/TestUtils'; + +describe('A ColorBlindCorrector', () => { + let bg: ex.ImageSource; + let engine: ex.Engine; + let clock: ex.TestClock; + + beforeEach(async () => { + engine = TestUtils.engine({ width: 800, height: 200 }, []); + bg = new ex.ImageSource('/src/spec/assets/images/ColorBlindCorrectorSpec/actor.png'); + const loader = new ex.Loader([bg]); + clock = engine.clock as ex.TestClock; + await TestUtils.runToReady(engine, loader); + }); + + afterEach(() => { + engine.stop(); + engine.dispose(); + }); + + it('is normal', () => + new Promise((done) => { + const actor = new ex.Actor(); + actor.graphics.use(bg.toSprite()); + engine.add(actor); + + engine.once('postframe', (ev: ex.PostDrawEvent) => { + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/ColorBlindCorrectorSpec/normal.png') + .then(() => { + done(); + }); + }); + clock.step(1); + })); + + it('corrects deuteranopia', () => + new Promise((done) => { + const actor = new ex.Actor(); + actor.graphics.use(bg.toSprite()); + engine.add(actor); + engine.debug.colorBlindMode.correct(ex.ColorBlindnessMode.Deuteranope); + engine.once('postframe', (ev: ex.PostDrawEvent) => { + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/ColorBlindCorrectorSpec/deuteranope_correct.png') + .then(() => { + done(); + }); + }); + clock.step(1); + })); + + it('simulates deuteranopia', () => + new Promise((done) => { + const actor = new ex.Actor(); + actor.graphics.use(bg.toSprite()); + engine.add(actor); + engine.debug.colorBlindMode.simulate(ex.ColorBlindnessMode.Deuteranope); + engine.once('postframe', (ev: ex.PostDrawEvent) => { + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/ColorBlindCorrectorSpec/deuteranope_simulate.png') + .then(() => { + done(); + }); + }); + clock.step(1); + })); + + it('corrects protanopia', () => + new Promise((done) => { + const actor = new ex.Actor(); + actor.graphics.use(bg.toSprite()); + engine.add(actor); + engine.debug.colorBlindMode.correct(ex.ColorBlindnessMode.Protanope); + engine.once('postframe', (ev: ex.PostDrawEvent) => { + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/ColorBlindCorrectorSpec/protanope_correct.png') + .then(() => { + done(); + }); + }); + clock.step(1); + })); + + it('simulates protanopia', () => + new Promise((done) => { + const actor = new ex.Actor(); + actor.graphics.use(bg.toSprite()); + engine.add(actor); + engine.debug.colorBlindMode.simulate(ex.ColorBlindnessMode.Protanope); + engine.once('postframe', (ev: ex.PostDrawEvent) => { + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/ColorBlindCorrectorSpec/protanope_simulate.png') + .then(() => { + done(); + }); + }); + clock.step(1); + })); + + it('corrects tritanopia', () => + new Promise((done) => { + const actor = new ex.Actor(); + actor.graphics.use(bg.toSprite()); + engine.add(actor); + engine.debug.colorBlindMode.correct(ex.ColorBlindnessMode.Tritanope); + engine.once('postframe', (ev: ex.PostDrawEvent) => { + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/ColorBlindCorrectorSpec/tritanope_correct.png') + .then(() => { + done(); + }); + }); + clock.step(1); + })); + + it('simulates tritanopia', () => + new Promise((done) => { + const actor = new ex.Actor(); + actor.graphics.use(bg.toSprite()); + engine.add(actor); + engine.debug.colorBlindMode.simulate(ex.ColorBlindnessMode.Tritanope); + engine.once('postframe', (ev: ex.PostDrawEvent) => { + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/ColorBlindCorrectorSpec/tritanope_simulate.png') + .then(() => { + done(); + }); + }); + clock.step(1); + })); +}); diff --git a/src/spec/ColorSpec.ts b/src/spec/vitest/ColorSpec.ts similarity index 89% rename from src/spec/ColorSpec.ts rename to src/spec/vitest/ColorSpec.ts index 5d6275bb..39023fd6 100644 --- a/src/spec/ColorSpec.ts +++ b/src/spec/vitest/ColorSpec.ts @@ -122,29 +122,29 @@ describe('A color', () => { it('can be darkened', () => { color = ex.Color.White.clone(); color = color.darken(); - expect(color.r).toBe(229.5, 'r'); - expect(color.g).toBe(229.5, 'g'); - expect(color.b).toBe(229.5, 'b'); + expect(color.r, 'r').toBe(229.5); + expect(color.g, 'g').toBe(229.5); + expect(color.b, 'b').toBe(229.5); }); it('can be lightened', () => { color = ex.Color.Black.clone(); color = color.lighten(); - expect(color.r).toBe(25.5, 'r'); - expect(color.g).toBe(25.5, 'g'); - expect(color.b).toBe(25.5, 'b'); + expect(color.r, 'r').toBe(25.5); + expect(color.g, 'g').toBe(25.5); + expect(color.b, 'b').toBe(25.5); color = ex.Color.White.clone(); color = color.lighten(); - expect(color.r).toBe(255, 'r'); - expect(color.g).toBe(255, 'g'); - expect(color.b).toBe(255, 'b'); + expect(color.r, 'r').toBe(255); + expect(color.g, 'g').toBe(255); + expect(color.b, 'b').toBe(255); }); it('can be averaged', () => { color = ex.Color.White.average(ex.Color.Black); - expect(color.r).toBe(255 / 2, 'r'); - expect(color.g).toBe(255 / 2, 'g'); - expect(color.b).toBe(255 / 2, 'b'); + expect(color.r, 'r').toBe(255 / 2); + expect(color.g, 'g').toBe(255 / 2); + expect(color.b, 'b').toBe(255 / 2); }); }); diff --git a/src/spec/ComponentSpec.ts b/src/spec/vitest/ComponentSpec.ts similarity index 95% rename from src/spec/ComponentSpec.ts rename to src/spec/vitest/ComponentSpec.ts index 5a3e4972..b7e25365 100644 --- a/src/spec/ComponentSpec.ts +++ b/src/spec/vitest/ComponentSpec.ts @@ -9,8 +9,8 @@ class ComponentImplementation extends ex.Component { super(); } - onAdd = jasmine.createSpy(); - onRemove = jasmine.createSpy(); + onAdd = vi.fn(); + onRemove = vi.fn(); } describe('A Component', () => { diff --git a/src/spec/CompositeColliderSpec.ts b/src/spec/vitest/CompositeColliderSpec.ts similarity index 90% rename from src/spec/CompositeColliderSpec.ts rename to src/spec/vitest/CompositeColliderSpec.ts index c7ab6212..83cd2684 100644 --- a/src/spec/CompositeColliderSpec.ts +++ b/src/spec/vitest/CompositeColliderSpec.ts @@ -1,12 +1,9 @@ import * as ex from '@excalibur'; import { BoundingBox, GameEvent, LineSegment, Projection, Ray, vec, Vector } from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; -import { getDefaultPhysicsConfig } from '../engine/Collision/PhysicsConfig'; + +import { getDefaultPhysicsConfig } from '../../engine/Collision/PhysicsConfig'; + describe('A CompositeCollider', () => { - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - jasmine.addMatchers(ExcaliburMatchers); - }); it('exists', () => { expect(ex.CompositeCollider).toBeDefined(); }); @@ -25,10 +22,10 @@ describe('A CompositeCollider', () => { it('can forward events from the individual colliders', () => { const circle = ex.Shape.Circle(50); const box = ex.Shape.Box(200, 10); - const precollision = jasmine.createSpy('event'); - const postcollision = jasmine.createSpy('event'); - const collisionstart = jasmine.createSpy('event'); - const collisionend = jasmine.createSpy('event'); + const precollision = vi.fn(); + const postcollision = vi.fn(); + const collisionstart = vi.fn(); + const collisionend = vi.fn(); const compCollider = new ex.CompositeCollider([circle, box]); @@ -54,10 +51,10 @@ describe('A CompositeCollider', () => { const down = compCollider.getFurthestPoint(Vector.Down); const left = compCollider.getFurthestPoint(Vector.Left); const right = compCollider.getFurthestPoint(Vector.Right); - expect(up).withContext('Top of the circle is (0, -50)').toBeVector(vec(0, -50)); - expect(down).withContext('Bottom of the circle is (0, 50)').toBeVector(vec(0, 50)); - expect(left).withContext('Upper Left of the box is (-100, -5)').toBeVector(vec(-100, -5)); - expect(right).withContext('Upper Right of the box is (-5, 100)').toBeVector(vec(100, -5)); + expect(up, 'Top of the circle is (0, -50)').toBeVector(vec(0, -50)); + expect(down, 'Bottom of the circle is (0, 50)').toBeVector(vec(0, 50)); + expect(left, 'Upper Left of the box is (-100, -5)').toBeVector(vec(-100, -5)); + expect(right, 'Upper Right of the box is (-5, 100)').toBeVector(vec(100, -5)); }); it('sums the inertia of the shapes', () => { @@ -130,13 +127,13 @@ describe('A CompositeCollider', () => { const contactBoxCircle = compCollider.collide(circle); expect(contactBoxCircle.length).toBe(1); - expect(contactBoxCircle[0].points[0]).withContext('Right edge of the box in comp').toEqual(vec(99, 0)); + expect(contactBoxCircle[0].points[0], 'Right edge of the box in comp').toEqual(vec(99, 0)); xf.pos = vec(0, -100); circle.update(xf); const contactCircleCircle = compCollider.collide(circle); expect(contactCircleCircle.length).toBe(1); - expect(contactCircleCircle[0].points[0]).withContext('Top of the circle in comp').toEqual(vec(0, -50)); + expect(contactCircleCircle[0].points[0], 'Top of the circle in comp').toEqual(vec(0, -50)); }); it('creates contacts that have the composite collider id', () => { @@ -183,9 +180,7 @@ describe('A CompositeCollider', () => { const contacts = compCollider1.collide(compCollider2); expect(contacts.length).toBe(1); - expect(contacts[0].points) - .withContext('Right edge of comp1 poly') - .toEqual([vec(100, 5), vec(100, -5)]); + expect(contacts[0].points, 'Right edge of comp1 poly').toEqual([vec(100, 5), vec(100, -5)]); }); it('returns empty on no contacts', () => { @@ -274,7 +269,7 @@ describe('A CompositeCollider', () => { ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/CompositeColliderSpec/composite.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/CompositeColliderSpec/composite.png'); }); it('is separated into a series of colliders in the dynamic tree', () => { diff --git a/src/spec/ContextSpec.ts b/src/spec/vitest/ContextSpec.ts similarity index 95% rename from src/spec/ContextSpec.ts rename to src/spec/vitest/ContextSpec.ts index d8893251..c5279093 100644 --- a/src/spec/ContextSpec.ts +++ b/src/spec/vitest/ContextSpec.ts @@ -1,4 +1,4 @@ -import { createContext, useContext } from '../../src/engine/Context'; +import { createContext, useContext } from '../../../src/engine/Context'; describe('A Context', () => { it('creates a context', () => { diff --git a/src/spec/CoroutineSpec.ts b/src/spec/vitest/CoroutineSpec.ts similarity index 81% rename from src/spec/CoroutineSpec.ts rename to src/spec/vitest/CoroutineSpec.ts index 16a1191c..5dd3626d 100644 --- a/src/spec/CoroutineSpec.ts +++ b/src/spec/vitest/CoroutineSpec.ts @@ -2,12 +2,20 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; describe('A Coroutine', () => { + let engine: ex.Engine; + + afterEach(async () => { + if (engine) { + engine.dispose(); + } + }); + it('exists', () => { expect(ex.coroutine).toBeDefined(); }); it('can be run', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); @@ -19,8 +27,7 @@ describe('A Coroutine', () => { }); clock.step(100); clock.step(100); - await expectAsync(result).toBeResolved(); - engine.dispose(); + await expect(result).resolves.toBeUndefined(); }); }); @@ -41,7 +48,7 @@ describe('A Coroutine', () => { }); it('can bind a this arg overload 1', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); @@ -54,13 +61,12 @@ describe('A Coroutine', () => { }); clock.step(100); clock.step(100); - await expectAsync(result).toBeResolved(); - engine.dispose(); + await expect(result).resolves.toBeUndefined(); }); }); it('can bind a this arg overload 2', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); @@ -73,13 +79,12 @@ describe('A Coroutine', () => { }); clock.step(100); clock.step(100); - await expectAsync(result).toBeResolved(); - engine.dispose(); + await expect(result).resolves.toBeUndefined(); }); }); it('can run overload 2', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); @@ -91,18 +96,17 @@ describe('A Coroutine', () => { }); clock.step(100); clock.step(100); - await expectAsync(result).toBeResolved(); - engine.dispose(); + await expect(result).resolves.toBeUndefined(); }); }); it('can be run on scheduled timing', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); - const calls = jasmine.createSpy('calls'); + const calls = vi.fn(); const preframe = ex.coroutine( function* () { @@ -166,19 +170,18 @@ describe('A Coroutine', () => { clock.step(100); clock.step(100); - expect(calls.calls.allArgs()).toEqual([['preframe'], ['preupdate'], ['postupdate'], ['predraw'], ['postdraw'], ['postframe']]); - await expectAsync(preframe).toBeResolved(); - await expectAsync(preupdate).toBeResolved(); - await expectAsync(postupdate).toBeResolved(); - await expectAsync(predraw).toBeResolved(); - await expectAsync(postdraw).toBeResolved(); - await expectAsync(postframe).toBeResolved(); + expect(calls.mock.calls).toEqual([['preframe'], ['preupdate'], ['postupdate'], ['predraw'], ['postdraw'], ['postframe']]); + await expect(preframe).resolves.toBeUndefined(); + await expect(preupdate).resolves.toBeUndefined(); + await expect(postupdate).resolves.toBeUndefined(); + await expect(predraw).resolves.toBeUndefined(); + await expect(postdraw).resolves.toBeUndefined(); + await expect(postframe).resolves.toBeUndefined(); }); - engine.dispose(); }); it('can wait for given ms', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); const clock = engine.clock as ex.TestClock; clock.start(); await engine.scope(async () => { @@ -191,13 +194,12 @@ describe('A Coroutine', () => { clock.step(200); // 1 more yield clock.step(100); - await expectAsync(result).toBeResolved(); + await expect(result).resolves.toBeUndefined(); }); - engine.dispose(); }); it('can wait for a promise', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); @@ -215,13 +217,12 @@ describe('A Coroutine', () => { // 1 more yield clock.step(100); - await expectAsync(result).toBeResolved(); + await expect(result).resolves.toBeUndefined(); }); - engine.dispose(); }); it('can throw error', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); @@ -240,13 +241,12 @@ describe('A Coroutine', () => { // 1 more yield clock.step(100); - await expectAsync(result).toBeRejectedWithError('error here'); - engine.dispose(); + await expect(result).rejects.toThrowError('error here'); }); }); it('can stop coroutines', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); @@ -264,14 +264,13 @@ describe('A Coroutine', () => { expect(result.isRunning()).toBe(false); clock.step(100); expect(result.isRunning()).toBe(false); - engine.dispose(); }); }); it('can start coroutines', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); @@ -295,12 +294,11 @@ describe('A Coroutine', () => { clock.step(100); expect(result.isRunning()).toBe(false); expect(result.isComplete()).toBe(true); - engine.dispose(); }); }); it('can have nested coroutines', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); @@ -322,7 +320,7 @@ describe('A Coroutine', () => { }); it('can iterate over coroutines', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); @@ -349,7 +347,7 @@ describe('A Coroutine', () => { }); it('can iterate over coroutines', async () => { - const engine = TestUtils.engine({ width: 100, height: 100 }); + engine = TestUtils.engine({ width: 100, height: 100 }); await engine.scope(async () => { const clock = engine.clock as ex.TestClock; clock.start(); diff --git a/src/spec/CrossFadeSpec.ts b/src/spec/vitest/CrossFadeSpec.ts similarity index 83% rename from src/spec/CrossFadeSpec.ts rename to src/spec/vitest/CrossFadeSpec.ts index a3982e56..b4ef5588 100644 --- a/src/spec/CrossFadeSpec.ts +++ b/src/spec/vitest/CrossFadeSpec.ts @@ -1,11 +1,7 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; -import { ExcaliburAsyncMatchers } from 'excalibur-jasmine'; describe('A CrossFade transition', () => { - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); it('exists', () => { expect(ex.CrossFade).toBeDefined(); }); @@ -38,7 +34,7 @@ describe('A CrossFade transition', () => { return await future.promise; } - xit('can cross fade', async () => { + it.skip('can cross fade', async () => { const engine = TestUtils.engine({ backgroundColor: ex.Color.ExcaliburBlue }); const clock = engine.clock as ex.TestClock; await TestUtils.runToReady(engine); @@ -51,9 +47,7 @@ describe('A CrossFade transition', () => { }) ); - const onDeactivateSpy = jasmine.createSpy('onDeactivate').and.callFake(async () => { - await Promise.resolve(); - }); + const onDeactivateSpy = vi.fn(() => Promise.resolve()); engine.director.getSceneInstance('root').onDeactivate = onDeactivateSpy; @@ -89,6 +83,6 @@ describe('A CrossFade transition', () => { expect(engine.currentSceneName).toBe('newScene'); expect(onDeactivateSpy).toHaveBeenCalledTimes(1); - await expectAsync(engine.canvas).toEqualImage('/src/spec/images/CrossFadeSpec/crossfade.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/CrossFadeSpec/crossfade.png'); }); }); diff --git a/src/spec/CurveActionSpec.ts b/src/spec/vitest/CurveActionSpec.ts similarity index 94% rename from src/spec/CurveActionSpec.ts rename to src/spec/vitest/CurveActionSpec.ts index c7184150..7697a673 100644 --- a/src/spec/CurveActionSpec.ts +++ b/src/spec/vitest/CurveActionSpec.ts @@ -1,12 +1,8 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; + import { TestUtils } from './util/TestUtils'; describe('A actor can curve', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); - let engine: ex.Engine; let clock: ex.TestClock; beforeEach(async () => { diff --git a/src/spec/DebugSpec.ts b/src/spec/vitest/DebugSpec.ts similarity index 82% rename from src/spec/DebugSpec.ts rename to src/spec/vitest/DebugSpec.ts index 3fc33279..6b071715 100644 --- a/src/spec/DebugSpec.ts +++ b/src/spec/vitest/DebugSpec.ts @@ -1,11 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers } from 'excalibur-jasmine'; describe('Debug draw static', () => { - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - it('exists', () => { expect(ex.Debug).toBeDefined(); }); @@ -32,7 +27,7 @@ describe('Debug draw static', () => { ex.Debug.flush(context); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/DebugSpec/point.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/DebugSpec/point.png'); context.dispose(); }); @@ -51,7 +46,7 @@ describe('Debug draw static', () => { ex.Debug.flush(context); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/DebugSpec/line.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/DebugSpec/line.png'); context.dispose(); }); @@ -70,11 +65,11 @@ describe('Debug draw static', () => { ex.Debug.flush(context); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/DebugSpec/lines.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/DebugSpec/lines.png', 0.99); context.dispose(); }); - xit('can draw text', async () => { + it.skip('can draw text', async () => { const canvas = document.createElement('canvas'); canvas.width = 100; canvas.height = 100; @@ -89,7 +84,7 @@ describe('Debug draw static', () => { ex.Debug.flush(context); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/DebugSpec/text.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/DebugSpec/text.png'); }); it('can draw a polygon', async () => { @@ -107,7 +102,7 @@ describe('Debug draw static', () => { ex.Debug.flush(context); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/DebugSpec/polygon.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/DebugSpec/polygon.png'); context.dispose(); }); @@ -126,7 +121,7 @@ describe('Debug draw static', () => { ex.Debug.flush(context); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/DebugSpec/circle.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/DebugSpec/circle.png'); context.dispose(); }); @@ -152,7 +147,7 @@ describe('Debug draw static', () => { ex.Debug.flush(context); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/DebugSpec/bounds.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/DebugSpec/bounds.png'); context.dispose(); }); @@ -173,7 +168,7 @@ describe('Debug draw static', () => { ex.Debug.flush(context); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/DebugSpec/ray.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/DebugSpec/ray.png'); context.dispose(); }); }); diff --git a/src/spec/DebugSystemSpec.ts b/src/spec/vitest/DebugSystemSpec.ts similarity index 88% rename from src/spec/DebugSystemSpec.ts rename to src/spec/vitest/DebugSystemSpec.ts index f74b3b02..e560fff4 100644 --- a/src/spec/DebugSystemSpec.ts +++ b/src/spec/vitest/DebugSystemSpec.ts @@ -1,11 +1,7 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers } from 'excalibur-jasmine'; import { TestUtils } from './util/TestUtils'; describe('DebugSystem', () => { - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); let engine: ex.Engine; let center: ex.Vector; @@ -76,7 +72,7 @@ describe('DebugSystem', () => { engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/DebugSystemSpec/transform.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/DebugSystemSpec/transform.png'); }); it('can show motion info', async () => { @@ -100,7 +96,7 @@ describe('DebugSystem', () => { engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/DebugSystemSpec/motion.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/DebugSystemSpec/motion.png'); }); it('can show body info', async () => { @@ -122,7 +118,7 @@ describe('DebugSystem', () => { engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/DebugSystemSpec/body.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/DebugSystemSpec/body.png'); }); it('can show collider info', async () => { @@ -143,7 +139,7 @@ describe('DebugSystem', () => { engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/DebugSystemSpec/collider.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/DebugSystemSpec/collider.png'); }); it('can show composite collider info', async () => { @@ -165,7 +161,7 @@ describe('DebugSystem', () => { engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/DebugSystemSpec/composite-collider.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/DebugSystemSpec/composite-collider.png'); }); it('can show graphics info', async () => { @@ -189,7 +185,7 @@ describe('DebugSystem', () => { engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/DebugSystemSpec/graphics.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/DebugSystemSpec/graphics.png'); }); it('can show DebugGraphicsComponent', async () => { @@ -210,7 +206,7 @@ describe('DebugSystem', () => { debugSystem.update(); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/DebugSystemSpec/debug-draw-component.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/DebugSystemSpec/debug-draw-component.png'); }); it('can debug draw a tilemap', async () => { @@ -237,6 +233,6 @@ describe('DebugSystem', () => { debugSystem.update(); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/DebugSystemSpec/tilemap-debug.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/DebugSystemSpec/tilemap-debug.png'); }); }); diff --git a/src/spec/DebugTextSpec.ts b/src/spec/vitest/DebugTextSpec.ts similarity index 73% rename from src/spec/DebugTextSpec.ts rename to src/spec/vitest/DebugTextSpec.ts index c1a799c4..fcf74ae7 100644 --- a/src/spec/DebugTextSpec.ts +++ b/src/spec/vitest/DebugTextSpec.ts @@ -1,11 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers } from 'excalibur-jasmine'; describe('DebugText', () => { - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - it('exists', () => { expect(ex.DebugText); }); @@ -26,7 +21,7 @@ describe('DebugText', () => { ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/DebugTextSpec/draw-canvas2d.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/DebugTextSpec/draw-canvas2d.png'); }); it('can write text (WebGL)', async () => { @@ -45,6 +40,6 @@ describe('DebugText', () => { ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/DebugTextSpec/draw-webgl.png', 0.94); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/DebugTextSpec/draw-webgl.png', 0.94); }); }); diff --git a/src/spec/DecoratorSpec.ts b/src/spec/vitest/DecoratorSpec.ts similarity index 98% rename from src/spec/DecoratorSpec.ts rename to src/spec/vitest/DecoratorSpec.ts index f590917c..c1251fc7 100644 --- a/src/spec/DecoratorSpec.ts +++ b/src/spec/vitest/DecoratorSpec.ts @@ -40,7 +40,7 @@ describe('An @obsolete decorator', () => { ex.Flags.disable('suppress-obsolete-message'); testObsolete = new TestObsolete(); logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); }); afterEach(() => { diff --git a/src/spec/DefaultLoaderSpec.ts b/src/spec/vitest/DefaultLoaderSpec.ts similarity index 68% rename from src/spec/DefaultLoaderSpec.ts rename to src/spec/vitest/DefaultLoaderSpec.ts index d5d875e6..adccfc9a 100644 --- a/src/spec/DefaultLoaderSpec.ts +++ b/src/spec/vitest/DefaultLoaderSpec.ts @@ -1,12 +1,9 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; describe('A DefaultLoader', () => { let engine: ex.Engine; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); engine = TestUtils.engine(); }); @@ -28,7 +25,7 @@ describe('A DefaultLoader', () => { it('is loaded when no resources', async () => { const loader = new ex.DefaultLoader(); expect(loader.isLoaded()).toBe(true); - await expectAsync(loader.areResourcesLoaded()).toBeResolved(); + await expect(loader.areResourcesLoaded()).resolves.toBeUndefined(); }); it('can be constructed with non-defaults', () => { @@ -49,22 +46,22 @@ describe('A DefaultLoader', () => { sut.onUpdate(engine, 100); sut.onDraw(sut.canvas.ctx); expect(sut.resources.length).toBe(3); - await expectAsync(sut.canvas.ctx).toEqualImage('src/spec/images/DefaultLoaderSpec/loading.png'); + await expect(sut.canvas.ctx).toEqualImage('/src/spec/assets/images/DefaultLoaderSpec/loading.png'); }); it('can load stuff', async () => { - const img1 = new ex.ImageSource('src/spec/images/DefaultLoaderSpec/loading.png'); - const img2 = new ex.ImageSource('src/spec/images/DefaultLoaderSpec/loading.png'); + const img1 = new ex.ImageSource('/src/spec/assets/images/DefaultLoaderSpec/loading.png'); + const img2 = new ex.ImageSource('/src/spec/assets/images/DefaultLoaderSpec/loading.png'); const sut = new ex.DefaultLoader({ loadables: [img1, img2] }); sut.onInitialize(engine); - const onBeforeLoadSpy = jasmine.createSpy('onBeforeLoad'); - const onAfterLoadSpy = jasmine.createSpy('onBeforeLoad'); - const onUserAction = jasmine.createSpy('onUserAction'); - const resourceStartLoad = jasmine.createSpy('resourceStartLoad'); - const resourceEndLoad = jasmine.createSpy('resourceStartLoad'); + const onBeforeLoadSpy = vi.fn(); + const onAfterLoadSpy = vi.fn(); + const onUserAction = vi.fn(); + const resourceStartLoad = vi.fn(); + const resourceEndLoad = vi.fn(); sut.on('loadresourcestart', resourceStartLoad); sut.on('loadresourceend', resourceEndLoad); sut.onBeforeLoad = onBeforeLoadSpy; diff --git a/src/spec/DirectorSpec.ts b/src/spec/vitest/DirectorSpec.ts similarity index 96% rename from src/spec/DirectorSpec.ts rename to src/spec/vitest/DirectorSpec.ts index a84c45b6..3aaec26e 100644 --- a/src/spec/DirectorSpec.ts +++ b/src/spec/vitest/DirectorSpec.ts @@ -1,11 +1,7 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; -import { ExcaliburAsyncMatchers } from 'excalibur-jasmine'; describe('A Director', () => { - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); it('exists', () => { expect(ex.Director).toBeDefined(); }); @@ -153,7 +149,7 @@ describe('A Director', () => { expect(sut.currentSceneName).toBe('scene1'); expect(sut.currentScene).toBe(scene1); - await expectAsync(engine.canvas).toEqualImage('/src/spec/images/DirectorSpec/fadein.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/DirectorSpec/fadein.png'); engine.dispose(); }); @@ -162,7 +158,7 @@ describe('A Director', () => { const clock = engine.clock as ex.TestClock; clock.start(); const scene1 = new ex.Scene(); - const loaderSpy = jasmine.createSpy('loader'); + const loaderSpy = vi.fn(); scene1.onPreLoad = loaderSpy; const scene2 = new ex.Scene(); const sut = new ex.Director(engine, { diff --git a/src/spec/DynamicTreeBroadphaseSpec.ts b/src/spec/vitest/DynamicTreeBroadphaseSpec.ts similarity index 98% rename from src/spec/DynamicTreeBroadphaseSpec.ts rename to src/spec/vitest/DynamicTreeBroadphaseSpec.ts index 44f7e1c6..71a864f3 100644 --- a/src/spec/DynamicTreeBroadphaseSpec.ts +++ b/src/spec/vitest/DynamicTreeBroadphaseSpec.ts @@ -1,6 +1,5 @@ import * as ex from '@excalibur'; -import { getDefaultPhysicsConfig } from '../engine/Collision/PhysicsConfig'; -import { TestUtils } from './util/TestUtils'; +import { getDefaultPhysicsConfig } from '../../engine/Collision/PhysicsConfig'; describe('A DynamicTree Broadphase', () => { let actorA: ex.Actor; diff --git a/src/spec/EasingFunctionSpec.ts b/src/spec/vitest/EasingFunctionSpec.ts similarity index 100% rename from src/spec/EasingFunctionSpec.ts rename to src/spec/vitest/EasingFunctionSpec.ts diff --git a/src/spec/EngineSpec.ts b/src/spec/vitest/EngineSpec.ts similarity index 74% rename from src/spec/EngineSpec.ts rename to src/spec/vitest/EngineSpec.ts index fc97bc48..dfa5dae7 100644 --- a/src/spec/EngineSpec.ts +++ b/src/spec/vitest/EngineSpec.ts @@ -1,6 +1,6 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; +import { inject } from 'vitest'; /** * @@ -30,9 +30,6 @@ describe('The engine', () => { }; beforeEach(async () => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - engine = TestUtils.engine(); scene = new ex.Scene(); engine.add('default', scene); @@ -47,7 +44,7 @@ describe('The engine', () => { }); it('should not throw if no loader provided', async () => { - const exceptionSpy = jasmine.createSpy('exception'); + const exceptionSpy = vi.fn(); const boot = async () => { const engine = TestUtils.engine(); await TestUtils.runToReady(engine); @@ -62,33 +59,35 @@ describe('The engine', () => { expect(exceptionSpy).not.toHaveBeenCalled(); }); - xit('should show the play button by default', (done) => { - reset(); - engine = TestUtils.engine({ - suppressPlayButton: false - }); - (engine)._suppressPlayButton = false; - const imageSource = new ex.ImageSource('src/spec/images/SpriteSpec/icon.png'); - const loader = new ex.Loader([imageSource]); - const testClock = engine.clock as ex.TestClock; - engine.start(loader).then(() => { - loader.areResourcesLoaded().then(() => { - testClock.run(2, 100); // 200 ms delay in loader - expect(document.getElementById('excalibur-play')).withContext('Play button should exist in the document').toBeDefined(); - setTimeout(() => { - // needed for the delay to work - testClock.run(1, 100); - engine.graphicsContext.flush(); - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/EngineSpec/engine-load-complete.png') - .then(() => { - done(); - }); + it.skip('should show the play button by default', () => + new Promise((done) => { + reset(); + engine = TestUtils.engine({ + suppressPlayButton: false + }); + (engine)._suppressPlayButton = false; + const imageSource = new ex.ImageSource('/src/spec/assets/images/SpriteSpec/icon.png'); + + const loader = new ex.Loader([imageSource]); + const testClock = engine.clock as ex.TestClock; + engine.start(loader).then(() => { + loader.areResourcesLoaded().then(() => { + testClock.run(2, 100); // 200 ms delay in loader + expect(document.getElementById('excalibur-play'), 'Play button should exist in the document').toBeDefined(); + setTimeout(() => { + // needed for the delay to work + testClock.run(1, 100); + engine.graphicsContext.flush(); + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/EngineSpec/engine-load-complete.png') + .then(() => { + done(); + }); + }); }); }); - }); - }); + })); it('should log if loading fails', async () => { class FailedLoader extends ex.DefaultLoader { @@ -102,7 +101,7 @@ describe('The engine', () => { } } const logger = ex.Logger.getInstance(); - spyOn(logger, 'error'); + vi.spyOn(logger, 'error'); engine.dispose(); engine = null; @@ -122,9 +121,9 @@ describe('The engine', () => { const originalScreen = engine.screen; const originalPointers = engine.input.pointers; - spyOn(engine.screen, 'dispose').and.callThrough(); - spyOn(engine.input.pointers, 'detach').and.callThrough(); - spyOn(engine.input.pointers, 'recreate').and.callThrough(); + vi.spyOn(engine.screen, 'dispose'); + vi.spyOn(engine.input.pointers, 'detach'); + vi.spyOn(engine.input.pointers, 'recreate'); engine.useCanvas2DFallback(); @@ -145,7 +144,7 @@ describe('The engine', () => { } }); await TestUtils.runToReady(engine); - spyOn(engine, 'useCanvas2DFallback'); + vi.spyOn(engine, 'useCanvas2DFallback'); const clock = engine.clock as ex.TestClock; clock.fpsSampler = new ex.FpsSampler({ @@ -170,8 +169,8 @@ describe('The engine', () => { await TestUtils.runToReady(engine); - spyOn(engine as any, '_update'); - spyOn(engine as any, '_draw'); + vi.spyOn(engine as any, '_update'); + vi.spyOn(engine as any, '_draw'); clock.step(101); @@ -190,8 +189,8 @@ describe('The engine', () => { await TestUtils.runToReady(engine); - spyOn(engine as any, '_update'); - spyOn(engine as any, '_draw'); + vi.spyOn(engine as any, '_update'); + vi.spyOn(engine as any, '_draw'); clock.step(16); clock.step(16); @@ -255,45 +254,46 @@ describe('The engine', () => { expect(ex.TextureLoader.filtering).toBe(ex.ImageFiltering.Pixel); }); - it('should not show the play button when suppressPlayButton is turned on', (done) => { - reset(); - engine = TestUtils.engine({ - suppressPlayButton: true - }); - engine.currentScene.add( - new ex.Actor({ - pos: new ex.Vector(250, 250), - width: 20, - height: 20, - color: ex.Color.Red - }) - ); - - const testClock = engine.clock as ex.TestClock; - const loader = new ex.Loader([new ex.ImageSource('src/spec/images/SpriteSpec/icon.png')]); - - TestUtils.runToReady(engine, loader).then(() => { - // With suppress play there is another 500 ms delay in engine load() - testClock.step(1); - engine.graphicsContext.flush(); - expectAsync(engine.canvas) - .toEqualImage('src/spec/images/EngineSpec/engine-suppress-play.png') - .then(() => { - done(); - }); - }); - }); + it('should not show the play button when suppressPlayButton is turned on', () => + new Promise((done) => { + reset(); + engine = TestUtils.engine({ + suppressPlayButton: true + }); + engine.currentScene.add( + new ex.Actor({ + pos: new ex.Vector(250, 250), + width: 20, + height: 20, + color: ex.Color.Red + }) + ); + + const testClock = engine.clock as ex.TestClock; + const loader = new ex.Loader([new ex.ImageSource('/src/spec/assets/images/SpriteSpec/icon.png')]); + + TestUtils.runToReady(engine, loader).then(() => { + // With suppress play there is another 500 ms delay in engine load() + testClock.step(1); + engine.graphicsContext.flush(); + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/EngineSpec/engine-suppress-play.png') + .then(() => { + done(); + }); + }); + })); it('can set snapToPixel', () => { engine.dispose(); engine = null; engine = TestUtils.engine({ width: 100, height: 100 }); - expect(engine.snapToPixel).toBeFalse(); + expect(engine.snapToPixel).toBe(false); engine.snapToPixel = true; - expect(engine.snapToPixel).toBeTrue(); - expect(engine.graphicsContext.snapToPixel).toBeTrue(); + expect(engine.snapToPixel).toBe(true); + expect(engine.graphicsContext.snapToPixel).toBe(true); }); it('can set pixelRatio', () => { @@ -319,7 +319,7 @@ describe('The engine', () => { }); it('should emit a preframe event', () => { - const fired = jasmine.createSpy('fired'); + const fired = vi.fn(); engine.on('preframe', fired); expect(fired).not.toHaveBeenCalled(); const clock = engine.clock as ex.TestClock; @@ -329,7 +329,7 @@ describe('The engine', () => { }); it('should emit a postframe event', () => { - const fired = jasmine.createSpy('fired'); + const fired = vi.fn(); engine.on('postframe', fired); expect(fired).not.toHaveBeenCalled(); @@ -340,7 +340,7 @@ describe('The engine', () => { }); it('should emit a preupdate event', () => { - const fired = jasmine.createSpy('fired'); + const fired = vi.fn(); engine.on('preupdate', fired); expect(fired).not.toHaveBeenCalled(); const clock = engine.clock as ex.TestClock; @@ -350,7 +350,7 @@ describe('The engine', () => { }); it('should emit a postupdate event', () => { - const fired = jasmine.createSpy('fired'); + const fired = vi.fn(); engine.on('postupdate', fired); expect(fired).not.toHaveBeenCalled(); @@ -361,46 +361,48 @@ describe('The engine', () => { }); it('will update keyboard & gamepad events after postupdate', () => { - const postupdate = jasmine.createSpy('postupdate'); - spyOn(engine.input.keyboard, 'update').and.callThrough(); - spyOn(engine.input.gamepads, 'update').and.callThrough(); + const postupdate = vi.fn(); + const keyboardUpdate = vi.spyOn(engine.input.keyboard, 'update'); + const gamepadUpdate = vi.spyOn(engine.input.gamepads, 'update'); engine.on('postupdate', postupdate); const clock = engine.clock as ex.TestClock; clock.step(1); - expect(postupdate).toHaveBeenCalledBefore(engine.input.keyboard.update); - expect(postupdate).toHaveBeenCalledBefore(engine.input.gamepads.update); + expect(postupdate).toHaveBeenCalledBefore(keyboardUpdate); + expect(postupdate).toHaveBeenCalledBefore(gamepadUpdate); }); - it('will fire wasPressed in onPostUpdate handler', (done) => { - engine.input.keyboard.triggerEvent('down', ex.Keys.Enter); - engine.on('postupdate', () => { - if (engine.input.keyboard.wasPressed(ex.Keys.Enter)) { - done(); - } - }); + it('will fire wasPressed in onPostUpdate handler', () => + new Promise((done) => { + engine.input.keyboard.triggerEvent('down', ex.Keys.Enter); + engine.on('postupdate', () => { + if (engine.input.keyboard.wasPressed(ex.Keys.Enter)) { + done(); + } + }); - const clock = engine.clock as ex.TestClock; - clock.step(1); - }); + const clock = engine.clock as ex.TestClock; + clock.step(1); + })); - it('will fire wasReleased in onPostUpdate handler', (done) => { - engine.input.keyboard.triggerEvent('up', ex.Keys.Enter); - engine.on('postupdate', () => { - if (engine.input.keyboard.wasReleased(ex.Keys.Enter)) { - done(); - } - }); + it('will fire wasReleased in onPostUpdate handler', () => + new Promise((done) => { + engine.input.keyboard.triggerEvent('up', ex.Keys.Enter); + engine.on('postupdate', () => { + if (engine.input.keyboard.wasReleased(ex.Keys.Enter)) { + done(); + } + }); - const clock = engine.clock as ex.TestClock; - clock.step(1); - }); + const clock = engine.clock as ex.TestClock; + clock.step(1); + })); it('will fire isHeld in onPostUpdate handler', () => { engine.input.keyboard.triggerEvent('down', ex.Keys.Enter); - const held = jasmine.createSpy('held'); + const held = vi.fn(); engine.on('postupdate', () => { if (engine.input.keyboard.isHeld(ex.Keys.Enter)) { held(); @@ -416,7 +418,7 @@ describe('The engine', () => { }); it('should emit a predraw event', () => { - const fired = jasmine.createSpy('fired'); + const fired = vi.fn(); engine.on('predraw', fired); expect(fired).not.toHaveBeenCalled(); @@ -427,7 +429,7 @@ describe('The engine', () => { }); it('should emit a postdraw event', () => { - const fired = jasmine.createSpy('fired'); + const fired = vi.fn(); engine.on('postdraw', fired); expect(fired).not.toHaveBeenCalled(); @@ -438,20 +440,20 @@ describe('The engine', () => { }); it('should emit a visible event', () => { - const fired = jasmine.createSpy('fired'); + const fired = vi.fn(); engine.on('visible', fired); - spyOnProperty(window.document, 'visibilityState').and.returnValue('visible'); + vi.spyOn(window.document, 'visibilityState', 'get').mockReturnValue('visible'); window.document.dispatchEvent(new CustomEvent('visibilitychange')); expect(fired).toHaveBeenCalled(); }); it('should emit a hidden event', () => { - const fired = jasmine.createSpy('fired'); + const fired = vi.fn(); engine.on('hidden', fired); - spyOnProperty(window.document, 'visibilityState').and.returnValue('hidden'); + vi.spyOn(window.document, 'visibilityState', 'get').mockReturnValue('hidden'); window.document.dispatchEvent(new CustomEvent('visibilitychange')); expect(fired).toHaveBeenCalled(); @@ -462,7 +464,7 @@ describe('The engine', () => { cancelable: true, bubbles: true }); - const spyPreventDefault = spyOn(mockEvent, 'preventDefault'); + const spyPreventDefault = vi.spyOn(mockEvent, 'preventDefault'); engine.canvas.dispatchEvent(mockEvent); expect(spyPreventDefault).toHaveBeenCalled(); @@ -476,7 +478,7 @@ describe('The engine', () => { cancelable: true, bubbles: true }); - const spyPreventDefault = spyOn(mockEvent, 'preventDefault'); + const spyPreventDefault = vi.spyOn(mockEvent, 'preventDefault'); engine.canvas.dispatchEvent(mockEvent); expect(spyPreventDefault).not.toHaveBeenCalled(); @@ -575,79 +577,82 @@ describe('The engine', () => { game.dispose(); }); - it('should detect hidpi when the device pixel ratio is greater than 1', (done) => { - // Arrange - const oldWidth = 100; - const oldHeight = 100; + it('should detect hidpi when the device pixel ratio is greater than 1', () => + new Promise((done) => { + // Arrange + const oldWidth = 100; + const oldHeight = 100; - (window).devicePixelRatio = 2; - const newWidth = oldWidth * (window).devicePixelRatio; - const newHeight = oldHeight * (window).devicePixelRatio; + (window).devicePixelRatio = 2; + const newWidth = oldWidth * (window).devicePixelRatio; + const newHeight = oldHeight * (window).devicePixelRatio; - engine.dispose(); - engine = null; - engine = TestUtils.engine({ - width: 100, - height: 100, - suppressHiDPIScaling: false - }); - // Act - engine.start().then(() => { - // Assert - expect(engine.isHiDpi).toBe(true); - (window).devicePixelRatio = 1; + engine.dispose(); + engine = null; + engine = TestUtils.engine({ + width: 100, + height: 100, + suppressHiDPIScaling: false + }); + // Act + engine.start().then(() => { + // Assert + expect(engine.isHiDpi).toBe(true); + (window).devicePixelRatio = 1; - done(); - }); - }); + done(); + }); + })); - it('should not detect hidpi with a device pixel ratio equal to 1', (done) => { - // Arrange - const oldWidth = 100; - const oldHeight = 100; + it('should not detect hidpi with a device pixel ratio equal to 1', () => + new Promise((done) => { + // Arrange + const oldWidth = 100; + const oldHeight = 100; - (window).devicePixelRatio = 1; - const newWidth = oldWidth * (window).devicePixelRatio; - const newHeight = oldHeight * (window).devicePixelRatio; + (window).devicePixelRatio = 1; + const newWidth = oldWidth * (window).devicePixelRatio; + const newHeight = oldHeight * (window).devicePixelRatio; - // Act - engine.dispose(); - engine = null; - engine = TestUtils.engine({ - width: 100, - height: 100, - suppressHiDPIScaling: false - }); + // Act + engine.dispose(); + engine = null; + engine = TestUtils.engine({ + width: 100, + height: 100, + suppressHiDPIScaling: false + }); - engine.start().then(() => { - // Assert - expect(engine.isHiDpi).toBe(false); - done(); - }); - }); + engine.start().then(() => { + // Assert + expect(engine.isHiDpi).toBe(false); + done(); + }); + })); - it('should respect a hidpi suppression flag even if the pixel ratio is greater than 1', (done) => { - // Arrange - (window).devicePixelRatio = 2; + it('should respect a hidpi suppression flag even if the pixel ratio is greater than 1', () => + new Promise((done) => { + // Arrange + (window).devicePixelRatio = 2; - // Act - engine.dispose(); - engine = null; - engine = TestUtils.engine({ - width: 100, - height: 100, - suppressHiDPIScaling: true - }); + // Act + engine.dispose(); + engine = null; + engine = TestUtils.engine({ + width: 100, + height: 100, + suppressHiDPIScaling: true + }); - engine.start().then(() => { - // Assert - expect(engine.isHiDpi).toBe(false); - expect(engine.drawWidth).toBe(100); - expect(engine.drawHeight).toBe(100); - (window).devicePixelRatio = 1; - done(); - }); - }); + engine.start().then(() => { + // Assert + expect(engine.isHiDpi).toBe(false); + expect(engine.drawWidth).toBe(100); + expect(engine.drawHeight).toBe(100); + (window).devicePixelRatio = 1; + done(); + }); + })); it('should accept custom enableCanvasTransparency false', () => { const game = new ex.Engine({ @@ -671,7 +676,7 @@ describe('The engine', () => { }); it('will warn if scenes are being overwritten', () => { - spyOn(ex.Logger.getInstance(), 'warn'); + vi.spyOn(ex.Logger.getInstance(), 'warn'); const scene = new ex.Scene(); engine.addScene('dup', scene); engine.addScene('dup', scene); @@ -707,7 +712,7 @@ describe('The engine', () => { }); it('will log an error if the scene does not exist', async () => { - spyOn(ex.Logger.getInstance(), 'warn'); + vi.spyOn(ex.Logger.getInstance(), 'warn'); await engine.goToScene('madeUp'); expect(ex.Logger.getInstance().warn).toHaveBeenCalledWith('Scene madeUp does not exist! Check the name, are you sure you added it?'); }); @@ -726,8 +731,8 @@ describe('The engine', () => { engine.add(new ex.Actor()); }; - spyOn(scene1, 'onInitialize').and.callThrough(); - spyOn(scene2, 'onInitialize').and.callThrough(); + vi.spyOn(scene1, 'onInitialize'); + vi.spyOn(scene2, 'onInitialize'); await engine.goToScene('scene1'); @@ -739,36 +744,37 @@ describe('The engine', () => { engine.dispose(); }); - it('can screen shot the game (in WebGL)', (done) => { - const engine = TestUtils.engine({}, []); - const clock = engine.clock as ex.TestClock; - - engine.add( - new ex.Actor({ - x: 50, - y: 50, - width: 100, - height: 100, - color: ex.Color.Red - }) - ); - TestUtils.runToReady(engine).then(() => { - clock.step(1); + it('can screen shot the game (in WebGL)', () => + new Promise((done) => { + const engine = TestUtils.engine({}, []); + const clock = engine.clock as ex.TestClock; - const canvas = flushWebGLCanvasTo2D(engine.canvas); - engine.screenshot().then((image) => { - expectAsync(image) - .toEqualImage(canvas) - .then(() => { - done(); - engine.dispose(); - }); + engine.add( + new ex.Actor({ + x: 50, + y: 50, + width: 100, + height: 100, + color: ex.Color.Red + }) + ); + TestUtils.runToReady(engine).then(() => { + clock.step(1); + + const canvas = flushWebGLCanvasTo2D(engine.canvas); + engine.screenshot().then((image) => { + expect(image) + .toEqualImage(canvas) + .then(() => { + done(); + engine.dispose(); + }); + }); + clock.step(1); + clock.step(1); + clock.step(1); }); - clock.step(1); - clock.step(1); - clock.step(1); - }); - }); + })); it('can screen shot the game HiDPI (in WebGL)', async () => { const engine = TestUtils.engine({}, []); @@ -802,11 +808,16 @@ describe('The engine', () => { expect(hidpiImage.width).toBe(1000); expect(hidpiImage.height).toBe(1000); - await expectAsync(hidpiImage).toEqualImage(canvas); + await expect(hidpiImage).toEqualImage(canvas); engine.dispose(); }); - it('can screen shot and match the anti-aliasing with a half pixel when pixelRatio != 1.0', async () => { + it('can screen shot and match the anti-aliasing with a half pixel when pixelRatio != 1.0', async ({ skip }) => { + // safari inconsistencies + if (inject('browser') === 'webkit') { + skip(); + } + const engine = TestUtils.engine( { width: 200, @@ -819,7 +830,7 @@ describe('The engine', () => { [] ); const clock = engine.clock as ex.TestClock; - const img = new ex.ImageSource('src/spec/images/EngineSpec/sprite.png'); + const img = new ex.ImageSource('/src/spec/assets/images/EngineSpec/sprite.png'); await img.load(); const actor = new ex.Actor({ x: 40.5, @@ -836,7 +847,7 @@ describe('The engine', () => { const image = await screenShotPromise; - await expectAsync(image).toEqualImage('src/spec/images/EngineSpec/screenshot.png', 1.0); + await expect(image).toEqualImage('/src/spec/assets/images/EngineSpec/screenshot.png', 0.999); engine.dispose(); }); @@ -849,7 +860,7 @@ describe('The engine', () => { }); const clock = engine.clock as ex.TestClock; await TestUtils.runToReady(engine); - const playerImage = new ex.ImageSource('src/spec/images/EngineSpec/hero.png'); + const playerImage = new ex.ImageSource('/src/spec/assets/images/EngineSpec/hero.png'); const playerSpriteSheet = ex.SpriteSheet.fromImageSource({ image: playerImage, grid: { @@ -859,7 +870,7 @@ describe('The engine', () => { columns: 8 } }); - const backgroundImage = new ex.ImageSource('src/spec/images/EngineSpec/tileset.png'); + const backgroundImage = new ex.ImageSource('/src/spec/assets/images/EngineSpec/tileset.png'); const backgroundSpriteSheet = ex.SpriteSheet.fromImageSource({ image: backgroundImage, grid: { @@ -895,7 +906,7 @@ describe('The engine', () => { clock.step(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/EngineSpec/snaptopixel.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/EngineSpec/snaptopixel.png'); engine.dispose(); }); @@ -909,7 +920,7 @@ describe('The engine', () => { }); const clock = engine.clock as ex.TestClock; await TestUtils.runToReady(engine); - const playerImage = new ex.ImageSource('src/spec/images/EngineSpec/hero.png'); + const playerImage = new ex.ImageSource('/src/spec/assets/images/EngineSpec/hero.png'); const playerSpriteSheet = ex.SpriteSheet.fromImageSource({ image: playerImage, grid: { @@ -919,7 +930,7 @@ describe('The engine', () => { columns: 8 } }); - const backgroundImage = new ex.ImageSource('src/spec/images/EngineSpec/tileset.png'); + const backgroundImage = new ex.ImageSource('/src/spec/assets/images/EngineSpec/tileset.png'); const backgroundSpriteSheet = ex.SpriteSheet.fromImageSource({ image: backgroundImage, grid: { @@ -954,7 +965,7 @@ describe('The engine', () => { engine.currentScene.camera.pos = player.pos; clock.step(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/EngineSpec/pixelart.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/EngineSpec/pixelart.png'); engine.dispose(); }); @@ -981,7 +992,7 @@ describe('The engine', () => { initCalled = true; }); - spyOn(engine, 'onInitialize').and.callThrough(); + vi.spyOn(engine, 'onInitialize'); await TestUtils.runToReady(engine); const clock = engine.clock as ex.TestClock; @@ -1001,8 +1012,8 @@ describe('The engine', () => { expect(elapsedMs).toBe(100); }; - spyOn(engine, 'onPostUpdate').and.callThrough(); - spyOn(engine, '_postupdate').and.callThrough(); + vi.spyOn(engine, 'onPostUpdate'); + vi.spyOn(engine, '_postupdate'); clock.step(100); clock.step(100); @@ -1021,8 +1032,8 @@ describe('The engine', () => { expect(elapsedMs).toBe(100); }; - spyOn(engine, 'onPreUpdate').and.callThrough(); - spyOn(engine, '_preupdate').and.callThrough(); + vi.spyOn(engine, 'onPreUpdate'); + vi.spyOn(engine, '_preupdate'); clock.step(100); clock.step(100); @@ -1041,8 +1052,8 @@ describe('The engine', () => { expect(ctx).not.toBe(null); expect(elapsedMs).toBe(100); }; - spyOn(engine, 'onPreDraw').and.callThrough(); - spyOn(engine, '_predraw').and.callThrough(); + vi.spyOn(engine, 'onPreDraw'); + vi.spyOn(engine, '_predraw'); clock.step(100); clock.step(100); @@ -1062,8 +1073,8 @@ describe('The engine', () => { expect(elapsedMs).toBe(100); }; - spyOn(engine, 'onPostDraw').and.callThrough(); - spyOn(engine, '_postdraw').and.callThrough(); + vi.spyOn(engine, 'onPostDraw'); + vi.spyOn(engine, '_postdraw'); clock.step(100); clock.step(100); diff --git a/src/spec/EntityManagerSpec.ts b/src/spec/vitest/EntityManagerSpec.ts similarity index 100% rename from src/spec/EntityManagerSpec.ts rename to src/spec/vitest/EntityManagerSpec.ts diff --git a/src/spec/EntitySpec.ts b/src/spec/vitest/EntitySpec.ts similarity index 84% rename from src/spec/EntitySpec.ts rename to src/spec/vitest/EntitySpec.ts index 731f31d4..cba45c97 100644 --- a/src/spec/EntitySpec.ts +++ b/src/spec/vitest/EntitySpec.ts @@ -23,7 +23,7 @@ describe('An entity', () => { const original = new FakeComponentA(); const e = new ex.Entity([original]); - spyOn(e, 'removeComponent'); + vi.spyOn(e, 'removeComponent'); const newComponent = new FakeComponentA(); e.addComponent(newComponent, true); expect(e.removeComponent).toHaveBeenCalledWith(FakeComponentA, true); @@ -101,7 +101,7 @@ describe('An entity', () => { expect(entity.types).toEqual([FakeComponentA]); expect(entity.tags).toEqual(new Set(['offscreen'])); - expect(entity.hasTag('offscreen')).toBeTrue(); + expect(entity.hasTag('offscreen')).toBe(true); }); it('can add and remove tags', () => { @@ -118,34 +118,36 @@ describe('An entity', () => { expect(entity.tags).toEqual(new Set(['someTag1'])); }); - it('can be observed for added changes', (done) => { - const entity = new ex.Entity(); - const typeA = new FakeComponentA(); - entity.componentAdded$.register({ - notify: (change) => { - expect(change.owner).toBe(entity); - expect(change).toBe(typeA); - done(); - } - }); - entity.addComponent(typeA); - }); - - it('can be observed for removed changes', (done) => { - const entity = new ex.Entity(); - const typeA = new FakeComponentA(); - - entity.addComponent(typeA); - entity.componentRemoved$.register({ - notify: (change) => { - expect(change.owner).toBe(entity); - expect(change).toBe(typeA); - done(); - } - }); - entity.removeComponent(FakeComponentA); - entity.processComponentRemoval(); - }); + it('can be observed for added changes', () => + new Promise((done) => { + const entity = new ex.Entity(); + const typeA = new FakeComponentA(); + entity.componentAdded$.register({ + notify: (change) => { + expect(change.owner).toBe(entity); + expect(change).toBe(typeA); + done(); + } + }); + entity.addComponent(typeA); + })); + + it('can be observed for removed changes', () => + new Promise((done) => { + const entity = new ex.Entity(); + const typeA = new FakeComponentA(); + + entity.addComponent(typeA); + entity.componentRemoved$.register({ + notify: (change) => { + expect(change.owner).toBe(entity); + expect(change).toBe(typeA); + done(); + } + }); + entity.removeComponent(FakeComponentA); + entity.processComponentRemoval(); + })); it('can be cloned', () => { const entity = new ex.Entity(); @@ -191,59 +193,65 @@ describe('An entity', () => { expect(entity.has(FakeComponentC)).toBe(false); }); - it('has an overridable initialize lifecycle handler', (done) => { - const entity = new ex.Entity(); - entity.onInitialize = () => { - done(); - }; + it('has an overridable initialize lifecycle handler', () => + new Promise((done) => { + const entity = new ex.Entity(); + entity.onInitialize = () => { + done(); + }; - entity._initialize(null); - }); + entity._initialize(null); + })); - it('has an event initialize handler', (done) => { - const entity = new ex.Entity(); - entity.on('initialize', () => { - done(); - }); + it('has an event initialize handler', () => + new Promise((done) => { + const entity = new ex.Entity(); + entity.on('initialize', () => { + done(); + }); - entity._initialize(null); - }); + entity._initialize(null); + })); - it('has an overridable preupdate lifecycle handler', (done) => { - const entity = new ex.Entity(); - entity.onPreUpdate = () => { - done(); - }; + it('has an overridable preupdate lifecycle handler', () => + new Promise((done) => { + const entity = new ex.Entity(); + entity.onPreUpdate = () => { + done(); + }; - entity._preupdate(null, 1); - }); + entity._preupdate(null, 1); + })); - it('has an event preupdate handler', (done) => { - const entity = new ex.Entity(); - entity.on('preupdate', () => { - done(); - }); + it('has an event preupdate handler', () => + new Promise((done) => { + const entity = new ex.Entity(); + entity.on('preupdate', () => { + done(); + }); - entity._preupdate(null, 1); - }); + entity._preupdate(null, 1); + })); - it('has an overridable postupdate lifecycle handler', (done) => { - const entity = new ex.Entity(); - entity.onPostUpdate = () => { - done(); - }; + it('has an overridable postupdate lifecycle handler', () => + new Promise((done) => { + const entity = new ex.Entity(); + entity.onPostUpdate = () => { + done(); + }; - entity._postupdate(null, 1); - }); + entity._postupdate(null, 1); + })); - it('has an event postupdate handler', (done) => { - const entity = new ex.Entity(); - entity.on('postupdate', () => { - done(); - }); + it('has an event postupdate handler', () => + new Promise((done) => { + const entity = new ex.Entity(); + entity.on('postupdate', () => { + done(); + }); - entity._postupdate(null, 1); - }); + entity._postupdate(null, 1); + })); it('can be parented', () => { const parent = new ex.Entity(); @@ -306,7 +314,7 @@ describe('An entity', () => { it('can observe components added', () => { const e = new ex.Entity(); - const addedSpy = jasmine.createSpy('addedSpy'); + const addedSpy = vi.fn(); e.componentAdded$.register({ notify: addedSpy }); @@ -317,7 +325,7 @@ describe('An entity', () => { it('can observe components removed', () => { const e = new ex.Entity(); - const removedSpy = jasmine.createSpy('removedSpy'); + const removedSpy = vi.fn(); e.componentRemoved$.register({ notify: removedSpy }); diff --git a/src/spec/EventEmitterSpec.ts b/src/spec/vitest/EventEmitterSpec.ts similarity index 87% rename from src/spec/EventEmitterSpec.ts rename to src/spec/vitest/EventEmitterSpec.ts index a989cd66..ca26e740 100644 --- a/src/spec/EventEmitterSpec.ts +++ b/src/spec/vitest/EventEmitterSpec.ts @@ -15,7 +15,7 @@ describe('An EventEmitter', () => { it('can listen to events "on" multiple times', () => { const emitter = new ex.EventEmitter<{ someevent: FakeEvent }>(); const evt = new FakeEvent(); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); emitter.on('someevent', handler); emitter.emit('someevent', evt); @@ -28,7 +28,7 @@ describe('An EventEmitter', () => { it('can listen to events "once" then unsubscribe', () => { const emitter = new ex.EventEmitter(); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); emitter.once('someotherevent', handler); emitter.emit('someotherevent'); @@ -41,7 +41,7 @@ describe('An EventEmitter', () => { it('can be closed when using "on"', () => { const emitter = new ex.EventEmitter(); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); const sub = emitter.on('myevent', handler); @@ -54,7 +54,7 @@ describe('An EventEmitter', () => { it('can be closed when using "once"', () => { const emitter = new ex.EventEmitter(); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); const sub = emitter.on('myevent', handler); sub.close(); @@ -67,7 +67,7 @@ describe('An EventEmitter', () => { it('can be switched off by name and handler', () => { const emitter = new ex.EventEmitter(); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); emitter.on('myevent2', handler); emitter.on('myevent1', handler); @@ -85,7 +85,7 @@ describe('An EventEmitter', () => { it('can be switched off by name and handler for multiple installs', () => { const emitter = new ex.EventEmitter(); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); emitter.on('myevent2', handler); emitter.on('myevent2', handler); @@ -99,7 +99,7 @@ describe('An EventEmitter', () => { it('can be switched off by name and handler for multiple installs in once', () => { const emitter = new ex.EventEmitter(); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); emitter.once('myevent2', handler); emitter.once('myevent2', handler); @@ -113,7 +113,7 @@ describe('An EventEmitter', () => { it('can be switched off by name and handler for "once"', () => { const emitter = new ex.EventEmitter(); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); emitter.on('onetime', handler); @@ -130,7 +130,7 @@ describe('An EventEmitter', () => { // Pipe actor events into scene const pipeSub = actorEmitter.pipe(sceneEmitter); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); sceneEmitter.on('myactorevent', handler); actorEmitter.emit('myactorevent'); @@ -145,14 +145,14 @@ describe('An EventEmitter', () => { const newPubSub = new ex.EventEmitter<{ someevent: number; otherevent: number }>(); newPubSub.pipe(pubSub); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); pubSub.on('someevent', handler); newPubSub.emit('someevent'); expect(handler).toHaveBeenCalledTimes(1); - const otherHandler = jasmine.createSpy('otherHandler'); + const otherHandler = vi.fn(); pubSub.on('otherevent', otherHandler); newPubSub.unpipe(pubSub); newPubSub.emit('otherevent'); @@ -165,14 +165,14 @@ describe('An EventEmitter', () => { const newPubSub = new ex.EventEmitter<{ someevent: number; otherevent: number }>(); const sub = newPubSub.pipe(pubSub); - const handler = jasmine.createSpy('handler'); + const handler = vi.fn(); pubSub.on('someevent', handler); newPubSub.emit('someevent'); expect(handler).toHaveBeenCalledTimes(1); - const otherHandler = jasmine.createSpy('otherHandler'); + const otherHandler = vi.fn(); pubSub.on('otherevent', otherHandler); sub.close(); @@ -191,7 +191,7 @@ describe('An EventEmitter', () => { it('can listen to a handler only once', () => { const pubsub = new ex.EventEmitter(); - const handler = jasmine.createSpy('onlyonce'); + const handler = vi.fn(); pubsub.once('onlyonce', handler); @@ -203,9 +203,9 @@ describe('An EventEmitter', () => { }); it('will handle remove invalid handler', () => { - const eventSpy1 = jasmine.createSpy('handler'); - const eventSpy2 = jasmine.createSpy('handler'); - const eventSpy3 = jasmine.createSpy('handler'); + const eventSpy1 = vi.fn(); + const eventSpy2 = vi.fn(); + const eventSpy3 = vi.fn(); const emitter = new ex.EventEmitter(); emitter.on('foo', () => eventSpy1()); emitter.on('foo', () => eventSpy2()); @@ -221,9 +221,9 @@ describe('An EventEmitter', () => { }); it('once will remove the handler correctly', () => { - const eventSpy1 = jasmine.createSpy('handler'); - const eventSpy2 = jasmine.createSpy('handler'); - const eventSpy3 = jasmine.createSpy('handler'); + const eventSpy1 = vi.fn(); + const eventSpy2 = vi.fn(); + const eventSpy3 = vi.fn(); const emitter = new ex.EventEmitter(); emitter.once('foo', () => eventSpy1()); emitter.on('foo', () => eventSpy2()); diff --git a/src/spec/ExcaliburGraphicsContextSpec.ts b/src/spec/vitest/ExcaliburGraphicsContextSpec.ts similarity index 82% rename from src/spec/ExcaliburGraphicsContextSpec.ts rename to src/spec/vitest/ExcaliburGraphicsContextSpec.ts index df35cdda..1cd65a97 100644 --- a/src/spec/ExcaliburGraphicsContextSpec.ts +++ b/src/spec/vitest/ExcaliburGraphicsContextSpec.ts @@ -1,6 +1,5 @@ import * as ex from '@excalibur'; import { TextureLoader } from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; describe('The ExcaliburGraphicsContext', () => { describe('2D', () => { @@ -9,17 +8,15 @@ describe('The ExcaliburGraphicsContext', () => { beforeAll(() => { testCanvasElement = document.createElement('canvas'); testContext = testCanvasElement.getContext('2d'); + document.body.appendChild(testCanvasElement); }); afterAll(() => { + document.body.removeChild(testCanvasElement); testCanvasElement.width = 0; testCanvasElement.height = 0; testCanvasElement = null; testContext = null; }); - beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); it('exists', () => { expect(ex.ExcaliburGraphicsContext2DCanvas).toBeDefined(); @@ -66,7 +63,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.clear(); sut.drawImage(rect._bitmap, 20, 20); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/2d-drawgraphic.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-drawgraphic.png'); }); it('can draw debug point', async () => { @@ -85,7 +82,7 @@ describe('The ExcaliburGraphicsContext', () => { color: ex.Color.Blue }); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/2d-drawpoint.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-drawpoint.png'); }); it('can draw debug line', async () => { @@ -103,7 +100,8 @@ describe('The ExcaliburGraphicsContext', () => { color: ex.Color.Blue }); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/2d-drawline.png'); + // chromium seems to alias this slightly differently than ff/webkit. 0.993 tolerance needed. + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-drawline.png', 0.993); }); it('can transform the context', async () => { @@ -131,7 +129,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.drawImage(rect._bitmap, -25, -25); sut.restore(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/2d-transform.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-transform.png'); }); it('can draw rectangle', async () => { @@ -148,7 +146,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.drawRectangle(ex.vec(10, 10), 80, 80, ex.Color.Blue); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/webgl-solid-rect.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-solid-rect.png'); }); it('can draw circle', async () => { @@ -165,7 +163,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.drawCircle(ex.vec(50, 50), 50, ex.Color.Blue); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/2d-circle.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-circle.png'); }); it('can draw a line', async () => { @@ -182,7 +180,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.drawLine(ex.vec(0, 0), ex.vec(100, 100), ex.Color.Blue, 5); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/2d-line.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-line.png'); }); it('can snap drawings to pixel', async () => { @@ -205,7 +203,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.clear(); sut.drawImage(rect._bitmap, 1.9, 1.9); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/2d-snap-to-pixel.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-snap-to-pixel.png'); }); it('can handle drawing a zero dimension image', () => { @@ -259,8 +257,6 @@ describe('The ExcaliburGraphicsContext', () => { testContext = null; }); beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); TextureLoader.filtering = ex.ImageFiltering.Pixel; testCanvasElement = document.createElement('canvas'); }); @@ -327,7 +323,7 @@ describe('The ExcaliburGraphicsContext', () => { rect.draw(context, 0.5, 0.5); //1 - 0.001, 1 - 0.001); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap.png'); context.dispose(); }); @@ -353,7 +349,7 @@ describe('The ExcaliburGraphicsContext', () => { rect.draw(context, 1 - 0.0001, 1 - 0.0001); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-next.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-next.png'); context.dispose(); }); @@ -374,7 +370,7 @@ describe('The ExcaliburGraphicsContext', () => { context.drawRectangle(ex.vec(1 - 0.0001, 1 - 0.0001), 2, 2, ex.Color.Red); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-next.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-next.png'); context.dispose(); }); @@ -395,7 +391,7 @@ describe('The ExcaliburGraphicsContext', () => { context.drawLine(ex.vec(1 - 0.0001, 2 - 0.0001), ex.vec(5, 2 - 0.0001), ex.Color.Red, 2); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-line-next.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-line-next.png'); context.dispose(); }); @@ -416,7 +412,7 @@ describe('The ExcaliburGraphicsContext', () => { context.drawCircle(ex.vec(5 - 0.0001, 5 - 0.0001), 3, ex.Color.Red); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-circle-next.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-circle-next.png'); context.dispose(); }); @@ -440,7 +436,7 @@ describe('The ExcaliburGraphicsContext', () => { }); context.flush(); - await expectAsync(canvas).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/pixel-snap-point-next.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/pixel-snap-point-next.png'); context.dispose(); }); @@ -465,7 +461,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.drawImage(rect._bitmap, 20, 20); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/2d-drawgraphic.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-drawgraphic.png'); sut.dispose(); }); @@ -487,13 +483,13 @@ describe('The ExcaliburGraphicsContext', () => { }); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/webgl-drawpoint.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-drawpoint.png'); sut.dispose(); }); it('will log a warning if you attempt to draw outside the lifecycle', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warnOnce').and.callThrough(); + vi.spyOn(logger, 'warnOnce'); const canvasElement = testCanvasElement; canvasElement.width = 100; @@ -516,7 +512,7 @@ describe('The ExcaliburGraphicsContext', () => { it('will not log a warning inside the lifecycle', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn').and.callThrough(); + vi.spyOn(logger, 'warn'); const canvasElement = testCanvasElement; canvasElement.width = 100; @@ -549,30 +545,30 @@ describe('The ExcaliburGraphicsContext', () => { snapToPixel: false }); - const tex = new ex.ImageSource('src/spec/images/ExcaliburGraphicsContextSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/ExcaliburGraphicsContextSpec/sword.png'); await tex.load(); const circleRenderer = sut.get('ex.circle'); - spyOn(circleRenderer, 'flush').and.callThrough(); + vi.spyOn(circleRenderer, 'flush'); const imageRenderer = sut.get('ex.image-v2'); - spyOn(imageRenderer, 'flush').and.callThrough(); + vi.spyOn(imageRenderer, 'flush'); const rectangleRenderer = sut.get('ex.rectangle'); - spyOn(rectangleRenderer, 'flush').and.callThrough(); + vi.spyOn(rectangleRenderer, 'flush'); sut.clear(); sut.useDrawSorting = false; sut.drawLine(ex.vec(0, 0), ex.vec(100, 100), ex.Color.Red, 2); - expect(rectangleRenderer.flush).withContext('rectangle line render not flushed yet').not.toHaveBeenCalled(); + expect(rectangleRenderer.flush, 'rectangle line render not flushed yet').not.toHaveBeenCalled(); sut.drawCircle(ex.Vector.Zero, 100, ex.Color.Red, ex.Color.Black, 2); - expect(circleRenderer.flush).withContext('circle is batched not flushed yet').not.toHaveBeenCalled(); - expect(rectangleRenderer.flush).withContext('rectangle line render').toHaveBeenCalled(); + expect(circleRenderer.flush, 'circle is batched not flushed yet').not.toHaveBeenCalled(); + expect(rectangleRenderer.flush, 'rectangle line render').toHaveBeenCalled(); sut.drawImage(tex.image, 0, 0, tex.width, tex.height, 20, 20); - expect(circleRenderer.flush).withContext('circle renderer switched, flush required').toHaveBeenCalled(); - expect(imageRenderer.flush).withContext('image batched not yet flushed').not.toHaveBeenCalled(); + expect(circleRenderer.flush, 'circle renderer switched, flush required').toHaveBeenCalled(); + expect(imageRenderer.flush, 'image batched not yet flushed').not.toHaveBeenCalled(); sut.drawRectangle(ex.Vector.Zero, 50, 50, ex.Color.Blue, ex.Color.Green, 2); expect(imageRenderer.flush).toHaveBeenCalled(); @@ -584,8 +580,8 @@ describe('The ExcaliburGraphicsContext', () => { expect(circleRenderer.flush).toHaveBeenCalledTimes(1); expect(imageRenderer.flush).toHaveBeenCalledTimes(1); - await expectAsync(canvasElement).toEqualImage( - 'src/spec/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png', + await expect(canvasElement).toEqualImage( + '/src/spec/assets/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png', 0.97 ); sut.dispose(); @@ -606,30 +602,30 @@ describe('The ExcaliburGraphicsContext', () => { }); sut.imageRenderer = 'ex.image'; - const tex = new ex.ImageSource('src/spec/images/ExcaliburGraphicsContextSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/ExcaliburGraphicsContextSpec/sword.png'); await tex.load(); const circleRenderer = sut.get('ex.circle'); - spyOn(circleRenderer, 'flush').and.callThrough(); + vi.spyOn(circleRenderer, 'flush'); const imageRenderer = sut.get('ex.image'); - spyOn(imageRenderer, 'flush').and.callThrough(); + vi.spyOn(imageRenderer, 'flush'); const rectangleRenderer = sut.get('ex.rectangle'); - spyOn(rectangleRenderer, 'flush').and.callThrough(); + vi.spyOn(rectangleRenderer, 'flush'); sut.clear(); sut.useDrawSorting = false; sut.drawLine(ex.vec(0, 0), ex.vec(100, 100), ex.Color.Red, 2); - expect(rectangleRenderer.flush).withContext('rectangle line render not flushed yet').not.toHaveBeenCalled(); + expect(rectangleRenderer.flush, 'rectangle line render not flushed yet').not.toHaveBeenCalled(); sut.drawCircle(ex.Vector.Zero, 100, ex.Color.Red, ex.Color.Black, 2); - expect(circleRenderer.flush).withContext('circle is batched not flushed yet').not.toHaveBeenCalled(); - expect(rectangleRenderer.flush).withContext('rectangle line render').toHaveBeenCalled(); + expect(circleRenderer.flush, 'circle is batched not flushed yet').not.toHaveBeenCalled(); + expect(rectangleRenderer.flush, 'rectangle line render').toHaveBeenCalled(); sut.drawImage(tex.image, 0, 0, tex.width, tex.height, 20, 20); - expect(circleRenderer.flush).withContext('circle renderer switched, flush required').toHaveBeenCalled(); - expect(imageRenderer.flush).withContext('image batched not yet flushed').not.toHaveBeenCalled(); + expect(circleRenderer.flush, 'circle renderer switched, flush required').toHaveBeenCalled(); + expect(imageRenderer.flush, 'image batched not yet flushed').not.toHaveBeenCalled(); sut.drawRectangle(ex.Vector.Zero, 50, 50, ex.Color.Blue, ex.Color.Green, 2); expect(imageRenderer.flush).toHaveBeenCalled(); @@ -641,8 +637,8 @@ describe('The ExcaliburGraphicsContext', () => { expect(circleRenderer.flush).toHaveBeenCalledTimes(1); expect(imageRenderer.flush).toHaveBeenCalledTimes(1); - await expectAsync(canvasElement).toEqualImage( - 'src/spec/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png', + await expect(canvasElement).toEqualImage( + '/src/spec/assets/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png', 0.97 ); sut.dispose(); @@ -662,15 +658,15 @@ describe('The ExcaliburGraphicsContext', () => { snapToPixel: false }); - const tex = new ex.ImageSource('src/spec/images/ExcaliburGraphicsContextSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/ExcaliburGraphicsContextSpec/sword.png'); await tex.load(); const circleRenderer = sut.get('ex.circle'); - spyOn(circleRenderer, 'flush').and.callThrough(); + vi.spyOn(circleRenderer, 'flush'); const imageRenderer = sut.get('ex.image-v2'); - spyOn(imageRenderer, 'flush').and.callThrough(); + vi.spyOn(imageRenderer, 'flush'); const rectangleRenderer = sut.get('ex.rectangle'); - spyOn(rectangleRenderer, 'flush').and.callThrough(); + vi.spyOn(rectangleRenderer, 'flush'); sut.clear(); sut.useDrawSorting = true; @@ -694,8 +690,8 @@ describe('The ExcaliburGraphicsContext', () => { expect(circleRenderer.flush).toHaveBeenCalledTimes(1); expect(imageRenderer.flush).toHaveBeenCalledTimes(1); - await expectAsync(canvasElement).toEqualImage( - 'src/spec/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png', + await expect(canvasElement).toEqualImage( + '/src/spec/assets/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png', 0.97 ); sut.dispose(); @@ -715,15 +711,15 @@ describe('The ExcaliburGraphicsContext', () => { }); sut.imageRenderer = 'ex.image'; - const tex = new ex.ImageSource('src/spec/images/ExcaliburGraphicsContextSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/ExcaliburGraphicsContextSpec/sword.png'); await tex.load(); const circleRenderer = sut.get('ex.circle'); - spyOn(circleRenderer, 'flush').and.callThrough(); + vi.spyOn(circleRenderer, 'flush'); const imageRenderer = sut.get('ex.image'); - spyOn(imageRenderer, 'flush').and.callThrough(); + vi.spyOn(imageRenderer, 'flush'); const rectangleRenderer = sut.get('ex.rectangle'); - spyOn(rectangleRenderer, 'flush').and.callThrough(); + vi.spyOn(rectangleRenderer, 'flush'); sut.clear(); sut.useDrawSorting = true; @@ -747,8 +743,8 @@ describe('The ExcaliburGraphicsContext', () => { expect(circleRenderer.flush).toHaveBeenCalledTimes(1); expect(imageRenderer.flush).toHaveBeenCalledTimes(1); - await expectAsync(canvasElement).toEqualImage( - 'src/spec/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png', + await expect(canvasElement).toEqualImage( + '/src/spec/assets/images/ExcaliburGraphicsContextSpec/painter-order-circle-image-rect.png', 0.97 ); sut.dispose(); @@ -773,7 +769,7 @@ describe('The ExcaliburGraphicsContext', () => { }); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/webgl-drawline.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-drawline.png'); sut.dispose(); }); @@ -796,7 +792,7 @@ describe('The ExcaliburGraphicsContext', () => { }); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/webgl-rect.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-rect.png'); sut.dispose(); }); @@ -815,7 +811,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.drawRectangle(ex.vec(10, 10), 80, 80, ex.Color.Blue); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/webgl-solid-rect.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-solid-rect.png'); sut.dispose(); }); @@ -834,7 +830,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.drawCircle(ex.vec(50, 50), 50, ex.Color.Blue); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/webgl-circle.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-circle.png'); sut.dispose(); }); @@ -854,13 +850,13 @@ describe('The ExcaliburGraphicsContext', () => { sut.drawCircle(ex.vec(50, 50), 50, ex.Color.Blue); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/webgl-circle-with-opacity.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-circle-with-opacity.png'); sut.dispose(); }); // FIXME these batch tests really kill test performance // I think there might be a better way to test this with configurable batch sizes - xit('can draw circles in batches (no draw sorting)', () => { + it.skip('can draw circles in batches (no draw sorting)', () => { const canvasElement = testCanvasElement; canvasElement.width = 100; canvasElement.height = 100; @@ -874,7 +870,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.clear(); const circleRenderer = sut.get('ex.circle'); - spyOn(circleRenderer, 'flush').and.callThrough(); + vi.spyOn(circleRenderer, 'flush'); for (let i = 0; i < 10922; i++) { sut.drawCircle(ex.vec(50, 50), 50, ex.Color.Blue); } @@ -890,7 +886,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.dispose(); }); - xit('can draw circles in batches (draw sorting)', () => { + it.skip('can draw circles in batches (draw sorting)', () => { const canvasElement = testCanvasElement; canvasElement.width = 100; canvasElement.height = 100; @@ -904,7 +900,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.clear(); const circleRenderer = sut.get('ex.circle'); - spyOn(circleRenderer, 'flush').and.callThrough(); + vi.spyOn(circleRenderer, 'flush'); for (let i = 0; i < 10922; i++) { sut.drawCircle(ex.vec(50, 50), 50, ex.Color.Blue); } @@ -919,7 +915,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.dispose(); }); - xit('can draw rectangles in batches (no draw sorting)', () => { + it.skip('can draw rectangles in batches (no draw sorting)', () => { const canvasElement = testCanvasElement; canvasElement.width = 100; canvasElement.height = 100; @@ -935,7 +931,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.clear(); const rectangleRenderer = sut.get('ex.rectangle'); - spyOn(rectangleRenderer, 'flush').and.callThrough(); + vi.spyOn(rectangleRenderer, 'flush'); for (let i = 0; i < 10922; i++) { sut.drawRectangle(ex.vec(50, 50), 50, 50, ex.Color.Blue); } @@ -951,7 +947,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.dispose(); }); - xit('can draw rectangles in batches (draw sorting)', () => { + it.skip('can draw rectangles in batches (draw sorting)', () => { const canvasElement = testCanvasElement; canvasElement.width = 100; canvasElement.height = 100; @@ -967,7 +963,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.clear(); const rectangleRenderer = sut.get('ex.rectangle'); - spyOn(rectangleRenderer, 'flush').and.callThrough(); + vi.spyOn(rectangleRenderer, 'flush'); for (let i = 0; i < 10922; i++) { sut.drawRectangle(ex.vec(50, 50), 50, 50, ex.Color.Blue); } @@ -983,7 +979,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.dispose(); }); - xit('can draw images in batches (no draw sorting)', async () => { + it.skip('can draw images in batches (no draw sorting)', async () => { const canvasElement = testCanvasElement; canvasElement.width = 100; canvasElement.height = 100; @@ -997,11 +993,11 @@ describe('The ExcaliburGraphicsContext', () => { sut.clear(); - const tex = new ex.ImageSource('src/spec/images/ExcaliburGraphicsContextSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/ExcaliburGraphicsContextSpec/sword.png'); await tex.load(); const imageRenderer = sut.get('ex.image'); - spyOn(imageRenderer, 'flush').and.callThrough(); + vi.spyOn(imageRenderer, 'flush'); for (let i = 0; i < 10922; i++) { sut.drawImage(tex.image, 0, 0); } @@ -1017,7 +1013,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.dispose(); }); - xit('can draw images in batches (draw sorting)', async () => { + it.skip('can draw images in batches (draw sorting)', async () => { const canvasElement = testCanvasElement; canvasElement.width = 100; canvasElement.height = 100; @@ -1031,11 +1027,11 @@ describe('The ExcaliburGraphicsContext', () => { sut.clear(); - const tex = new ex.ImageSource('src/spec/images/ExcaliburGraphicsContextSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/ExcaliburGraphicsContextSpec/sword.png'); await tex.load(); const imageRenderer = sut.get('ex.image'); - spyOn(imageRenderer, 'flush').and.callThrough(); + vi.spyOn(imageRenderer, 'flush'); for (let i = 0; i < 10922; i++) { sut.drawImage(tex.image, 0, 0); } @@ -1067,7 +1063,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.clear(); sut.drawLine(ex.vec(0, 0), ex.vec(100, 100), ex.Color.Blue, 5); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/webgl-line.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-line.png'); sut.dispose(); }); @@ -1100,7 +1096,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.restore(); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/webgl-transform.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/webgl-transform.png'); sut.dispose(); }); @@ -1126,7 +1122,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.drawImage(rect._bitmap, 1.9, 1.9); sut.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/2d-snap-to-pixel.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/2d-snap-to-pixel.png'); sut.dispose(); }); @@ -1166,7 +1162,7 @@ describe('The ExcaliburGraphicsContext', () => { it('can handle rendering rasters in succession', async () => { // arrange - const image = new ex.ImageSource('src/spec/images/ExcaliburGraphicsContextSpec/test.png'); + const image = new ex.ImageSource('/src/spec/assets/images/ExcaliburGraphicsContextSpec/test.png'); await image.load(); const spriteSheet = ex.SpriteSheet.fromImageSource({ image: image, @@ -1215,7 +1211,7 @@ describe('The ExcaliburGraphicsContext', () => { sut.flush(); // assert - await expectAsync(canvasElement).toEqualImage('src/spec/images/ExcaliburGraphicsContextSpec/rasters.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/ExcaliburGraphicsContextSpec/rasters.png'); sut.dispose(); }); }); diff --git a/src/spec/FadeInOutSpec.ts b/src/spec/vitest/FadeInOutSpec.ts similarity index 83% rename from src/spec/FadeInOutSpec.ts rename to src/spec/vitest/FadeInOutSpec.ts index 6a393ef5..7e861f50 100644 --- a/src/spec/FadeInOutSpec.ts +++ b/src/spec/vitest/FadeInOutSpec.ts @@ -1,11 +1,7 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; -import { ExcaliburAsyncMatchers } from 'excalibur-jasmine'; describe('A FadeInOut transition', () => { - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); it('exists', () => { expect(ex.CrossFade).toBeDefined(); }); @@ -30,9 +26,7 @@ describe('A FadeInOut transition', () => { }) ); - const onDeactivateSpy = jasmine.createSpy('onDeactivate').and.callFake(async () => { - await Promise.resolve(); - }); + const onDeactivateSpy = vi.fn(() => Promise.resolve()); engine.director.getSceneInstance('root').onDeactivate = onDeactivateSpy; @@ -53,7 +47,7 @@ describe('A FadeInOut transition', () => { clock.step(500); await Promise.resolve(); expect(onDeactivateSpy).toHaveBeenCalledTimes(1); - await expectAsync(engine.canvas).toEqualImage('/src/spec/images/FadeInOutSpec/fadein.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/FadeInOutSpec/fadein.png'); engine.dispose(); }); @@ -86,7 +80,7 @@ describe('A FadeInOut transition', () => { await TestUtils.flushMicrotasks(clock, 3); clock.step(900); await Promise.resolve(); - await expectAsync(engine.canvas).toEqualImage('/src/spec/images/FadeInOutSpec/fadeout.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/FadeInOutSpec/fadeout.png'); engine.dispose(); }); }); diff --git a/src/spec/FlagsSpec.ts b/src/spec/vitest/FlagsSpec.ts similarity index 85% rename from src/spec/FlagsSpec.ts rename to src/spec/vitest/FlagsSpec.ts index 5a66e782..5b46ada4 100644 --- a/src/spec/FlagsSpec.ts +++ b/src/spec/vitest/FlagsSpec.ts @@ -24,24 +24,24 @@ describe('Feature Flags', () => { it('should let you set flags', () => { ex.Flags.enable('some-flag'); - expect(ex.Flags.isEnabled('some-flag')).toBeTrue(); + expect(ex.Flags.isEnabled('some-flag')).toBe(true); }); it('should let you disable flags', () => { ex.Flags.disable('some-other-flag'); - expect(ex.Flags.isEnabled('some-other-flag')).toBeFalse(); + expect(ex.Flags.isEnabled('some-other-flag')).toBe(false); }); it('should let you toggle flags', () => { ex.Flags.enable('some-cool-flag'); - expect(ex.Flags.isEnabled('some-cool-flag')).toBeTrue(); + expect(ex.Flags.isEnabled('some-cool-flag')).toBe(true); ex.Flags.disable('some-cool-flag'); - expect(ex.Flags.isEnabled('some-cool-flag')).toBeFalse(); + expect(ex.Flags.isEnabled('some-cool-flag')).toBe(false); }); it('should return false if the flag is unknown', () => { - expect(ex.Flags.isEnabled('some-random-flag')).toBeFalse(); + expect(ex.Flags.isEnabled('some-random-flag')).toBe(false); }); it('should not allow flags to be enabled after being frozen', () => { diff --git a/src/spec/FontSourceSpec.ts b/src/spec/vitest/FontSourceSpec.ts similarity index 61% rename from src/spec/FontSourceSpec.ts rename to src/spec/vitest/FontSourceSpec.ts index cc0f3415..5c07e9b5 100644 --- a/src/spec/FontSourceSpec.ts +++ b/src/spec/vitest/FontSourceSpec.ts @@ -6,12 +6,12 @@ describe('A FontSource', () => { }); it('can be constructed', () => { - const fontSource = new ex.FontSource('src/spec/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel'); + const fontSource = new ex.FontSource('/src/spec/assets/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel'); expect(fontSource).toBeDefined(); }); it('can load fonts', async () => { - const fontSource = new ex.FontSource('src/spec/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel'); + const fontSource = new ex.FontSource('/src/spec/assets/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel'); await fontSource.load(); @@ -19,15 +19,15 @@ describe('A FontSource', () => { }); it('adds a FontFace to document.fonts', async () => { - const fontSource = new ex.FontSource('src/spec/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel'); + const fontSource = new ex.FontSource('/src/spec/assets/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel'); await fontSource.load(); - expect(document.fonts.has(fontSource.data)).toBeTrue(); + expect(document.fonts.has(fontSource.data)).toBe(true); }); it('can convert to a Font', async () => { - const fontSource = new ex.FontSource('src/spec/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel'); + const fontSource = new ex.FontSource('/src/spec/assets/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel'); await fontSource.load(); const font = fontSource.toFont(); @@ -36,7 +36,7 @@ describe('A FontSource', () => { }); it('will use options from FontSource', async () => { - const fontSource = new ex.FontSource('src/spec/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel', { + const fontSource = new ex.FontSource('/src/spec/assets/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel', { size: 50, color: ex.Color.Red }); @@ -49,7 +49,7 @@ describe('A FontSource', () => { }); it('will override options when converting to a Font', async () => { - const fontSource = new ex.FontSource('src/spec/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel', { + const fontSource = new ex.FontSource('/src/spec/assets/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel', { size: 50, opacity: 0.5 }); @@ -66,7 +66,7 @@ describe('A FontSource', () => { }); it('will resolve the font if already loaded', async () => { - const fontSource = new ex.FontSource('src/spec/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel'); + const fontSource = new ex.FontSource('/src/spec/assets/fonts/Gorgeous Pixel.ttf', 'Gorgeous Pixel'); const font = await fontSource.load(); @@ -77,8 +77,8 @@ describe('A FontSource', () => { }); it("will return error if font doesn't exist", async () => { - const fontSource = new ex.FontSource('42.ttf', '42'); + const fontSource = new ex.FontSource('/42.ttf', '42'); - await expectAsync(fontSource.load()).toBeRejectedWith("Error loading FontSource from path '42.ttf' with error [Not Found]"); + await expect(fontSource.load()).rejects.toThrowError("Error loading FontSource from path '/42.ttf' with error [Not Found]"); }); }); diff --git a/src/spec/FrameStatsSpec.ts b/src/spec/vitest/FrameStatsSpec.ts similarity index 66% rename from src/spec/FrameStatsSpec.ts rename to src/spec/vitest/FrameStatsSpec.ts index a11663b9..1de0a66c 100644 --- a/src/spec/FrameStatsSpec.ts +++ b/src/spec/vitest/FrameStatsSpec.ts @@ -1,7 +1,7 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; import { Mocks } from './util/Mocks'; -import { TestClock } from '@excalibur'; +import type { TestClock } from '@excalibur'; describe('The engine', () => { let engine: ex.Engine; @@ -40,25 +40,25 @@ describe('The engine', () => { describe('after frame is ended', () => { it('should collect frame elapsedMs', () => { - expect(stats.elapsedMs).withContext('Frame stats elapsedMs should be ~16ms').toBeCloseTo(16.6, 0); + expect(stats.elapsedMs, 'Frame stats elapsedMs should be ~16ms').toBeCloseTo(16.6, 0); }); it('should collect frame fps', () => { - expect(stats.fps).withContext('Frame stats fps should be ~60fps').toBeCloseTo(60); + expect(stats.fps, 'Frame stats fps should be ~60fps').toBeCloseTo(60); }); it('should collect frame actor stats', () => { - expect(stats.actors.total).toBe(1, 'Frame actor total is wrong'); - expect(stats.actors.alive).toBe(1, 'Frame actor alive is wrong'); - expect(stats.actors.killed).toBe(0, 'Frame actor killed is wrong'); - expect(stats.actors.remaining).toBe(1, 'Frame actor remaining is wrong'); - expect(stats.actors.ui).toBe(0, 'Frame actor ui count is wrong'); + expect(stats.actors.total, 'Frame actor total is wrong').toBe(1); + expect(stats.actors.alive, 'Frame actor alive is wrong').toBe(1); + expect(stats.actors.killed, 'Frame actor killed is wrong').toBe(0); + expect(stats.actors.remaining, 'Frame actor remaining is wrong').toBe(1); + expect(stats.actors.ui, 'Frame actor ui count is wrong').toBe(0); }); it('should collect frame duration stats', () => { - expect(stats.duration.total).toBeCloseTo(0, 1, 'Frame duration total is wrong'); - expect(stats.duration.draw).toBeCloseTo(0, 1, 'Frame duration draw is wrong'); - expect(stats.duration.update).toBeCloseTo(0, 1, 'Frame duration update is wrong'); + expect(stats.duration.total, 'Frame duration total is wrong').toBeCloseTo(0, 1); + expect(stats.duration.draw, 'Frame duration draw is wrong').toBeCloseTo(0, 1); + expect(stats.duration.update, 'Frame duration update is wrong').toBeCloseTo(0, 1); }); }); }); diff --git a/src/spec/vitest/FutureSpec.ts b/src/spec/vitest/FutureSpec.ts new file mode 100644 index 00000000..1f234db8 --- /dev/null +++ b/src/spec/vitest/FutureSpec.ts @@ -0,0 +1,77 @@ +import * as ex from '@excalibur'; + +describe('A Future', () => { + it('exists', () => { + expect(ex.Future).toBeDefined(); + }); + + it('it can be constructed', () => { + const future = new ex.Future(); + + expect(future).toBeDefined(); + }); + + it('can be resolved', () => + new Promise((done) => { + const future = new ex.Future(); + + expect(future.isCompleted).toBe(false); + + future.promise.then(() => { + expect(future.isCompleted).toBe(true); + done(); + }); + future.resolve(); + })); + + it('can be resolved multiple times without error', () => + new Promise((done) => { + const future = new ex.Future(); + + expect(future.isCompleted).toBe(false); + + future.promise.then(() => { + expect(future.isCompleted).toBe(true); + done(); + }); + expect(() => { + future.resolve(); + future.resolve(); + future.resolve(); + future.resolve(); + }).not.toThrow(); + })); + + it('can be rejected', () => + new Promise((done) => { + const future = new ex.Future(); + + expect(future.isCompleted).toBe(false); + + future.promise.catch((err) => { + expect(err).toEqual(new Error('Some error')); + expect(future.isCompleted).toBe(true); + done(); + }); + future.reject(new Error('Some error')); + })); + + it('can be rejected multiple times without error', () => + new Promise((done) => { + const future = new ex.Future(); + + expect(future.isCompleted).toBe(false); + + future.promise.catch(() => { + expect(future.isCompleted).toBe(true); + done(); + }); + expect(() => { + future.reject(new Error('Some error')); + future.reject(new Error('Some error')); + future.reject(new Error('Some error')); + future.reject(new Error('Some error')); + future.reject(new Error('Some error')); + }).not.toThrow(); + })); +}); diff --git a/src/spec/GamepadSpec.ts b/src/spec/vitest/GamepadSpec.ts similarity index 97% rename from src/spec/GamepadSpec.ts rename to src/spec/vitest/GamepadSpec.ts index f55e1f01..87d46d30 100644 --- a/src/spec/GamepadSpec.ts +++ b/src/spec/vitest/GamepadSpec.ts @@ -13,9 +13,7 @@ describe('A gamepad', () => { nav = mock.navigator(); - spyOn(navigator, 'getGamepads').and.callFake(function (): any[] { - return nav.getGamepads(); - }); + vi.spyOn(navigator, 'getGamepads').mockImplementation(() => nav.getGamepads()); }); afterEach(() => { diff --git a/src/spec/GarbageCollectorSpec.ts b/src/spec/vitest/GarbageCollectorSpec.ts similarity index 80% rename from src/spec/GarbageCollectorSpec.ts rename to src/spec/vitest/GarbageCollectorSpec.ts index b20acb21..fb229f20 100644 --- a/src/spec/GarbageCollectorSpec.ts +++ b/src/spec/vitest/GarbageCollectorSpec.ts @@ -1,16 +1,17 @@ import * as ex from '@excalibur'; +import { type MockInstance } from 'vitest'; describe('A garbage collector', () => { - let requestIdleCallback: jasmine.Spy<(typeof window)['requestIdleCallback']>; - let cancelIdleCallback: jasmine.Spy<(typeof window)['cancelIdleCallback']>; + let requestIdleCallback: MockInstance; + let cancelIdleCallback: MockInstance; it('exists', () => { expect(ex.GarbageCollector).toBeDefined(); }); beforeEach(() => { - requestIdleCallback = spyOn(window, 'requestIdleCallback'); - cancelIdleCallback = spyOn(window, 'cancelIdleCallback'); + requestIdleCallback = vi.spyOn(window, 'requestIdleCallback'); + cancelIdleCallback = vi.spyOn(window, 'cancelIdleCallback'); }); it('can be started', () => { @@ -36,7 +37,7 @@ describe('A garbage collector', () => { const getTimestamp = () => currentTime; const sut = new ex.GarbageCollector({ getTimestamp }); - const collect = jasmine.createSpy('collect').and.returnValue(true); + const collect = vi.fn(() => true); sut.start(); sut.registerCollector('test', 100, collect); @@ -56,7 +57,7 @@ describe('A garbage collector', () => { const getTimestamp = () => currentTime; const sut = new ex.GarbageCollector({ getTimestamp }); - const collect = jasmine.createSpy('collect').and.returnValue(true); + const collect = vi.fn(() => true); sut.start(); sut.registerCollector('test', 100, collect); @@ -81,7 +82,7 @@ describe('A garbage collector', () => { const getTimestamp = () => currentTime; const sut = new ex.GarbageCollector({ getTimestamp }); - const collect = jasmine.createSpy('collect').and.returnValue(true); + const collect = vi.fn(() => true); sut.start(); sut.registerCollector('test', 100, collect); @@ -93,7 +94,7 @@ describe('A garbage collector', () => { sut.forceCollectAll(); - expect(collect.calls.argsFor(0)).toEqual([resource]); - expect(collect.calls.argsFor(1)).toEqual([resource2]); + expect(collect.mock.calls[0]).toEqual([resource]); + expect(collect.mock.calls[1]).toEqual([resource2]); }); }); diff --git a/src/spec/GifSpec.ts b/src/spec/vitest/GifSpec.ts similarity index 64% rename from src/spec/GifSpec.ts rename to src/spec/vitest/GifSpec.ts index 4fbdf2c5..0ee9fb65 100644 --- a/src/spec/GifSpec.ts +++ b/src/spec/vitest/GifSpec.ts @@ -1,4 +1,3 @@ -import { ExcaliburMatchers, ensureImagesLoaded, ExcaliburAsyncMatchers } from 'excalibur-jasmine'; import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; @@ -6,14 +5,12 @@ describe('A Gif', () => { let engine: ex.Engine; let gif: ex.Gif; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); engine = TestUtils.engine({ width: 100, height: 100 }); - gif = new ex.Gif('src/spec/images/GifSpec/sword.gif'); + gif = new ex.Gif('/src/spec/assets/images/GifSpec/sword.gif'); }); afterEach(() => { engine.stop(); @@ -21,16 +18,17 @@ describe('A Gif', () => { engine = null; }); - it('should parse gif files correctly', (done) => { - gif.load().then(() => { - expect(gif).not.toBeNull(); - expect(gif.readCheckBytes).toEqual([11, 3, 4, 11, 4]); - done(); - }); - }); + it('should parse gif files correctly', () => + new Promise((done) => { + gif.load().then(() => { + expect(gif).not.toBeNull(); + expect(gif.readCheckBytes).toEqual([11, 3, 4, 11, 4]); + done(); + }); + })); it('should parse gifs that have lct & anim params', async () => { - const sut = new ex.Gif('src/spec/images/GifSpec/loading-screen.gif'); + const sut = new ex.Gif('/src/spec/assets/images/GifSpec/loading-screen.gif'); await sut.load(); const sprite = sut.toSprite(20); @@ -39,11 +37,11 @@ describe('A Gif', () => { sprite.draw(engine.graphicsContext, 0, 0); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GifSpec/loading-frame-20.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GifSpec/loading-frame-20.png'); }); it('should parse gifs that have animations with sub frames', async () => { - const sut = new ex.Gif('src/spec/images/GifSpec/stoplight.gif'); + const sut = new ex.Gif('/src/spec/assets/images/GifSpec/stoplight.gif'); await sut.load(); expect(sut.isLoaded()).toBe(true); @@ -51,19 +49,19 @@ describe('A Gif', () => { sprite2.draw(engine.graphicsContext, 0, 0); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GifSpec/stoplight-frame-3.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GifSpec/stoplight-frame-3.png'); const sprite1 = sut.toSprite(1); sprite1.draw(engine.graphicsContext, 0, 0); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GifSpec/stoplight-frame-2.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GifSpec/stoplight-frame-2.png'); const sprite0 = sut.toSprite(0); sprite0.draw(engine.graphicsContext, 0, 0); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GifSpec/stoplight-frame-1.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GifSpec/stoplight-frame-1.png'); }); it('should load each frame', async () => { @@ -80,7 +78,7 @@ describe('A Gif', () => { sprite.draw(engine.graphicsContext, 0, 0); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GifSpec/frame1.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GifSpec/frame1.png'); engine.graphicsContext.backgroundColor = ex.Color.Transparent; engine.graphicsContext.clear(); @@ -89,7 +87,7 @@ describe('A Gif', () => { sprite.draw(engine.graphicsContext, 0, 0); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GifSpec/frame2.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GifSpec/frame2.png'); }); it('should be read as a SpriteSheet', async () => { @@ -100,7 +98,7 @@ describe('A Gif', () => { sprite.draw(engine.graphicsContext, 0, 0); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GifSpec/frame1.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GifSpec/frame1.png'); }); it('should be read as an Animation', async () => { @@ -115,6 +113,6 @@ describe('A Gif', () => { frame2.graphic.draw(engine.graphicsContext, 0, 0); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GifSpec/frame2.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GifSpec/frame2.png'); }); }); diff --git a/src/spec/GpuParticleSpec.ts b/src/spec/vitest/GpuParticleSpec.ts similarity index 94% rename from src/spec/GpuParticleSpec.ts rename to src/spec/vitest/GpuParticleSpec.ts index cc514e1a..57c640ca 100644 --- a/src/spec/GpuParticleSpec.ts +++ b/src/spec/vitest/GpuParticleSpec.ts @@ -1,4 +1,3 @@ -import { ExcaliburMatchers, ExcaliburAsyncMatchers } from 'excalibur-jasmine'; import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; @@ -6,8 +5,6 @@ describe('A GPU particle', () => { let engine: ex.Engine; let scene: ex.Scene; beforeEach(async () => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); engine = TestUtils.engine( { width: 800, @@ -128,7 +125,7 @@ describe('A GPU particle', () => { engine.currentScene.update(engine, 100); engine.currentScene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GpuParticlesSpec/particles.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GpuParticlesSpec/particles.png'); }); it('should clear particles', async () => { @@ -171,7 +168,7 @@ describe('A GPU particle', () => { engine.currentScene.update(engine, 100); engine.currentScene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GpuParticlesSpec/clear.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GpuParticlesSpec/clear.png'); }); it("should emit particles and wrap it's ring buffer", async () => { @@ -228,7 +225,7 @@ describe('A GPU particle', () => { engine.currentScene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GpuParticlesSpec/particles-wrapped.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GpuParticlesSpec/particles-wrapped.png'); }); it('can be parented', async () => { @@ -278,7 +275,7 @@ describe('A GPU particle', () => { engine.currentScene.update(engine, 100); engine.currentScene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/ParticleSpec/parented.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/ParticleSpec/parented.png'); }); it('can set the particle transform to local making particles children of the emitter', () => { diff --git a/src/spec/GraphicSpec.ts b/src/spec/vitest/GraphicSpec.ts similarity index 83% rename from src/spec/GraphicSpec.ts rename to src/spec/vitest/GraphicSpec.ts index e08498a2..0b980ad8 100644 --- a/src/spec/GraphicSpec.ts +++ b/src/spec/vitest/GraphicSpec.ts @@ -1,5 +1,4 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; class TestGraphic extends ex.Graphic { constructor(options?: ex.GraphicOptions) { @@ -47,9 +46,6 @@ describe('A Graphic', () => { let canvasElement: HTMLCanvasElement; let ctx: ex.ExcaliburGraphicsContext; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - canvasElement = document.createElement('canvas'); canvasElement.width = 100; canvasElement.height = 100; @@ -108,7 +104,7 @@ describe('A Graphic', () => { ctx.clear(); const sut = new TestGraphic(); sut.draw(ctx, 25, 25); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicSpec/base.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicSpec/base.png'); }); it('has local bounds based on the width/height', () => { @@ -121,7 +117,7 @@ describe('A Graphic', () => { const sut = new TestGraphic(); sut.rotation = Math.PI / 4; sut.draw(ctx, 25, 25); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicSpec/rotated.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicSpec/rotated.png'); }); it('can flip a graphic implementation', async () => { @@ -130,7 +126,7 @@ describe('A Graphic', () => { sut.flipHorizontal = true; sut.flipVertical = true; sut.draw(ctx, 25, 25); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicSpec/flipped.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicSpec/flipped.png'); }); it('can scale a graphic implementation', async () => { @@ -138,7 +134,7 @@ describe('A Graphic', () => { const sut = new TestGraphic(); sut.scale = ex.vec(2, 2); sut.draw(ctx, 25, 25); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicSpec/scaled.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicSpec/scaled.png'); }); it('can set opacity on a graphic implementation', async () => { @@ -146,7 +142,7 @@ describe('A Graphic', () => { const sut = new TestGraphic(); sut.opacity = 0.2; sut.draw(ctx, 25, 25); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicSpec/opacity.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicSpec/opacity.png'); }); it('can show a debug rect', async () => { @@ -154,6 +150,6 @@ describe('A Graphic', () => { const sut = new TestGraphic(); sut.showDebug = true; sut.draw(ctx, 25, 25); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicSpec/debug.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicSpec/debug.png'); }); }); diff --git a/src/spec/GraphicsComponentSpec.ts b/src/spec/vitest/GraphicsComponentSpec.ts similarity index 97% rename from src/spec/GraphicsComponentSpec.ts rename to src/spec/vitest/GraphicsComponentSpec.ts index baaee378..25cc2868 100644 --- a/src/spec/GraphicsComponentSpec.ts +++ b/src/spec/vitest/GraphicsComponentSpec.ts @@ -1,12 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; describe('A Graphics ECS Component', () => { - beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - it('exists', () => { expect(ex.GraphicsComponent); }); @@ -171,7 +165,7 @@ describe('A Graphics ECS Component', () => { }); const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); expect(sut.current).toBeUndefined(); sut.use('some-gfx-2'); @@ -265,7 +259,7 @@ describe('A Graphics ECS Component', () => { const animation = new ex.Animation({ frames: [] }); - spyOn(animation, 'tick'); + vi.spyOn(animation, 'tick'); const sut = new ex.GraphicsComponent(); sut.add(animation); diff --git a/src/spec/GraphicsGroupSpec.ts b/src/spec/vitest/GraphicsGroupSpec.ts similarity index 82% rename from src/spec/GraphicsGroupSpec.ts rename to src/spec/vitest/GraphicsGroupSpec.ts index bafd033b..ea9a4de5 100644 --- a/src/spec/GraphicsGroupSpec.ts +++ b/src/spec/vitest/GraphicsGroupSpec.ts @@ -1,12 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; describe('A Graphics Group', () => { - beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - it('exists', () => { expect(ex.GraphicsGroup).toBeDefined(); }); @@ -44,7 +38,7 @@ describe('A Graphics Group', () => { ctx.clear(); group.draw(ctx, 25, 25); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsGroupSpec/graphics-group.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsGroupSpec/graphics-group.png'); }); it('can be created and drawn without anchor', async () => { @@ -81,7 +75,7 @@ describe('A Graphics Group', () => { ctx.clear(); group.draw(ctx, 100, 100); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsGroupSpec/graphics-group-without-anchor.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsGroupSpec/graphics-group-without-anchor.png'); }); it('can be cloned', () => { @@ -100,9 +94,7 @@ describe('A Graphics Group', () => { const animation = new ex.Animation({ frames: [] }); - spyOn(animation, 'tick').and.callFake((elapsed, idempot) => { - // fake - }); + vi.spyOn(animation, 'tick').mockImplementation(() => void 0); const group = new ex.GraphicsGroup({ members: [{ offset: ex.vec(0, 0), graphic: animation }] @@ -116,9 +108,7 @@ describe('A Graphics Group', () => { const animation = new ex.Animation({ frames: [] }); - spyOn(animation, 'reset').and.callFake(() => { - // fake - }); + vi.spyOn(animation, 'reset').mockImplementation(() => void 0); const group = new ex.GraphicsGroup({ members: [{ offset: ex.vec(0, 0), graphic: animation }] diff --git a/src/spec/GraphicsSystemSpec.ts b/src/spec/vitest/GraphicsSystemSpec.ts similarity index 85% rename from src/spec/GraphicsSystemSpec.ts rename to src/spec/vitest/GraphicsSystemSpec.ts index 15d1d625..598af0ca 100644 --- a/src/spec/GraphicsSystemSpec.ts +++ b/src/spec/vitest/GraphicsSystemSpec.ts @@ -1,16 +1,12 @@ import * as ex from '@excalibur'; import { TransformComponent } from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; -import { GraphicsComponent } from '../engine/Graphics'; +import { GraphicsComponent } from '../../engine/Graphics'; import { TestUtils } from './util/TestUtils'; describe('A Graphics ECS System', () => { let entities: ex.Entity[]; let engine: ex.Engine; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - engine = TestUtils.engine({ width: 100, height: 100 }); entities = [ new ex.Entity().addComponent(new ex.TransformComponent()).addComponent(new ex.GraphicsComponent()), @@ -96,10 +92,10 @@ describe('A Graphics ECS System', () => { offscreen.get(TransformComponent).pos = ex.vec(112.5, 112.5); offscreen.get(GraphicsComponent).use(offscreenRect); - spyOn(rect, 'draw').and.callThrough(); - spyOn(circle, 'draw').and.callThrough(); - spyOn(rect2, 'draw').and.callThrough(); - spyOn(offscreenRect, 'draw').and.callThrough(); + vi.spyOn(rect, 'draw'); + vi.spyOn(circle, 'draw'); + vi.spyOn(rect2, 'draw'); + vi.spyOn(offscreenRect, 'draw'); entities.push(offscreen); engine.graphicsContext.clear(); @@ -117,7 +113,7 @@ describe('A Graphics ECS System', () => { expect(offscreenRect.draw).not.toHaveBeenCalled(); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GraphicsSystemSpec/graphics-system.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GraphicsSystemSpec/graphics-system.png'); }); it('will interpolate body graphics when fixed update is enabled', async () => { @@ -136,9 +132,9 @@ describe('A Graphics ECS System', () => { actor.body.__oldTransformCaptured = true; - spyOn(game.graphicsContext, 'translate'); - spyOn(game.graphicsContext, 'rotate'); - spyOn(game.graphicsContext, 'scale'); + vi.spyOn(game.graphicsContext, 'translate'); + vi.spyOn(game.graphicsContext, 'rotate'); + vi.spyOn(game.graphicsContext, 'scale'); const graphicsSystem = new ex.GraphicsSystem(game.currentScene.world); graphicsSystem.initialize(game.currentScene.world, game.currentScene); @@ -174,9 +170,9 @@ describe('A Graphics ECS System', () => { actor.body.__oldTransformCaptured = true; - const translateSpy = spyOn(game.graphicsContext, 'translate'); - spyOn(game.graphicsContext, 'rotate'); - spyOn(game.graphicsContext, 'scale'); + const translateSpy = vi.spyOn(game.graphicsContext, 'translate'); + vi.spyOn(game.graphicsContext, 'rotate'); + vi.spyOn(game.graphicsContext, 'scale'); const graphicsSystem = new ex.GraphicsSystem(game.currentScene.world); graphicsSystem.initialize(game.currentScene.world, game.currentScene); @@ -186,8 +182,8 @@ describe('A Graphics ECS System', () => { game.currentFrameLagMs = 1000 / 30 / 2; // current lag in a 30 fps frame graphicsSystem.update(16); - expect(translateSpy.calls.argsFor(0)).toEqual([10, 10]); - expect(translateSpy.calls.argsFor(1)).toEqual([45, 45]); // 45 because the parent offsets by (-10, -10) + expect(translateSpy.mock.calls[0]).toEqual([10, 10]); + expect(translateSpy.mock.calls[1]).toEqual([45, 45]); // 45 because the parent offsets by (-10, -10) game.dispose(); }); @@ -207,9 +203,9 @@ describe('A Graphics ECS System', () => { actor.body.__oldTransformCaptured = true; - spyOn(game.graphicsContext, 'translate'); - spyOn(game.graphicsContext, 'rotate'); - spyOn(game.graphicsContext, 'scale'); + vi.spyOn(game.graphicsContext, 'translate'); + vi.spyOn(game.graphicsContext, 'rotate'); + vi.spyOn(game.graphicsContext, 'scale'); const graphicsSystem = new ex.GraphicsSystem(game.currentScene.world); graphicsSystem.initialize(game.currentScene.world, game.currentScene); @@ -255,7 +251,7 @@ describe('A Graphics ECS System', () => { sut.update(1); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GraphicsSystemSpec/graphics-context-opacity.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GraphicsSystemSpec/graphics-context-opacity.png'); }); it('can flip graphics horizontally', async () => { @@ -268,7 +264,7 @@ describe('A Graphics ECS System', () => { offscreenSystem.initialize(world, engine.currentScene); sut.initialize(world, engine.currentScene); - const sword = new ex.ImageSource('src/spec/images/GraphicsSystemSpec/sword.png'); + const sword = new ex.ImageSource('/src/spec/assets/images/GraphicsSystemSpec/sword.png'); await sword.load(); const actor = new ex.Actor({ @@ -289,7 +285,7 @@ describe('A Graphics ECS System', () => { sut.update(1); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GraphicsSystemSpec/sword-flip-horizontal.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GraphicsSystemSpec/sword-flip-horizontal.png'); }); it('can flip graphics vertically', async () => { @@ -302,7 +298,7 @@ describe('A Graphics ECS System', () => { offscreenSystem.initialize(world, engine.currentScene); sut.initialize(world, engine.currentScene); - const sword = new ex.ImageSource('src/spec/images/GraphicsSystemSpec/sword.png'); + const sword = new ex.ImageSource('/src/spec/assets/images/GraphicsSystemSpec/sword.png'); await sword.load(); const actor = new ex.Actor({ @@ -323,7 +319,7 @@ describe('A Graphics ECS System', () => { sut.update(1); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GraphicsSystemSpec/sword-flip-vertical.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GraphicsSystemSpec/sword-flip-vertical.png'); }); it('can flip graphics both horizontally and vertically', async () => { @@ -336,7 +332,7 @@ describe('A Graphics ECS System', () => { offscreenSystem.initialize(world, engine.currentScene); sut.initialize(world, engine.currentScene); - const sword = new ex.ImageSource('src/spec/images/GraphicsSystemSpec/sword.png'); + const sword = new ex.ImageSource('/src/spec/assets/images/GraphicsSystemSpec/sword.png'); await sword.load(); const actor = new ex.Actor({ @@ -358,7 +354,7 @@ describe('A Graphics ECS System', () => { sut.update(1); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GraphicsSystemSpec/sword-flip-both.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GraphicsSystemSpec/sword-flip-both.png'); }); it('can flip graphics both horizontally and vertically with an offset', async () => { @@ -371,7 +367,7 @@ describe('A Graphics ECS System', () => { offscreenSystem.initialize(world, engine.currentScene); sut.initialize(world, engine.currentScene); - const sword = new ex.ImageSource('src/spec/images/GraphicsSystemSpec/sword.png'); + const sword = new ex.ImageSource('/src/spec/assets/images/GraphicsSystemSpec/sword.png'); await sword.load(); const actor = new ex.Actor({ @@ -394,7 +390,7 @@ describe('A Graphics ECS System', () => { sut.update(1); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/GraphicsSystemSpec/sword-flip-both-offset.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/GraphicsSystemSpec/sword-flip-both-offset.png'); }); it('can add graphics+transform to a parent without a transform', () => { diff --git a/src/spec/ImageSourceSpec.ts b/src/spec/vitest/ImageSourceSpec.ts similarity index 78% rename from src/spec/ImageSourceSpec.ts rename to src/spec/vitest/ImageSourceSpec.ts index 2305bb91..fc8368df 100644 --- a/src/spec/ImageSourceSpec.ts +++ b/src/spec/vitest/ImageSourceSpec.ts @@ -1,14 +1,9 @@ import * as ex from '@excalibur'; -import { ImageRenderer } from '../engine/Graphics/Context/image-renderer/image-renderer'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; +import { ImageRenderer } from '../../engine/Graphics/Context/image-renderer/image-renderer'; describe('A ImageSource', () => { let canvasElement: HTMLCanvasElement; let ctx: ex.ExcaliburGraphicsContext; - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); beforeEach(() => { ex.TextureLoader.filtering = ex.ImageFiltering.Pixel; @@ -29,13 +24,13 @@ describe('A ImageSource', () => { }); it('can be constructed', () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); expect(spriteFontImage).toBeDefined(); }); it('logs a warning on image type not supported', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); const image1 = new ex.ImageSource('base/404/img.svg'); expect(logger.warn).toHaveBeenCalledTimes(0); const image2 = new ex.ImageSource('base/404/img.gif'); @@ -43,8 +38,8 @@ describe('A ImageSource', () => { }); it('can load images', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); - const whenLoaded = jasmine.createSpy('whenLoaded'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); + const whenLoaded = vi.fn(); const image = await spriteFontImage.load(); await spriteFontImage.ready.then(whenLoaded); @@ -67,7 +62,7 @@ describe('A ImageSource', () => { l241.211-241.211L418.506,606.348z"/> `); - const whenLoaded = jasmine.createSpy('whenLoaded'); + const whenLoaded = vi.fn(); await svgImage.load(); await svgImage.ready.then(whenLoaded); expect(svgImage.image.src).not.toBeNull(); @@ -75,8 +70,8 @@ describe('A ImageSource', () => { }); it('can load svg images', async () => { - const svgImage = new ex.ImageSource('src/spec/images/GraphicsImageSourceSpec/arrows.svg'); - const whenLoaded = jasmine.createSpy('whenLoaded'); + const svgImage = new ex.ImageSource('/src/spec/assets/images/GraphicsImageSourceSpec/arrows.svg'); + const whenLoaded = vi.fn(); await svgImage.load(); await svgImage.ready.then(whenLoaded); expect(svgImage.image.src).not.toBeNull(); @@ -96,15 +91,15 @@ describe('A ImageSource', () => { backgroundColor: ex.Color.White }); const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); - spyOn(logger, 'error'); + vi.spyOn(logger, 'warn'); + vi.spyOn(logger, 'error'); - const sut = new ex.ImageSource('src/spec/images/GraphicsImageSourceSpec/big-image.png'); + const sut = new ex.ImageSource('/src/spec/assets/images/GraphicsImageSourceSpec/big-image.png'); await sut.load(); expect(logger.warn).toHaveBeenCalledWith( - `The image [src/spec/images/GraphicsImageSourceSpec/big-image.png] provided to excalibur` + + `The image [/src/spec/assets/images/GraphicsImageSourceSpec/big-image.png] provided to excalibur` + ` is too large may not work on all mobile devices, it is recommended you resize images to a maximum (4096x4096).\n\n` + `Images will likely render as black rectangles on some mobile platforms.\n\n` + `Read more here: https://developer.mozilla.org/en-US/docs/Web/API/WebGL_API/WebGL_best_practices#understand_system_limits` @@ -122,17 +117,17 @@ describe('A ImageSource', () => { backgroundColor: ex.Color.White }); const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); - spyOn(logger, 'error'); + vi.spyOn(logger, 'warn'); + vi.spyOn(logger, 'error'); (ex.TextureLoader as any)._MAX_TEXTURE_SIZE = 4096; - const sut = new ex.ImageSource('src/spec/images/GraphicsImageSourceSpec/big-image.png'); + const sut = new ex.ImageSource('/src/spec/assets/images/GraphicsImageSourceSpec/big-image.png'); await sut.load(); expect(logger.error).toHaveBeenCalledWith( - `The image [src/spec/images/GraphicsImageSourceSpec/big-image.png] provided to Excalibur is too large for the device's maximum ` + + `The image [/src/spec/assets/images/GraphicsImageSourceSpec/big-image.png] provided to Excalibur is too large for the device's maximum ` + `texture size of (4096x4096) please resize to an image for excalibur to render properly.\n\n` + `Images will likely render as black rectangles.\n\n` + `Read more here: https://developer.mozilla.org/en-US/docs/Web/API/WebGL_API/WebGL_best_practices#understand_system_limits` @@ -146,10 +141,10 @@ describe('A ImageSource', () => { }); const imageRenderer = new ImageRenderer({ pixelArtSampler: false, uvPadding: 0 }); imageRenderer.initialize(webgl.__gl, webgl); - spyOn(webgl.textureLoader, 'load').and.callThrough(); + vi.spyOn(webgl.textureLoader, 'load'); - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png', false, ex.ImageFiltering.Blended); - const whenLoaded = jasmine.createSpy('whenLoaded'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png', false, ex.ImageFiltering.Blended); + const whenLoaded = vi.fn(); const image = await spriteFontImage.load(); await spriteFontImage.ready.then(whenLoaded); @@ -177,10 +172,10 @@ describe('A ImageSource', () => { }); const imageRenderer = new ImageRenderer({ pixelArtSampler: false, uvPadding: 0 }); imageRenderer.initialize(webgl.__gl, webgl); - spyOn(webgl.textureLoader, 'load').and.callThrough(); + vi.spyOn(webgl.textureLoader, 'load'); - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png', false, ex.ImageFiltering.Pixel); - const whenLoaded = jasmine.createSpy('whenLoaded'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png', false, ex.ImageFiltering.Pixel); + const whenLoaded = vi.fn(); const image = await spriteFontImage.load(); await spriteFontImage.ready.then(whenLoaded); @@ -208,13 +203,13 @@ describe('A ImageSource', () => { }); const imageRenderer = new ImageRenderer({ pixelArtSampler: false, uvPadding: 0 }); imageRenderer.initialize(webgl.__gl, webgl); - spyOn(webgl.textureLoader, 'load').and.callThrough(); + vi.spyOn(webgl.textureLoader, 'load'); - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png', { + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png', { filtering: ex.ImageFiltering.Pixel, wrapping: ex.ImageWrapping.Repeat }); - const whenLoaded = jasmine.createSpy('whenLoaded'); + const whenLoaded = vi.fn(); const image = await spriteFontImage.load(); await spriteFontImage.ready.then(whenLoaded); @@ -242,13 +237,13 @@ describe('A ImageSource', () => { }); const imageRenderer = new ImageRenderer({ pixelArtSampler: false, uvPadding: 0 }); imageRenderer.initialize(webgl.__gl, webgl); - spyOn(webgl.textureLoader, 'load').and.callThrough(); + vi.spyOn(webgl.textureLoader, 'load'); - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png', { + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png', { filtering: ex.ImageFiltering.Pixel, wrapping: ex.ImageWrapping.Mirror }); - const whenLoaded = jasmine.createSpy('whenLoaded'); + const whenLoaded = vi.fn(); const image = await spriteFontImage.load(); await spriteFontImage.ready.then(whenLoaded); @@ -276,18 +271,18 @@ describe('A ImageSource', () => { }); const imageRenderer = new ImageRenderer({ pixelArtSampler: false, uvPadding: 0 }); imageRenderer.initialize(webgl.__gl, webgl); - spyOn(webgl.textureLoader, 'load').and.callThrough(); - const texParameteri = spyOn(webgl.__gl, 'texParameteri').and.callThrough(); + vi.spyOn(webgl.textureLoader, 'load'); + const texParameteri = vi.spyOn(webgl.__gl, 'texParameteri'); const gl = webgl.__gl; - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png', { + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png', { filtering: ex.ImageFiltering.Pixel, wrapping: { x: ex.ImageWrapping.Mirror, y: ex.ImageWrapping.Clamp } }); - const whenLoaded = jasmine.createSpy('whenLoaded'); + const whenLoaded = vi.fn(); const image = await spriteFontImage.load(); await spriteFontImage.ready.then(whenLoaded); @@ -295,8 +290,8 @@ describe('A ImageSource', () => { expect(image.src).not.toBeNull(); expect(whenLoaded).toHaveBeenCalledTimes(1); - expect(texParameteri.calls.argsFor(0)).toEqual([gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.MIRRORED_REPEAT]); - expect(texParameteri.calls.argsFor(1)).toEqual([gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE]); + expect(texParameteri.mock.calls[0]).toEqual([gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.MIRRORED_REPEAT]); + expect(texParameteri.mock.calls[1]).toEqual([gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE]); expect(webgl.textureLoader.load).toHaveBeenCalledWith( image, { @@ -311,7 +306,7 @@ describe('A ImageSource', () => { }); it('can convert to a Sprite', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const sprite = spriteFontImage.toSprite(); // Sprites have no width/height until the underlying image is loaded @@ -325,7 +320,7 @@ describe('A ImageSource', () => { }); it('can convert to a Sprite with options', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const sprite = spriteFontImage.toSprite({ sourceView: { x: 16, @@ -350,7 +345,7 @@ describe('A ImageSource', () => { }); it('can unload from memory', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); expect(spriteFontImage.image.src).not.toBeNull(); spriteFontImage.unload(); @@ -358,7 +353,7 @@ describe('A ImageSource', () => { }); it('will resolve the image if already loaded', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const image = await spriteFontImage.load(); expect(spriteFontImage.isLoaded()).toBe(true); @@ -380,9 +375,9 @@ describe('A ImageSource', () => { }); it("will return error if image doesn't exist", async () => { - const spriteFontImage = new ex.ImageSource('42.png'); + const spriteFontImage = new ex.ImageSource('/42.png'); - await expectAsync(spriteFontImage.load()).toBeRejectedWith("Error loading ImageSource from path '42.png' with error [Not Found]"); + await expect(spriteFontImage.load()).rejects.toThrowError("Error loading ImageSource from path '/42.png' with error [Not Found]"); }); it('can be built from canvas elements', async () => { @@ -401,7 +396,7 @@ describe('A ImageSource', () => { sprite.draw(ctx, 0, 0); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsImageSourceSpec/canvas-image.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsImageSourceSpec/canvas-image.png'); }); it('can be built from canvas elements with wrapping/filtering specified', async () => { @@ -439,6 +434,6 @@ describe('A ImageSource', () => { sprite.draw(ctx, 0, 0); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsImageSourceSpec/canvas-image.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsImageSourceSpec/canvas-image.png'); }); }); diff --git a/src/spec/InputMapperSpec.ts b/src/spec/vitest/InputMapperSpec.ts similarity index 78% rename from src/spec/InputMapperSpec.ts rename to src/spec/vitest/InputMapperSpec.ts index cd98f743..67f776cb 100644 --- a/src/spec/InputMapperSpec.ts +++ b/src/spec/vitest/InputMapperSpec.ts @@ -7,9 +7,10 @@ describe('An InputMapper', () => { }); it('can listen to events and map to the command', () => { - const command = jasmine.createSpy('command'); - const keyboard = jasmine.createSpyObj('keyboard', ['isHeld']); - keyboard.isHeld.and.returnValue(true); + const command = vi.fn(); + const keyboard = { + isHeld: vi.fn(() => true) + }; const sut = new ex.InputMapper({ keyboard: keyboard as unknown as ex.Keyboard, pointers: {} as any, @@ -29,11 +30,12 @@ describe('An InputMapper', () => { }); it('can listen to events and not map to the command', () => { - const command = jasmine.createSpy('command'); - const keyboard = jasmine.createSpyObj('keyboard', ['isHeld']); - keyboard.isHeld.and.returnValue(false); + const command = vi.fn(); + const keyboard = { + isHeld: vi.fn(() => false) + }; const sut = new ex.InputMapper({ - keyboard: keyboard, + keyboard: keyboard as any, pointers: {} as any, gamepads: {} as any }); @@ -58,8 +60,8 @@ describe('An InputMapper', () => { engine.input.keyboard.triggerEvent('down', ex.Keys.Space); const sut = engine.inputMapper; - const keyPressedSpy = jasmine.createSpy('keyPressed'); - const keyReleasedSpy = jasmine.createSpy('keyReleased'); + const keyPressedSpy = vi.fn(); + const keyReleasedSpy = vi.fn(); sut.on(({ keyboard }) => keyboard.wasPressed(ex.Keys.Space), keyPressedSpy); sut.on(({ keyboard }) => keyboard.wasReleased(ex.Keys.Space), keyReleasedSpy); diff --git a/src/spec/IsometricMapSpec.ts b/src/spec/vitest/IsometricMapSpec.ts similarity index 87% rename from src/spec/IsometricMapSpec.ts rename to src/spec/vitest/IsometricMapSpec.ts index 512cc901..d2d936ed 100644 --- a/src/spec/IsometricMapSpec.ts +++ b/src/spec/vitest/IsometricMapSpec.ts @@ -1,12 +1,8 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; + import { TestUtils } from './util/TestUtils'; describe('A IsometricMap', () => { - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - jasmine.addMatchers(ExcaliburMatchers); - }); it('exists', () => { expect(ex.IsometricMap).toBeDefined(); }); @@ -27,7 +23,7 @@ describe('A IsometricMap', () => { const engine = TestUtils.engine({}, ['suppress-obsolete-message']); // engine.toggleDebug(); const clock = engine.clock as ex.TestClock; - const image = new ex.ImageSource('src/spec/images/IsometricMapSpec/tile.png'); + const image = new ex.ImageSource('/src/spec/assets/images/IsometricMapSpec/tile.png'); await image.load(); const sprite = image.toSprite(); await TestUtils.runToReady(engine); @@ -45,7 +41,7 @@ describe('A IsometricMap', () => { engine.add(sut); clock.step(100); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/IsometricMapSpec/map.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/IsometricMapSpec/map.png'); engine.dispose(); }); @@ -53,7 +49,7 @@ describe('A IsometricMap', () => { const engine = TestUtils.engine({}, ['suppress-obsolete-message']); // engine.toggleDebug(); const clock = engine.clock as ex.TestClock; - const image = new ex.ImageSource('src/spec/images/IsometricMapSpec/cube.png'); + const image = new ex.ImageSource('/src/spec/assets/images/IsometricMapSpec/cube.png'); await image.load(); const sprite = image.toSprite(); await TestUtils.runToReady(engine); @@ -72,7 +68,7 @@ describe('A IsometricMap', () => { engine.add(sut); clock.step(100); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/IsometricMapSpec/cube-map-top.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/IsometricMapSpec/cube-map-top.png'); engine.dispose(); }); @@ -80,7 +76,7 @@ describe('A IsometricMap', () => { const engine = TestUtils.engine({}, ['suppress-obsolete-message']); // engine.toggleDebug(); const clock = engine.clock as ex.TestClock; - const image = new ex.ImageSource('src/spec/images/IsometricMapSpec/cube.png'); + const image = new ex.ImageSource('/src/spec/assets/images/IsometricMapSpec/cube.png'); await image.load(); const sprite = image.toSprite(); await TestUtils.runToReady(engine); @@ -98,7 +94,7 @@ describe('A IsometricMap', () => { engine.add(sut); clock.step(100); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/IsometricMapSpec/cube-map-bottom.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/IsometricMapSpec/cube-map-bottom.png'); engine.dispose(); }); @@ -112,7 +108,7 @@ describe('A IsometricMap', () => { engine.debug.isometric.showGrid = true; engine.debug.isometric.showPosition = true; const clock = engine.clock as ex.TestClock; - const image = new ex.ImageSource('src/spec/images/IsometricMapSpec/cube.png'); + const image = new ex.ImageSource('/src/spec/assets/images/IsometricMapSpec/cube.png'); await image.load(); const sprite = image.toSprite(); await TestUtils.runToReady(engine); @@ -130,7 +126,7 @@ describe('A IsometricMap', () => { engine.add(sut); clock.step(100); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/IsometricMapSpec/cube-map-debug.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/IsometricMapSpec/cube-map-debug.png'); engine.dispose(); }); @@ -245,7 +241,7 @@ describe('A IsometricMap', () => { }); it('can update graphics', async () => { - const image = new ex.ImageSource('src/spec/images/IsometricMapSpec/cube.png'); + const image = new ex.ImageSource('/src/spec/assets/images/IsometricMapSpec/cube.png'); await image.load(); const sprite = image.toSprite(); @@ -315,10 +311,10 @@ describe('A IsometricMap', () => { const tile = sut.getTile(0, 0); - const pointerdown = jasmine.createSpy('pointerdown'); - const pointerup = jasmine.createSpy('pointerup'); - const pointermove = jasmine.createSpy('pointermove'); - const pointercancel = jasmine.createSpy('pointercancel'); + const pointerdown = vi.fn(); + const pointerup = vi.fn(); + const pointermove = vi.fn(); + const pointercancel = vi.fn(); tile.on('pointerdown', pointerdown); tile.on('pointerup', pointerup); tile.on('pointermove', pointermove); diff --git a/src/spec/KeyInputSpec.ts b/src/spec/vitest/KeyInputSpec.ts similarity index 100% rename from src/spec/KeyInputSpec.ts rename to src/spec/vitest/KeyInputSpec.ts diff --git a/src/spec/LabelSpec.ts b/src/spec/vitest/LabelSpec.ts similarity index 91% rename from src/spec/LabelSpec.ts rename to src/spec/vitest/LabelSpec.ts index 2dae6f87..cdc6c3a7 100644 --- a/src/spec/LabelSpec.ts +++ b/src/spec/vitest/LabelSpec.ts @@ -1,4 +1,3 @@ -import { ExcaliburMatchers, ensureImagesLoaded } from 'excalibur-jasmine'; import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; @@ -8,7 +7,6 @@ describe('A label', () => { let scene: ex.Scene; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); engine = TestUtils.engine({ width: 500, height: 500 @@ -58,7 +56,7 @@ describe('A label', () => { }); it('can be constructed with a spritefont', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); diff --git a/src/spec/LineSpec.ts b/src/spec/vitest/LineSpec.ts similarity index 88% rename from src/spec/LineSpec.ts rename to src/spec/vitest/LineSpec.ts index 46d186ba..e7542248 100644 --- a/src/spec/LineSpec.ts +++ b/src/spec/vitest/LineSpec.ts @@ -1,11 +1,7 @@ -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; + describe('A Line', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); it('exists', () => { expect(ex.Line).toBeDefined(); }); @@ -88,7 +84,7 @@ describe('A Line', () => { sut.draw(ctx, 0, 0); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/LineSpec/line.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/LineSpec/line.png'); }); it('can draw a line when added to a graphics component', async () => { @@ -118,7 +114,7 @@ describe('A Line', () => { testClock.step(16); - await expectAsync(game.canvas).toEqualImage('src/spec/images/LineSpec/line.png'); + await expect(game.canvas).toEqualImage('/src/spec/assets/images/LineSpec/line.png'); game.dispose(); }); diff --git a/src/spec/vitest/LoaderSpec.ts b/src/spec/vitest/LoaderSpec.ts new file mode 100644 index 00000000..8c77f982 --- /dev/null +++ b/src/spec/vitest/LoaderSpec.ts @@ -0,0 +1,398 @@ +import * as ex from '@excalibur'; + +import { TestUtils } from './util/TestUtils'; + +describe('A loader', () => { + let engine: ex.Engine; + + const reset = () => { + engine.stop(); + engine.dispose(); + engine = null; + (window).devicePixelRatio = 1; + const playButton = document.getElementById('excalibur-play'); + if (playButton) { + const body = playButton.parentNode.parentNode; + body.removeChild(playButton.parentNode); + } + }; + beforeEach(() => { + engine = TestUtils.engine(); + }); + + afterEach(() => { + engine.stop(); + engine.dispose(); + engine = null; + }); + + it('exists', () => { + expect(ex.Loader).toBeDefined(); + }); + + it('can be constructed', () => { + const loader = new ex.Loader(); + expect(loader).toBeTruthy(); + }); + + it('can report progress, empty loaders are done', () => { + const loader = new ex.Loader(); + expect(loader.progress).toBe(1); + }); + + it('can report progress, loader start at 0', () => { + const loader = new ex.Loader([, , ,]); + expect(loader.progress).toBe(0); + }); + + it('can report progress', () => { + const loader = new ex.Loader([, , , ,]); + expect(loader.progress).toBe(0); + loader.markResourceComplete(); + expect(loader.progress).toBe(0.25); + loader.markResourceComplete(); + expect(loader.progress).toBe(0.5); + loader.markResourceComplete(); + expect(loader.progress).toBe(0.75); + loader.markResourceComplete(); + expect(loader.progress).toBe(1); + }); + + it('can be drawn at 0', () => + new Promise((done) => { + const loader = new ex.Loader([, , , ,]); + (loader as any)._image.onload = () => { + loader.onInitialize(engine); + loader.onDraw(loader.canvas.ctx); + expect(loader.canvas.ctx.canvas) + .toHaveLoadedImages(['/src/spec/assets/images/LoaderSpec/zero.png']) + .then(() => { + done(); + }); + }; + })); + + it('can be drawn at 50', () => + new Promise((done) => { + const loader = new ex.Loader([, , , ,]); + (loader as any)._image.onload = () => { + loader.markResourceComplete(); + loader.markResourceComplete(); + + loader.onInitialize(engine); + loader.onDraw(loader.canvas.ctx); + expect(loader.canvas.ctx.canvas) + .toHaveLoadedImages(['/src/spec/assets/images/LoaderSpec/fifty.png']) + .then(() => { + done(); + }); + }; + })); + + it('can be drawn at 100', () => + new Promise((done) => { + const loader = new ex.Loader([, , , ,]); + (loader as any)._image.onload = () => { + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + + loader.onInitialize(engine); + loader.onDraw(loader.canvas.ctx); + expect(loader.canvas.ctx.canvas) + .toHaveLoadedImages(['/src/spec/assets/images/LoaderSpec/100.png']) + .then(() => { + done(); + }); + }; + })); + + it('does not show progress when the play button is shown', () => + new Promise((done) => { + const loader = new ex.Loader([, , , ,]); + (loader as any)._image.onload = () => { + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.onInitialize(engine); + loader.showPlayButton(); + + loader.onDraw(loader.canvas.ctx); + expect(loader.canvas.ctx.canvas) + .toHaveLoadedImages(['/src/spec/assets/images/LoaderSpec/playbuttonshown-noprogressbar.png']) + .then(() => { + done(); + }); + }; + })); + + it('can have the play button position customized', () => { + const loader = new ex.Loader([, , , ,]); + loader.onInitialize(engine); + loader.playButtonPosition = ex.vec(42, 77); + loader.showPlayButton(); + loader.onDraw(loader.canvas.ctx); + // there is some dom pollution want to be sure we get the RIGHT root element + const playbutton = (loader as any)._playButtonRootElement as HTMLDivElement; + expect(playbutton.style.left).toBe('42px'); + expect(playbutton.style.top).toBe('77px'); + }); + + it('can have the logo position customized', () => + new Promise((done) => { + const loader = new ex.Loader([, , , ,]); + (loader as any)._image.onload = () => { + loader.onInitialize(engine); + loader.logoPosition = ex.vec(0, 0); + loader.showPlayButton(); + loader.onDraw(loader.canvas.ctx); + expect(loader.canvas.ctx.canvas) + .toHaveLoadedImages(['/src/spec/assets/images/LoaderSpec/logo-position.png']) + .then(() => { + done(); + }); + }; + })); + + it('can have the loader customized', () => + new Promise((done) => { + const loader = new ex.Loader([, , , ,]); + loader.loadingBarPosition = ex.vec(0, 0); + loader.loadingBarColor = ex.Color.Red; + (loader as any)._image.onload = () => { + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.onInitialize(engine); + loader.onDraw(loader.canvas.ctx); + expect(loader.canvas.ctx.canvas) + .toHaveLoadedImages(['/src/spec/assets/images/LoaderSpec/loader-position-color.png']) + .then(() => { + done(); + }); + }; + })); + + it('play button shows up after done loading', () => { + const loader = new ex.Loader([, , , ,]); + loader.loadingBarPosition = ex.vec(0, 0); + loader.loadingBarColor = ex.Color.Red; + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.showPlayButton(); + + expect(loader.playButtonRootElement).toBeTruthy(); + }); + + it('play button is cleaned up on dispose', () => { + const loader = new ex.Loader([, , , ,]); + loader.loadingBarPosition = ex.vec(0, 0); + loader.loadingBarColor = ex.Color.Red; + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.showPlayButton(); + loader.dispose(); + expect(loader.playButtonRootElement).toBeFalsy(); + }); + + it('can have the enter key pressed to start', () => + new Promise((done) => { + const loader = new ex.Loader([, , , ,]); + loader.onInitialize(engine); + loader.loadingBarPosition = ex.vec(0, 0); + loader.loadingBarColor = ex.Color.Red; + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.showPlayButton().then(() => { + done(); + loader.dispose(); + }); + document.body.dispatchEvent(new KeyboardEvent('keyup', { key: 'Enter' })); + })); + + it('can reload without building root elements', () => { + const loader = new ex.Loader([, , ,]); + loader.showPlayButton(); + loader.showPlayButton(); + loader.showPlayButton(); + const roots = document.querySelectorAll('#excalibur-play-root'); + const buttons = document.querySelectorAll('#excalibur-play'); + expect(roots.length).toBe(1); + expect(buttons.length).toBe(1); + }); + + /** + * + */ + function executeMouseEvent(type: string, target: HTMLElement, button: ex.NativePointerButton = null, x: number = 0, y: number = 0) { + const evt = new PointerEvent(type, { + clientX: x, + clientY: y, + button: button, + bubbles: true + }); + + target.dispatchEvent(evt); + } + + it('does not propagate the start button click to pointers', async () => { + engine.dispose(); + engine = null; + engine = new ex.Engine({ width: 1000, height: 1000 }); + (ex.WebAudio as any)._UNLOCKED = true; + const clock = (engine.clock = engine.clock.toTestClock()); + const pointerHandler = vi.fn(); + engine.input.pointers.primary.on('up', pointerHandler); + const loader = new ex.Loader([new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png')]); + const start = engine.start(loader); + + await loader.areResourcesLoaded(); + clock.step(200); + + const btn = (loader as any)._playButton; + const btnClickHandler = vi.fn(); + btn.addEventListener('pointerup', btnClickHandler); + const rect = btn.getBoundingClientRect(); + executeMouseEvent('pointerup', btn as any, ex.NativePointerButton.Left, rect.x + rect.width / 2, rect.y + rect.height / 2); + + expect(pointerHandler).not.toHaveBeenCalled(); + expect(btnClickHandler).toHaveBeenCalled(); + }); + + it('updates the play button position on resize', () => { + engine.dispose(); + engine = null; + engine = new ex.Engine({ width: 1000, height: 1000 }); + const loader = new ex.Loader([, , , ,]); + loader.onInitialize(engine); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.markResourceComplete(); + loader.showPlayButton(); + + expect(loader.playButtonRootElement).toBeTruthy(); + + engine.browser.window.nativeComponent.dispatchEvent(new Event('resize')); + + const oldPos = [loader.playButtonRootElement.style.left, loader.playButtonRootElement.style.top]; + + engine.screen.viewport = { width: 100, height: 100 }; + + engine.browser.window.nativeComponent.dispatchEvent(new Event('resize')); + + const newPos = [loader.playButtonRootElement.style.left, loader.playButtonRootElement.style.top]; + + expect(oldPos).not.toEqual(newPos); + }); + + it('does not throw when more than 256 images are being loaded', () => + new Promise((done) => { + /** + * + */ + function drawRandomCircleOnContext(ctx) { + const x = Math.floor(Math.random() * 100); + const y = Math.floor(Math.random() * 100); + const radius = Math.floor(Math.random() * 20); + + const r = Math.floor(Math.random() * 255); + const g = Math.floor(Math.random() * 255); + const b = Math.floor(Math.random() * 255); + + ctx.beginPath(); + ctx.arc(x, y, radius, Math.PI * 2, 0, false); + ctx.fillStyle = 'rgba(' + r + ',' + g + ',' + b + ',1)'; + ctx.fill(); + ctx.closePath(); + } + + /** + * + */ + function generateRandomImage() { + const canvas = document.createElement('canvas'); + canvas.width = 100; + canvas.height = 100; + + const ctx = canvas.getContext('2d'); + ctx.clearRect(0, 0, 100, 100); + + for (let i = 0; i < 20; i++) { + drawRandomCircleOnContext(ctx); + } + return canvas.toDataURL('image/png'); + } + + const logger = ex.Logger.getInstance(); + vi.spyOn(logger, 'error'); + const game = TestUtils.engine({ + width: 100, + height: 100 + }); + const testClock = game.clock as ex.TestClock; + + const loader = new ex.Loader(); + + const srcs = []; + for (let i = 0; i < 800; i++) { + srcs.push(generateRandomImage()); + } + const images = srcs.map((src) => new ex.ImageSource(src)); + images.forEach((image) => { + image.ready.then(() => { + testClock.step(1); + }); + }); + loader.addResources(images); + + const ready = TestUtils.runToReady(game, loader) + .then(() => { + expect(logger.error).not.toHaveBeenCalled(); + game.dispose(); + done(); + }) + .catch(() => { + fail(); + }); + })); + + it('should not show the play button when suppressPlayButton is turned on', () => + new Promise((done, reject) => { + reset(); + engine = TestUtils.engine({ suppressPlayButton: false }); + engine.currentScene.add( + new ex.Actor({ + pos: new ex.Vector(250, 250), + width: 20, + height: 20, + color: ex.Color.Red + }) + ); + + const testClock = engine.clock as ex.TestClock; + const loader = new ex.Loader([new ex.ImageSource('/src/spec/assets/images/SpriteSpec/icon.png')]); + loader.suppressPlayButton = true; + + TestUtils.runToReady(engine, loader).then(async () => { + // With suppress play there is another 500 ms delay in engine load() + testClock.step(1); + engine.graphicsContext.flush(); + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/EngineSpec/engine-suppress-play.png') + .then(() => { + done(); + }) + .catch(reject); + }); + })); +}); diff --git a/src/spec/LogSpec.ts b/src/spec/vitest/LogSpec.ts similarity index 91% rename from src/spec/LogSpec.ts rename to src/spec/vitest/LogSpec.ts index d2b7ab79..5761bdef 100644 --- a/src/spec/LogSpec.ts +++ b/src/spec/vitest/LogSpec.ts @@ -1,14 +1,15 @@ import * as ex from '@excalibur'; +import { type MockInstance } from 'vitest'; describe('Logger', () => { let logger: ex.Logger; describe('ConsoleAppender', () => { let appender: ex.Appender; - let spiedAppender: jasmine.Spy; - let spiedConsoleLog: jasmine.Spy; - let spiedConsoleWarn: jasmine.Spy; - let spiedConsoleError: jasmine.Spy; + let spiedAppender: MockInstance; + let spiedConsoleLog: MockInstance; + let spiedConsoleWarn: MockInstance; + let spiedConsoleError: MockInstance; beforeEach(() => { appender = new ex.ConsoleAppender(); @@ -16,14 +17,13 @@ describe('Logger', () => { logger = ex.Logger.getInstance(); logger.clearAppenders(); logger.addAppender(appender); - spiedAppender = spyOn(appender, 'log'); - spiedAppender.and.callThrough(); + spiedAppender = vi.spyOn(appender, 'log'); logger.defaultLevel = ex.LogLevel.Debug; - spiedConsoleLog = spyOn(console, 'log'); - spiedConsoleWarn = spyOn(console, 'warn'); - spiedConsoleError = spyOn(console, 'error'); + spiedConsoleLog = vi.spyOn(console, 'log'); + spiedConsoleWarn = vi.spyOn(console, 'warn'); + spiedConsoleError = vi.spyOn(console, 'error'); }); afterEach(() => { diff --git a/src/spec/MaterialRendererSpec.ts b/src/spec/vitest/MaterialRendererSpec.ts similarity index 86% rename from src/spec/MaterialRendererSpec.ts rename to src/spec/vitest/MaterialRendererSpec.ts index 1fcbc619..ef39ec07 100644 --- a/src/spec/MaterialRendererSpec.ts +++ b/src/spec/vitest/MaterialRendererSpec.ts @@ -1,13 +1,9 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; -import { ExcaliburAsyncMatchers } from 'excalibur-jasmine'; describe('A Material', () => { let engine: ex.Engine; let graphicsContext: ex.ExcaliburGraphicsContext; - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); beforeEach(() => { engine = TestUtils.engine(); @@ -85,7 +81,7 @@ describe('A Material', () => { }` }); - const tex = new ex.ImageSource('src/spec/images/MaterialRendererSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/MaterialRendererSpec/sword.png'); await tex.load(); graphicsContext.clear(); @@ -96,7 +92,7 @@ describe('A Material', () => { graphicsContext.restore(); expect(graphicsContext.material).toBe(null); - await expectAsync(canvas).toEqualImage('src/spec/images/MaterialRendererSpec/material.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/MaterialRendererSpec/material.png'); graphicsContext.dispose(); }); @@ -128,7 +124,7 @@ describe('A Material', () => { }` }); - const tex = new ex.ImageSource('src/spec/images/MaterialRendererSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/MaterialRendererSpec/sword.png'); await tex.load(); context.clear(); @@ -139,7 +135,7 @@ describe('A Material', () => { context.restore(); expect(context.material).toBe(null); - await expectAsync(canvas).toEqualImage('src/spec/images/MaterialRendererSpec/multiply-comp.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/MaterialRendererSpec/multiply-comp.png'); context.dispose(); }); @@ -172,7 +168,7 @@ describe('A Material', () => { }` }); - const tex = new ex.ImageSource('src/spec/images/MaterialRendererSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/MaterialRendererSpec/sword.png'); await tex.load(); context.clear(); @@ -186,7 +182,7 @@ describe('A Material', () => { context.restore(); expect(context.material).toBe(null); - await expectAsync(canvas).toEqualImage('src/spec/images/MaterialRendererSpec/update-uniform.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/MaterialRendererSpec/update-uniform.png'); }); it('can be created with a custom fragment shader with the graphics component', async () => { @@ -218,7 +214,7 @@ describe('A Material', () => { }` }); - const tex = new ex.ImageSource('src/spec/images/MaterialRendererSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/MaterialRendererSpec/sword.png'); const loader = new ex.Loader([tex]); @@ -239,7 +235,7 @@ describe('A Material', () => { graphicsContext.flush(); expect(graphicsContext.material).toBe(null); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/MaterialRendererSpec/material-component.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/MaterialRendererSpec/material-component.png'); engine.dispose(); }); @@ -277,7 +273,7 @@ describe('A Material', () => { }` }); - const tex = new ex.ImageSource('src/spec/images/MaterialRendererSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/MaterialRendererSpec/sword.png'); const loader = new ex.Loader([tex]); @@ -308,7 +304,7 @@ describe('A Material', () => { graphicsContext.flush(); expect(graphicsContext.material).toBe(null); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/MaterialRendererSpec/multi-mat.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/MaterialRendererSpec/multi-mat.png'); engine.dispose(); }); @@ -324,7 +320,7 @@ describe('A Material', () => { snapToPixel: true }); - const stars = new ex.ImageSource('src/spec/images/MaterialRendererSpec/stars.png'); + const stars = new ex.ImageSource('/src/spec/assets/images/MaterialRendererSpec/stars.png'); await stars.load(); const material = new ex.Material({ @@ -351,7 +347,7 @@ describe('A Material', () => { } }); - const tex = new ex.ImageSource('src/spec/images/MaterialRendererSpec/sword.png'); + const tex = new ex.ImageSource('/src/spec/assets/images/MaterialRendererSpec/sword.png'); await tex.load(); graphicsContext.clear(); @@ -362,12 +358,12 @@ describe('A Material', () => { graphicsContext.restore(); expect(graphicsContext.material).toBe(null); - await expectAsync(canvas).toEqualImage('src/spec/images/MaterialRendererSpec/additional.png'); + await expect(canvas).toEqualImage('/src/spec/assets/images/MaterialRendererSpec/additional.png'); }); it('will log a warning if you exceed you texture slots', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); const canvas = document.createElement('canvas'); canvas.width = 100; @@ -379,7 +375,7 @@ describe('A Material', () => { snapToPixel: true }); - const stars = new ex.ImageSource('src/spec/images/MaterialRendererSpec/stars.png'); + const stars = new ex.ImageSource('/src/spec/assets/images/MaterialRendererSpec/stars.png'); const material = new ex.Material({ name: 'test', @@ -439,7 +435,10 @@ describe('A Material', () => { expect(material).toBeDefined(); expect(logger.warn).toHaveBeenCalledWith( - 'Max number texture slots 31 have been reached for material "test", no more textures will be uploaded due to hardware constraints.' + expect.stringMatching( + // this was 31 before, but since moving to vite it's 15. Is there a difference in max texture slots from chromium vs old karma browser? + /Max number texture slots (\d+) have been reached for material "test", no more textures will be uploaded due to hardware constraints\./ + ) ); }); }); diff --git a/src/spec/MathSpec.ts b/src/spec/vitest/MathSpec.ts similarity index 100% rename from src/spec/MathSpec.ts rename to src/spec/vitest/MathSpec.ts diff --git a/src/spec/MatrixSpec.ts b/src/spec/vitest/MatrixSpec.ts similarity index 65% rename from src/spec/MatrixSpec.ts rename to src/spec/vitest/MatrixSpec.ts index 36493595..e6822a0b 100644 --- a/src/spec/MatrixSpec.ts +++ b/src/spec/vitest/MatrixSpec.ts @@ -1,11 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A Matrix', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); - it('exists', () => { expect(ex.Matrix).toBeDefined(); }); @@ -17,7 +12,7 @@ describe('A Matrix', () => { it('can make an identity matrix', () => { const identity = ex.Matrix.identity(); - expect(identity.isIdentity()).toBeTrue(); + expect(identity.isIdentity()).toBe(true); }); it('can make a translation matrix', () => { @@ -75,79 +70,79 @@ describe('A Matrix', () => { it('can set scale with rotation in the mix', () => { const mat = ex.Matrix.identity(); mat.setScale(ex.vec(-1, -1)); - expect(mat.getScaleX()).toBe(-1, 'getScaleX()'); - expect(mat.getScaleY()).toBe(-1, 'getScaleY()'); + expect(mat.getScaleX(), 'getScaleX()').toBe(-1); + expect(mat.getScaleY(), 'getScaleY()').toBe(-1); mat.setScale(ex.vec(-2, -5)); - expect(mat.getScaleX()).toBe(-2, 'getScaleX()'); - expect(mat.getScaleY()).toBe(-5, 'getScaleY()'); + expect(mat.getScaleX(), 'getScaleX()').toBe(-2); + expect(mat.getScaleY(), 'getScaleY()').toBe(-5); mat.setScale(ex.vec(5, 11)); - expect(mat.getScaleX()).toBe(5, 'getScaleX()'); - expect(mat.getScaleY()).toBe(11, 'getScaleY()'); + expect(mat.getScaleX(), 'getScaleX()').toBe(5); + expect(mat.getScaleY(), 'getScaleY()').toBe(11); expect(mat.data[0]).toBe(5); expect(mat.data[5]).toBe(11); mat.setScale(ex.vec(1, -1)); - expect(mat.getScaleX()).toBe(1, 'getScaleX()'); - expect(mat.getScaleY()).toBe(-1, 'getScaleY()'); + expect(mat.getScaleX(), 'getScaleX()').toBe(1); + expect(mat.getScaleY(), 'getScaleY()').toBe(-1); mat.setRotation(Math.PI / 3); - expect(mat.getScaleX()).toBeCloseTo(1, 2, 'rotated PI/3 getScaleX()'); - expect(mat.getScaleY()).toBeCloseTo(-1, 2, 'rotated PI/3 getScaleY()'); - expect(mat.getRotation()).toBeCloseTo(Math.PI / 3, 2, 'rotated PI/3 getRotation()'); + expect(mat.getScaleX(), 'rotated PI/3 getScaleX()').toBeCloseTo(1, 2); + expect(mat.getScaleY(), 'rotated PI/3 getScaleY()').toBeCloseTo(-1, 2); + expect(mat.getRotation(), 'rotated PI/3 getRotation()').toBeCloseTo(Math.PI / 3, 2); mat.setRotation(Math.PI); - expect(mat.getScaleX()).toBeCloseTo(1, 2, 'rotated PI getScaleX()'); - expect(mat.getScaleY()).toBeCloseTo(-1, 2, 'rotated PI getScaleY()'); - expect(mat.getRotation()).toBeCloseTo(Math.PI, 2, 'rotated PI getRotation()'); + expect(mat.getScaleX(), 'rotated PI getScaleX()').toBeCloseTo(1, 2); + expect(mat.getScaleY(), 'rotated PI getScaleY()').toBeCloseTo(-1, 2); + expect(mat.getRotation(), 'rotated PI getRotation()').toBeCloseTo(Math.PI, 2); mat.setRotation(Math.PI * 2); - expect(mat.getScaleX()).toBeCloseTo(1, 2, 'rotated 2 PI getScaleX()'); - expect(mat.getScaleY()).toBeCloseTo(-1, 2, 'rotated 2 PI getScaleY()'); - expect(mat.getRotation()).toBeCloseTo(Math.PI * 2, 2, 'rotated 2 PI getRotation()'); + expect(mat.getScaleX(), 'rotated 2 PI getScaleX()').toBeCloseTo(1, 2); + expect(mat.getScaleY(), 'rotated 2 PI getScaleY()').toBeCloseTo(-1, 2); + expect(mat.getRotation(), 'rotated 2 PI getRotation()').toBeCloseTo(Math.PI * 2, 2); mat.setRotation(Math.PI * 3); - expect(mat.getScaleX()).toBeCloseTo(1, 2, 'rotated 3 PI getScaleX()'); - expect(mat.getScaleY()).toBeCloseTo(-1, 2, 'rotated 3 PI getScaleY()'); - expect(mat.getRotation()).toBeCloseTo(Math.PI, 2, 'rotated 3 * PI getRotation()'); + expect(mat.getScaleX(), 'rotated 3 PI getScaleX()').toBeCloseTo(1, 2); + expect(mat.getScaleY(), 'rotated 3 PI getScaleY()').toBeCloseTo(-1, 2); + expect(mat.getRotation(), 'rotated 3 * PI getRotation()').toBeCloseTo(Math.PI, 2); }); it('can set the rotation', () => { const mat = ex.Matrix.identity(); mat.setRotation(0); - expect(mat.getRotation()).toBeCloseTo(0, 2, 'rotation 0'); + expect(mat.getRotation(), 'rotation 0').toBeCloseTo(0, 2); mat.setRotation(Math.PI / 3); - expect(mat.getRotation()).toBeCloseTo(Math.PI / 3, 2, 'rotation PI/3'); + expect(mat.getRotation(), 'rotation PI/3').toBeCloseTo(Math.PI / 3, 2); mat.setRotation(Math.PI); - expect(mat.getRotation()).toBeCloseTo(Math.PI, 2, 'rotation PI'); + expect(mat.getRotation(), 'rotation PI').toBeCloseTo(Math.PI, 2); mat.setRotation(Math.PI * 2); - expect(mat.getRotation()).toBeCloseTo(Math.PI * 2, 2, 'rotation 2 PI'); + expect(mat.getRotation(), 'rotation 2 PI').toBeCloseTo(Math.PI * 2, 2); mat.setRotation(Math.PI * 3); - expect(mat.getRotation()).toBeCloseTo(Math.PI, 2, 'roation 3 PI'); + expect(mat.getRotation(), 'roation 3 PI').toBeCloseTo(Math.PI, 2); }); it('can find the affine inverse', () => { const mat = ex.Matrix.identity().translate(100, -200).scale(2, 4); const inv = mat.getAffineInverse(); - expect(mat.multiply(inv).isIdentity()).toBeTrue(); - expect(inv.multiply(mat).isIdentity()).toBeTrue(); + expect(mat.multiply(inv).isIdentity()).toBe(true); + expect(inv.multiply(mat).isIdentity()).toBe(true); }); it('can find the affine inverse and store it into a target', () => { const target = ex.Matrix.identity(); const mat = ex.Matrix.identity().translate(100, -200).scale(2, 4); - spyOn(ex.Matrix, 'identity'); + vi.spyOn(ex.Matrix, 'identity'); const inv = mat.getAffineInverse(target); - expect(mat.multiply(inv).isIdentity()).toBeTrue(); - expect(inv.multiply(mat).isIdentity()).toBeTrue(); + expect(mat.multiply(inv).isIdentity()).toBe(true); + expect(inv.multiply(mat).isIdentity()).toBe(true); expect(target).toBe(inv); - expect(ex.Matrix.identity).withContext('using a target doesnt create a new mat').not.toHaveBeenCalledWith(); + expect(ex.Matrix.identity, 'using a target doesnt create a new mat').not.toHaveBeenCalledWith(); }); it('can be created from a float32array', () => { diff --git a/src/spec/MotionComponentSpec.ts b/src/spec/vitest/MotionComponentSpec.ts similarity index 89% rename from src/spec/MotionComponentSpec.ts rename to src/spec/vitest/MotionComponentSpec.ts index 8e9c322a..ad14da44 100644 --- a/src/spec/MotionComponentSpec.ts +++ b/src/spec/vitest/MotionComponentSpec.ts @@ -1,11 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A Motion Component', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); - it('can be cloned', () => { const motion = new ex.MotionComponent(); const owner = new ex.Entity([motion]); diff --git a/src/spec/NineSliceSpec.ts b/src/spec/vitest/NineSliceSpec.ts similarity index 86% rename from src/spec/NineSliceSpec.ts rename to src/spec/vitest/NineSliceSpec.ts index 13053b7d..324940b4 100644 --- a/src/spec/NineSliceSpec.ts +++ b/src/spec/vitest/NineSliceSpec.ts @@ -1,7 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; -const inputTile = new ex.ImageSource('src/spec/images/GraphicsNineSliceSpec/InputTile.png'); +const inputTile = new ex.ImageSource('/src/spec/assets/images/GraphicsNineSliceSpec/InputTile.png'); describe('A NineSlice', () => { let canvasElement: HTMLCanvasElement; @@ -108,8 +107,6 @@ describe('A NineSlice', () => { }; }); beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); canvasElement = document.createElement('canvas'); canvasElement.width = 64; canvasElement.height = 64; @@ -172,7 +169,7 @@ describe('A NineSlice', () => { ctx.clear(); const sut = new ex.NineSlice(testGraphicConfigSmall); sut.draw(ctx, 0, 0); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsNineSliceSpec/InputTile.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsNineSliceSpec/InputTile.png'); }); it('can draw a tiled copy of input tile', async () => { @@ -181,7 +178,7 @@ describe('A NineSlice', () => { ctx.clear(); const sut = new ex.NineSlice(testGraphicConfigTile); sut.draw(ctx, 0, 0); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_tile_h_tile.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_tile_h_tile.png'); }); it('can draw a fitted tile copy of input tile', async () => { @@ -190,7 +187,7 @@ describe('A NineSlice', () => { ctx.clear(); const sut = new ex.NineSlice(testGraphicConfigTileFit); sut.draw(ctx, 0, 0); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_tilefit_h_tilefit.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_tilefit_h_tilefit.png'); }); it('can draw a stretched copy of input tile', async () => { @@ -199,7 +196,7 @@ describe('A NineSlice', () => { ctx.clear(); const sut = new ex.NineSlice(testGraphicConfigStretch); sut.draw(ctx, 0, 0); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsNineSliceSpec/resultImage_128_128_v_stretch_h_stretch.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_128_128_v_stretch_h_stretch.png'); }); it('can draw the frame of a tile with no center', async () => { @@ -208,6 +205,6 @@ describe('A NineSlice', () => { ctx.clear(); const sut = new ex.NineSlice(testGraphicConfigNoCenter); sut.draw(ctx, 0, 0); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsNineSliceSpec/resultImage_64_64_noCenter.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsNineSliceSpec/resultImage_64_64_noCenter.png'); }); }); diff --git a/src/spec/OffscreenSystemSpec.ts b/src/spec/vitest/OffscreenSystemSpec.ts similarity index 82% rename from src/spec/OffscreenSystemSpec.ts rename to src/spec/vitest/OffscreenSystemSpec.ts index 57bbd3df..34226b50 100644 --- a/src/spec/OffscreenSystemSpec.ts +++ b/src/spec/vitest/OffscreenSystemSpec.ts @@ -1,15 +1,12 @@ import * as ex from '@excalibur'; import { GraphicsComponent, TransformComponent } from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; + import { TestUtils } from './util/TestUtils'; describe('The OffscreenSystem', () => { let entities: ex.Entity[]; let engine: ex.Engine; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - engine = TestUtils.engine({ width: 100, height: 100 }); entities = [ new ex.Entity().addComponent(new ex.TransformComponent()).addComponent(new ex.GraphicsComponent()), @@ -49,8 +46,8 @@ describe('The OffscreenSystem', () => { offscreen.get(GraphicsComponent).use(rect); offscreen.get(TransformComponent).pos = ex.vec(112.5, 112.5); - const offscreenSpy = jasmine.createSpy('offscreenSpy'); - const onscreenSpy = jasmine.createSpy('onscreenSpy'); + const offscreenSpy = vi.fn(); + const onscreenSpy = vi.fn(); offscreen.events.on('enterviewport', onscreenSpy); offscreen.events.on('exitviewport', offscreenSpy); @@ -60,9 +57,9 @@ describe('The OffscreenSystem', () => { sut.update(); expect(offscreenSpy).toHaveBeenCalled(); expect(onscreenSpy).not.toHaveBeenCalled(); - expect(offscreen.hasTag('ex.offscreen')).toBeTrue(); - offscreenSpy.calls.reset(); - onscreenSpy.calls.reset(); + expect(offscreen.hasTag('ex.offscreen')).toBe(true); + offscreenSpy.mockReset(); + onscreenSpy.mockReset(); // Should be onscreen offscreen.get(TransformComponent).pos = ex.vec(80, 80); @@ -70,6 +67,6 @@ describe('The OffscreenSystem', () => { offscreen.processComponentRemoval(); expect(offscreenSpy).not.toHaveBeenCalled(); expect(onscreenSpy).toHaveBeenCalled(); - expect(offscreen.hasTag('ex.offscreen')).toBeFalse(); + expect(offscreen.hasTag('ex.offscreen')).toBe(false); }); }); diff --git a/src/spec/PairSpec.ts b/src/spec/vitest/PairSpec.ts similarity index 100% rename from src/spec/PairSpec.ts rename to src/spec/vitest/PairSpec.ts diff --git a/src/spec/ParallaxSpec.ts b/src/spec/vitest/ParallaxSpec.ts similarity index 77% rename from src/spec/ParallaxSpec.ts rename to src/spec/vitest/ParallaxSpec.ts index f4417118..5d089067 100644 --- a/src/spec/ParallaxSpec.ts +++ b/src/spec/vitest/ParallaxSpec.ts @@ -1,12 +1,8 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; + import { TestUtils } from './util/TestUtils'; describe('A Parallax Component', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); it('exists', () => { expect(ex.ParallaxComponent).toBeDefined(); }); @@ -37,21 +33,21 @@ describe('A Parallax Component', () => { expect(game.currentScene.camera.pos).toBeVector(ex.vec(100, 100)); clock.step(16); - await expectAsync(game.canvas).toEqualImage('src/spec/images/ParallaxSpec/parallax1.png'); - expect(actor.hasTag('ex.offscreen')).toBeFalse(); + await expect(game.canvas).toEqualImage('/src/spec/assets/images/ParallaxSpec/parallax1.png'); + expect(actor.hasTag('ex.offscreen')).toBe(false); game.currentScene.camera.pos = ex.vec(520, 520); game.currentScene.camera.drawPos = ex.vec(520, 520); clock.step(); expect(game.currentScene.camera.pos).toBeVector(ex.vec(520, 520)); - await expectAsync(game.canvas).toEqualImage('src/spec/images/ParallaxSpec/parallax2.png'); - expect(actor.hasTag('ex.offscreen')).toBeFalse(); + await expect(game.canvas).toEqualImage('/src/spec/assets/images/ParallaxSpec/parallax2.png'); + expect(actor.hasTag('ex.offscreen')).toBe(false); game.currentScene.camera.pos = ex.vec(620, 620); game.currentScene.camera.drawPos = ex.vec(620, 620); clock.step(); expect(game.currentScene.camera.pos).toBeVector(ex.vec(620, 620)); - expect(actor.hasTag('ex.offscreen')).toBeTrue(); + expect(actor.hasTag('ex.offscreen')).toBe(true); game.dispose(); }); @@ -82,14 +78,14 @@ describe('A Parallax Component', () => { clock.step(16); - await expectAsync(game.canvas).toEqualImage('src/spec/images/ParallaxSpec/tilemap.png'); + await expect(game.canvas).toEqualImage('/src/spec/assets/images/ParallaxSpec/tilemap.png'); game.currentScene.camera.pos = ex.vec(250, -480); clock.step(16); // seems like there is an out of phase issue clock.step(16); - await expectAsync(game.canvas).toEqualImage('src/spec/images/ParallaxSpec/tilemap2.png'); + await expect(game.canvas).toEqualImage('/src/spec/assets/images/ParallaxSpec/tilemap2.png'); game.dispose(); }); }); diff --git a/src/spec/ParticleSpec.ts b/src/spec/vitest/ParticleSpec.ts similarity index 94% rename from src/spec/ParticleSpec.ts rename to src/spec/vitest/ParticleSpec.ts index 8d594c96..5147ca4a 100644 --- a/src/spec/ParticleSpec.ts +++ b/src/spec/vitest/ParticleSpec.ts @@ -1,4 +1,3 @@ -import { ExcaliburMatchers, ExcaliburAsyncMatchers } from 'excalibur-jasmine'; import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; @@ -6,8 +5,6 @@ describe('A particle', () => { let engine: ex.Engine; let scene: ex.Scene; beforeEach(async () => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); engine = TestUtils.engine( { width: 800, @@ -128,7 +125,7 @@ describe('A particle', () => { engine.currentScene.update(engine, 100); engine.currentScene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/ParticleSpec/Particles.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/ParticleSpec/Particles.png'); }); it('should clear particles', async () => { @@ -171,7 +168,7 @@ describe('A particle', () => { engine.currentScene.update(engine, 100); engine.currentScene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/ParticleSpec/clear.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/ParticleSpec/clear.png'); }); it('can be parented', async () => { @@ -221,7 +218,7 @@ describe('A particle', () => { engine.currentScene.update(engine, 100); engine.currentScene.draw(engine.graphicsContext, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/ParticleSpec/parented.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/ParticleSpec/parented.png'); }); it('can set the particle transform to local making particles children of the emitter', () => { diff --git a/src/spec/PhysicsWorldSpec.ts b/src/spec/vitest/PhysicsWorldSpec.ts similarity index 100% rename from src/spec/PhysicsWorldSpec.ts rename to src/spec/vitest/PhysicsWorldSpec.ts diff --git a/src/spec/PointerInputSpec.ts b/src/spec/vitest/PointerInputSpec.ts similarity index 90% rename from src/spec/PointerInputSpec.ts rename to src/spec/vitest/PointerInputSpec.ts index f830005a..0deceaa3 100644 --- a/src/spec/PointerInputSpec.ts +++ b/src/spec/vitest/PointerInputSpec.ts @@ -64,9 +64,9 @@ describe('A pointer', () => { // process pointer events engine.currentScene.update(engine, 0); - expect(eventLeftFired).toBe(true, 'left should fire'); - expect(eventRightFired).toBe(true, 'right should fire'); - expect(eventMiddleFired).toBe(true, 'middle should fire'); + expect(eventLeftFired, 'left should fire').toBe(true); + expect(eventRightFired, 'right should fire').toBe(true); + expect(eventMiddleFired, 'middle should fire').toBe(true); }); it('should fire pointerup events', () => { @@ -92,9 +92,9 @@ describe('A pointer', () => { // process pointer events engine.currentScene.update(engine, 0); - expect(eventLeftFired).toBeTruthy('left should fire'); - expect(eventRightFired).toBeTruthy('right should fire'); - expect(eventMiddleFired).toBeTruthy('middle should fire'); + expect(eventLeftFired, 'left should fire').toBeTruthy(); + expect(eventRightFired, 'right should fire').toBeTruthy(); + expect(eventMiddleFired, 'middle should fire').toBeTruthy(); }); it('should fire pointermove events', () => { @@ -173,38 +173,38 @@ describe('A pointer', () => { it('should not dispatch canceled events to the top level', () => { const actor1 = new ex.Actor({ x: 50, y: 50, width: 100, height: 100 }); - const spyActorDown = jasmine.createSpy('actorDown'); + const spyActorDown = vi.fn(); actor1.on('pointerdown', (e) => { spyActorDown(); e.cancel(); }); - const spyActorUp = jasmine.createSpy('actorUp'); + const spyActorUp = vi.fn(); actor1.on('pointerup', (e) => { spyActorUp(); e.cancel(); }); - const spyActorMove = jasmine.createSpy('actorMove'); + const spyActorMove = vi.fn(); actor1.on('pointermove', (e) => { spyActorMove(); e.cancel(); }); - const spyActorWheel = jasmine.createSpy('actorWheel'); + const spyActorWheel = vi.fn(); actor1.on('pointerwheel', (e) => { spyActorWheel(); e.cancel(); }); engine.add(actor1); - const spyTopLevelPointerDown = jasmine.createSpy('pointerdown'); + const spyTopLevelPointerDown = vi.fn(); engine.input.pointers.primary.on('down', spyTopLevelPointerDown); engine.input.pointers.on('down', spyTopLevelPointerDown); - const spyTopLevelPointerUp = jasmine.createSpy('pointerup'); + const spyTopLevelPointerUp = vi.fn(); engine.input.pointers.primary.on('up', spyTopLevelPointerUp); engine.input.pointers.on('up', spyTopLevelPointerUp); - const spyTopLevelPointerMove = jasmine.createSpy('pointermove'); + const spyTopLevelPointerMove = vi.fn(); engine.input.pointers.primary.on('move', spyTopLevelPointerMove); engine.input.pointers.on('move', spyTopLevelPointerMove); - const spyTopLevelPointerWheel = jasmine.createSpy('pointerwheel'); + const spyTopLevelPointerWheel = vi.fn(); engine.input.pointers.primary.on('wheel', spyTopLevelPointerWheel); engine.input.pointers.on('wheel', spyTopLevelPointerWheel); @@ -253,7 +253,7 @@ describe('A pointer', () => { }); it('should dispatch point events on screen elements', () => { - const pointerDownSpy = jasmine.createSpy('pointerdown'); + const pointerDownSpy = vi.fn(); const screenElement = new ex.ScreenElement({ x: 50, y: 50, @@ -275,7 +275,7 @@ describe('A pointer', () => { expect(pointerDownSpy).toHaveBeenCalledTimes(5); - pointerDownSpy.calls.reset(); + pointerDownSpy.mockReset(); executeMouseEvent('pointerdown', document, null, 49, 49); executeMouseEvent('pointerdown', document, null, 49, 151); @@ -326,7 +326,7 @@ describe('A pointer', () => { }); it('can click on screen locked actors', () => { - const clickSpy = jasmine.createSpy('down'); + const clickSpy = vi.fn(); const actor1 = new ex.Actor({ pos: ex.vec(50, 50), width: 100, @@ -348,7 +348,7 @@ describe('A pointer', () => { describe('at the engine level', () => { it('should fire pointer up events', () => { - const upHandler = jasmine.createSpy('upHandler'); + const upHandler = vi.fn(); engine.input.pointers.on('up', upHandler); executeMouseEvent('pointerup', document, null, 50, 50); @@ -360,7 +360,7 @@ describe('A pointer', () => { }); it('should fire pointer down events', () => { - const downHandler = jasmine.createSpy('downHandler'); + const downHandler = vi.fn(); engine.input.pointers.on('down', downHandler); executeMouseEvent('pointerdown', document, null, 50, 50); @@ -372,7 +372,7 @@ describe('A pointer', () => { }); it('should fire pointer move events', () => { - const moveHandler = jasmine.createSpy('moveHandler'); + const moveHandler = vi.fn(); engine.input.pointers.on('move', moveHandler); executeMouseEvent('pointermove', document, null, 50, 50); @@ -384,7 +384,7 @@ describe('A pointer', () => { }); it('should fire wheel events', () => { - const wheelHandler = jasmine.createSpy('wheelHandler'); + const wheelHandler = vi.fn(); engine.input.pointers.on('wheel', wheelHandler); executeMouseEvent('wheel', document, null, 50, 50); diff --git a/src/spec/PolygonSpec.ts b/src/spec/vitest/PolygonSpec.ts similarity index 85% rename from src/spec/PolygonSpec.ts rename to src/spec/vitest/PolygonSpec.ts index 919f3aca..e0762391 100644 --- a/src/spec/PolygonSpec.ts +++ b/src/spec/vitest/PolygonSpec.ts @@ -1,13 +1,9 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; describe('A Polygon Graphic', () => { let canvasElement: HTMLCanvasElement; let ctx: ex.ExcaliburGraphicsContext; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - canvasElement = document.createElement('canvas'); canvasElement.width = 100; canvasElement.height = 100; @@ -57,6 +53,6 @@ describe('A Polygon Graphic', () => { poly.draw(ctx, 0, 0); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsPolygonSpec/poly.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsPolygonSpec/poly.png', 0.993); }); }); diff --git a/src/spec/PoolSpec.ts b/src/spec/vitest/PoolSpec.ts similarity index 91% rename from src/spec/PoolSpec.ts rename to src/spec/vitest/PoolSpec.ts index 3f7d3bb5..02ac4f11 100644 --- a/src/spec/PoolSpec.ts +++ b/src/spec/vitest/PoolSpec.ts @@ -29,7 +29,7 @@ describe('An object Pool', () => { 10 ); const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); for (let i = 0; i < 10; i++) { const instance = pool.get(); } @@ -37,11 +37,11 @@ describe('An object Pool', () => { expect(pool.totalAllocations).toBe(10); expect(logger.warn).not.toHaveBeenCalled(); pool.get(); - expect(logger.warn).toHaveBeenCalledOnceWith('Max pooled objects reached, possible memory leak? Doubling'); + expect(logger.warn).toHaveBeenCalledExactlyOnceWith('Max pooled objects reached, possible memory leak? Doubling'); }); it('can get instances and return them to get recycled', () => { - const recycler = jasmine.createSpy().and.callFake((m) => m.dispose()); + const recycler = vi.fn((m) => m.dispose()); const pool = new ex.Pool(() => new MockPoolable(), recycler, 10); const intances: MockPoolable[] = []; for (let i = 0; i < 10; i++) { @@ -54,7 +54,7 @@ describe('An object Pool', () => { expect(pool.index).toBe(0); for (let i = 0; i < 10; i++) { const instance = pool.get(); - expect(instance.recycled).toBeTrue(); + expect(instance.recycled).toBe(true); } expect(recycler).toHaveBeenCalledTimes(10); diff --git a/src/spec/PostProcessorSpec.ts b/src/spec/vitest/PostProcessorSpec.ts similarity index 80% rename from src/spec/PostProcessorSpec.ts rename to src/spec/vitest/PostProcessorSpec.ts index 780a1149..10abcc13 100644 --- a/src/spec/PostProcessorSpec.ts +++ b/src/spec/vitest/PostProcessorSpec.ts @@ -26,7 +26,7 @@ class MockPostProcessor implements ex.PostProcessor { getLayout(): ex.VertexLayout { return this._shader.getLayout(); } - onUpdate = jasmine.createSpy('update'); + onUpdate = vi.fn(); } describe('A PostProcessor', () => { @@ -62,16 +62,16 @@ describe('A PostProcessor', () => { const shader = mock.getShader(); - const setUniformFloatCalls = spyOn(shader, 'setUniformFloat'); - const setUniformFloatVectorCalls = spyOn(shader, 'setUniformFloatVector'); + const setUniformFloatCalls = vi.spyOn(shader, 'setUniformFloat'); + const setUniformFloatVectorCalls = vi.spyOn(shader, 'setUniformFloatVector'); context.updatePostProcessors(10); expect(shader.setUniformFloat).toHaveBeenCalledTimes(2); expect(shader.setUniformFloatVector).toHaveBeenCalledTimes(1); - expect(setUniformFloatCalls.calls.argsFor(0)).toEqual(['u_time_ms', 10]); - expect(setUniformFloatCalls.calls.argsFor(1)).toEqual(['u_elapsed_ms', 10]); - expect(setUniformFloatVectorCalls.calls.argsFor(0)).toEqual(['u_resolution', ex.vec(100, 100)]); + expect(setUniformFloatCalls.mock.calls[0]).toEqual(['u_time_ms', 10]); + expect(setUniformFloatCalls.mock.calls[1]).toEqual(['u_elapsed_ms', 10]); + expect(setUniformFloatVectorCalls.mock.calls[0]).toEqual(['u_resolution', ex.vec(100, 100)]); }); }); diff --git a/src/spec/QuadIndexBufferSpec.ts b/src/spec/vitest/QuadIndexBufferSpec.ts similarity index 77% rename from src/spec/QuadIndexBufferSpec.ts rename to src/spec/vitest/QuadIndexBufferSpec.ts index 804c34d6..80c388d5 100644 --- a/src/spec/QuadIndexBufferSpec.ts +++ b/src/spec/vitest/QuadIndexBufferSpec.ts @@ -1,11 +1,7 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A QuadIndexBuffer', () => { let gl: WebGL2RenderingContext; - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); beforeEach(() => { const canvas = document.createElement('canvas'); @@ -23,20 +19,20 @@ describe('A QuadIndexBuffer', () => { it('can be constructed', () => { const sut = new ex.QuadIndexBuffer(gl, 2); - expect(sut.bufferData.length).withContext('2 quads * 2 triangle * 3 verts').toBe(12); + expect(sut.bufferData.length, '2 quads * 2 triangle * 3 verts').toBe(12); expect(sut.bufferData).toEqual(new Uint32Array([0, 1, 2, 2, 1, 3, 4, 5, 6, 6, 5, 7])); }); it('can be constructed with uint16 buffer', () => { const sut = new ex.QuadIndexBuffer(gl, 2, true); - expect(sut.bufferData.length).withContext('2 quads * 2 triangle * 3 verts').toBe(12); + expect(sut.bufferData.length, '2 quads * 2 triangle * 3 verts').toBe(12); expect(sut.bufferData).toEqual(new Uint16Array([0, 1, 2, 2, 1, 3, 4, 5, 6, 6, 5, 7])); }); it('can upload data to the GPU', () => { const sut = new ex.QuadIndexBuffer(gl, 2, true); - spyOn(gl, 'bindBuffer').and.callThrough(); - spyOn(gl, 'bufferData').and.callThrough(); + vi.spyOn(gl, 'bindBuffer'); + vi.spyOn(gl, 'bufferData'); sut.upload(); expect(gl.bindBuffer).toHaveBeenCalledWith(gl.ELEMENT_ARRAY_BUFFER, sut.buffer); @@ -50,7 +46,7 @@ describe('A QuadIndexBuffer', () => { it('will warn if geometry is maxed out uint16', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn').and.callThrough(); + vi.spyOn(logger, 'warn'); const sut = new ex.QuadIndexBuffer(gl, 16384, true); expect(logger.warn).toHaveBeenCalledWith('Total quads exceeds hardware index buffer limit (uint16), max(16383) requested quads(16384)'); }); diff --git a/src/spec/QuadTreeSpec.ts b/src/spec/vitest/QuadTreeSpec.ts similarity index 98% rename from src/spec/QuadTreeSpec.ts rename to src/spec/vitest/QuadTreeSpec.ts index 63e01895..dfe3312a 100644 --- a/src/spec/QuadTreeSpec.ts +++ b/src/spec/vitest/QuadTreeSpec.ts @@ -1,5 +1,4 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A QuadTree', () => { it('exists', () => { diff --git a/src/spec/QueryManagerSpec.ts b/src/spec/vitest/QueryManagerSpec.ts similarity index 79% rename from src/spec/QueryManagerSpec.ts rename to src/spec/vitest/QueryManagerSpec.ts index 60277305..caf6fc19 100644 --- a/src/spec/QueryManagerSpec.ts +++ b/src/spec/vitest/QueryManagerSpec.ts @@ -31,22 +31,22 @@ describe('A QueryManager', () => { // Query for all entities that have type A & B components const queryAB = world.query([FakeComponentA, FakeComponentB]); - expect(queryA.getEntities()).toEqual([entity1, entity2], 'Both entities have component A'); - expect(queryAB.getEntities()).toEqual([entity1], 'Only entity1 has both A+B'); + expect(queryA.getEntities(), 'Both entities have component A').toEqual([entity1, entity2]); + expect(queryAB.getEntities(), 'Only entity1 has both A+B').toEqual([entity1]); // Queries update if component change entity2.addComponent(new FakeComponentB()); - expect(queryAB.getEntities()).toEqual([entity1, entity2], 'Now both entities have A+B'); + expect(queryAB.getEntities(), 'Now both entities have A+B').toEqual([entity1, entity2]); // Queries update if components change entity2.removeComponent(FakeComponentB, true); - expect(queryAB.getEntities()).toEqual([entity1], 'Component force removed from entity, only entity1 A+B'); + expect(queryAB.getEntities(), 'Component force removed from entity, only entity1 A+B').toEqual([entity1]); // Queries are deferred by default, so queries will update after removals entity1.removeComponent(FakeComponentB); - expect(queryAB.getEntities()).toEqual([entity1], 'Deferred removal, component is still part of entity1'); + expect(queryAB.getEntities(), 'Deferred removal, component is still part of entity1').toEqual([entity1]); entity1.processComponentRemoval(); - expect(queryAB.getEntities()).toEqual([], 'No entities should match'); + expect(queryAB.getEntities(), 'No entities should match').toEqual([]); }); it('can add entities to queries', () => { @@ -202,37 +202,39 @@ describe('A QueryManager', () => { expect(queryAB.getEntities()).toEqual([entity1, entity2]); }); - it('will be notified when entity components are added', (done) => { - const world = new ex.World(null); - const entity = new ex.Entity(); - world.add(entity); - - const componentA = new FakeComponentA(); - const query = world.query([FakeComponentA]); - query.entityAdded$.subscribe((e) => { - expect(e).toBe(entity); - expect(e.get(FakeComponentA)).toBe(componentA); - done(); - }); - - entity.addComponent(componentA); - }); - - it('will be notified when entity components are removed', (done) => { - const world = new ex.World(null); - const entity = new ex.Entity(); - world.add(entity); - const componentA = new FakeComponentA(); - entity.addComponent(componentA); - - const query = world.query([FakeComponentA]); - query.entityRemoved$.subscribe((e) => { - expect(e).toBe(entity); - expect(e.get(FakeComponentA)).toBe(componentA); - done(); - }); - - entity.removeComponent(FakeComponentA); - entity.processComponentRemoval(); - }); + it('will be notified when entity components are added', () => + new Promise((done) => { + const world = new ex.World(null); + const entity = new ex.Entity(); + world.add(entity); + + const componentA = new FakeComponentA(); + const query = world.query([FakeComponentA]); + query.entityAdded$.subscribe((e) => { + expect(e).toBe(entity); + expect(e.get(FakeComponentA)).toBe(componentA); + done(); + }); + + entity.addComponent(componentA); + })); + + it('will be notified when entity components are removed', () => + new Promise((done) => { + const world = new ex.World(null); + const entity = new ex.Entity(); + world.add(entity); + const componentA = new FakeComponentA(); + entity.addComponent(componentA); + + const query = world.query([FakeComponentA]); + query.entityRemoved$.subscribe((e) => { + expect(e).toBe(entity); + expect(e.get(FakeComponentA)).toBe(componentA); + done(); + }); + + entity.removeComponent(FakeComponentA); + entity.processComponentRemoval(); + })); }); diff --git a/src/spec/QuerySpec.ts b/src/spec/vitest/QuerySpec.ts similarity index 71% rename from src/spec/QuerySpec.ts rename to src/spec/vitest/QuerySpec.ts index fe2738ef..787357c3 100644 --- a/src/spec/QuerySpec.ts +++ b/src/spec/vitest/QuerySpec.ts @@ -71,36 +71,38 @@ describe('A query', () => { expect(queryAB.getEntities()).toEqual([]); }); - it('notifies observers of when something is added to the query', (done) => { - const queryAB = new ex.Query([FakeComponentA, FakeComponentB]); - const compA = new FakeComponentA(); - const compB = new FakeComponentB(); - const entity1 = new ex.Entity(); - entity1.addComponent(compA); - entity1.addComponent(compB); - - queryAB.entityAdded$.subscribe((e) => { - expect(e).toBe(entity1); - done(); - }); - - queryAB.checkAndAdd(entity1); - }); - - it('notifies observers of when something is added to the query', (done) => { - const queryAB = new ex.Query([FakeComponentA, FakeComponentB]); - const compA = new FakeComponentA(); - const compB = new FakeComponentB(); - const entity1 = new ex.Entity(); - entity1.addComponent(compA); - entity1.addComponent(compB); - queryAB.checkAndAdd(entity1); - - queryAB.entityRemoved$.subscribe((e) => { - expect(e).toBe(entity1); - done(); - }); - - queryAB.removeEntity(entity1); - }); + it('notifies observers of when something is added to the query', () => + new Promise((done) => { + const queryAB = new ex.Query([FakeComponentA, FakeComponentB]); + const compA = new FakeComponentA(); + const compB = new FakeComponentB(); + const entity1 = new ex.Entity(); + entity1.addComponent(compA); + entity1.addComponent(compB); + + queryAB.entityAdded$.subscribe((e) => { + expect(e).toBe(entity1); + done(); + }); + + queryAB.checkAndAdd(entity1); + })); + + it('notifies observers of when something is added to the query', () => + new Promise((done) => { + const queryAB = new ex.Query([FakeComponentA, FakeComponentB]); + const compA = new FakeComponentA(); + const compB = new FakeComponentB(); + const entity1 = new ex.Entity(); + entity1.addComponent(compA); + entity1.addComponent(compB); + queryAB.checkAndAdd(entity1); + + queryAB.entityRemoved$.subscribe((e) => { + expect(e).toBe(entity1); + done(); + }); + + queryAB.removeEntity(entity1); + })); }); diff --git a/src/spec/RandomSpec.ts b/src/spec/vitest/RandomSpec.ts similarity index 92% rename from src/spec/RandomSpec.ts rename to src/spec/vitest/RandomSpec.ts index 71378c0e..0ea0ac1e 100644 --- a/src/spec/RandomSpec.ts +++ b/src/spec/vitest/RandomSpec.ts @@ -60,7 +60,7 @@ describe('A random number', () => { for (let i = 0; i < 9000; i++) { const r = random1.next(); const inrange = 0 <= r && r < 1.0; - expect(inrange).toBe(true, `Random ${r} not in range [0, 1). Seed [${random1.seed}] Iteration [${i}]`); + expect(inrange, `Random ${r} not in range [0, 1). Seed [${random1.seed}] Iteration [${i}]`).toBe(true); } }); @@ -69,7 +69,7 @@ describe('A random number', () => { for (let i = 0; i < 9000; i++) { const r = random1.floating(-88, 1900); const inrange = -88 <= r && r < 1900; - expect(inrange).toBe(true, `Random ${r} not in range [-88, 1900). Seed [${random1.seed}] Iteration [${i}]`); + expect(inrange, `Random ${r} not in range [-88, 1900). Seed [${random1.seed}] Iteration [${i}]`).toBe(true); } }); @@ -78,7 +78,7 @@ describe('A random number', () => { for (let i = 0; i < 9000; i++) { const r = random1.integer(-10, 10); const inrange = -10 <= r && r <= 10; - expect(inrange).toBe(true, `Random ${r} not in range [-10, 10]. Seed [${random1.seed}] Iteration [${i}]`); + expect(inrange, `Random ${r} not in range [-10, 10]. Seed [${random1.seed}] Iteration [${i}]`).toBe(true); } }); @@ -96,7 +96,7 @@ describe('A random number', () => { } } const ratio = truthCount / falseCount; - expect(ratio).toBeCloseTo(1.0, 0.1, `Bool did not appear to be 50/50 Ratio true/false [${ratio}]`); + expect(ratio, `Bool did not appear to be 50/50 Ratio true/false [${ratio}]`).toBeCloseTo(1.0, 0.1); }); it('can pick an element out of an array', () => { @@ -135,7 +135,7 @@ describe('A random number', () => { expect(four).toBeGreaterThan(0); const ratio = one / two / (three / four); - expect(ratio).toBeCloseTo(1.0, 0.1, 'Should pick elements equally'); + expect(ratio, 'Should pick elements equally').toBeCloseTo(1.0, 0.1); }); it('can pick a subset of an array', () => { @@ -197,7 +197,7 @@ describe('A random number', () => { expect(countsSum).toEqual(numCounts); const ratio = counts.one.count / counts.two.count / (counts.three.count / counts.four.count); - expect(ratio).toBeCloseTo(1.0, 0.1, 'Should pick elements equally'); + expect(ratio, 'Should pick elements equally').toBeCloseTo(1.0, 0.1); }); it('can shuffle arrays', () => { @@ -227,7 +227,7 @@ describe('A random number', () => { return acc + curr; }, 0) / 1000; - expect(average).toBeCloseTo(expectedValue, 0.01, 'Should pick elements equally'); + expect(average, 'Should pick elements equally').toBeCloseTo(expectedValue, 0.01); }); it('can do d4 dice rolls', () => { diff --git a/src/spec/RasterSpec.ts b/src/spec/vitest/RasterSpec.ts similarity index 86% rename from src/spec/RasterSpec.ts rename to src/spec/vitest/RasterSpec.ts index b59acb26..52ef8ad5 100644 --- a/src/spec/RasterSpec.ts +++ b/src/spec/vitest/RasterSpec.ts @@ -1,7 +1,7 @@ import * as ex from '@excalibur'; import { Color } from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; -import { RasterOptions } from '../engine/Graphics'; + +import type { RasterOptions } from '../../engine/Graphics'; class TestRaster extends ex.Raster { constructor(options?: RasterOptions) { @@ -25,9 +25,6 @@ describe('A Raster', () => { let canvasElement: HTMLCanvasElement; let ctx: ex.ExcaliburGraphicsContext; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - canvasElement = document.createElement('canvas'); canvasElement.width = 100; canvasElement.height = 100; @@ -79,22 +76,22 @@ describe('A Raster', () => { const sut = new TestRaster(); sut.draw(ctx, 0, 0); - expect(sut.dirty).toBeFalse(); + expect(sut.dirty).toBe(false); sut.color = new ex.Color(125, 0, 0); sut.color.b = 125; expect(sut.color.r).toBe(125); expect(sut.color.b).toBe(125); - expect(sut.dirty).toBeTrue(); + expect(sut.dirty).toBe(true); sut.draw(ctx, 0, 0); - expect(sut.dirty).toBeFalse(); + expect(sut.dirty).toBe(false); sut.strokeColor = new ex.Color(1, 1, 1); sut.strokeColor.r = 12; - expect(sut.dirty).toBeTrue(); + expect(sut.dirty).toBe(true); }); it('can clone RasterOptions', () => { @@ -114,12 +111,12 @@ describe('A Raster', () => { it('can be drawn', async () => { const sut = new TestRaster(); - spyOn(sut, 'rasterize').and.callThrough(); - spyOn(sut, 'execute').and.callThrough(); + vi.spyOn(sut, 'rasterize'); + vi.spyOn(sut, 'execute'); sut.draw(ctx, 0, 0); expect(sut.execute).toHaveBeenCalledTimes(1); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsRasterSpec/raster.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsRasterSpec/raster.png'); }); it('knows when it must be re-rastered', () => { @@ -137,7 +134,7 @@ describe('A Raster', () => { }); sut.quality = 4; sut.draw(ctx, 25, 25); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsRasterSpec/raster-quality.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsRasterSpec/raster-quality.png'); }); it('can have padding and maintain correct size and not grow after each draw', () => { diff --git a/src/spec/RealisticSolverSpec.ts b/src/spec/vitest/RealisticSolverSpec.ts similarity index 84% rename from src/spec/RealisticSolverSpec.ts rename to src/spec/vitest/RealisticSolverSpec.ts index 872730c7..2a618645 100644 --- a/src/spec/RealisticSolverSpec.ts +++ b/src/spec/vitest/RealisticSolverSpec.ts @@ -1,12 +1,7 @@ -import { ExcaliburMatchers } from 'excalibur-jasmine'; import * as ex from '@excalibur'; -import { getDefaultPhysicsConfig } from '../engine/Collision/PhysicsConfig'; +import { getDefaultPhysicsConfig } from '../../engine/Collision/PhysicsConfig'; describe('A RealisticSolver', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); - it('should exist', () => { expect(ex.RealisticSolver).toBeDefined(); }); diff --git a/src/spec/RectangleSpec.ts b/src/spec/vitest/RectangleSpec.ts similarity index 77% rename from src/spec/RectangleSpec.ts rename to src/spec/vitest/RectangleSpec.ts index e7143730..479236cb 100644 --- a/src/spec/RectangleSpec.ts +++ b/src/spec/vitest/RectangleSpec.ts @@ -1,13 +1,9 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; describe('A Rectangle Graphic', () => { let canvasElement: HTMLCanvasElement; let ctx: ex.ExcaliburGraphicsContext; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - canvasElement = document.createElement('canvas'); canvasElement.width = 100; canvasElement.height = 100; @@ -35,7 +31,7 @@ describe('A Rectangle Graphic', () => { rect.draw(ctx, 25, 25); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsRectSpec/rect.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsRectSpec/rect.png'); }); it('can be cloned', async () => { @@ -58,6 +54,6 @@ describe('A Rectangle Graphic', () => { rect2.draw(ctx, 15, 25); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsRectSpec/clone-rect.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsRectSpec/clone-rect.png'); }); }); diff --git a/src/spec/vitest/ResourceSpec.ts b/src/spec/vitest/ResourceSpec.ts new file mode 100644 index 00000000..3a475c02 --- /dev/null +++ b/src/spec/vitest/ResourceSpec.ts @@ -0,0 +1,77 @@ +import * as ex from '@excalibur'; +import { TestUtils } from './util/TestUtils'; + +describe('A generic Resource', () => { + let resource: ex.Resource; + + beforeEach(() => { + // vitest falls back to the UI page on non-existent paths + // but doing ../ seems to properly trigger a not found error + resource = new ex.Resource('../a/path/to/a/resource.png', 'blob'); + + ex.Logger.getInstance().defaultLevel = ex.LogLevel.Error; + }); + + it('should not be loaded by default', () => { + expect(resource.isLoaded()).toBe(false); + }); + + it('should log failure when not found', () => + new Promise((done, fail) => { + const spy = vi.spyOn(ex.Logger.getInstance(), 'error').mockImplementation(() => void 0); + + resource.events.on('error', vi.fn()); + resource.load().then( + () => fail(), + () => { + try { + expect(spy).toHaveBeenCalled(); + done(); + } catch (e) { + fail(e); + } + } + ); + })); + + describe('without data', () => { + it('should not fail on load', async () => { + const emptyLoader = new ex.Loader(); + const game = TestUtils.engine(); + await game.start(); + expect(emptyLoader.isLoaded()).toBe(true); + game.dispose(); + }); + }); + + describe('with some data', () => { + beforeEach(() => { + resource.data = 'blob://data'; + }); + + it('should be loaded immediately', () => { + expect(resource.isLoaded()).toBe(true); + }); + + it('should return the processed data', () => { + expect(resource.data).toBe('blob://data'); + }); + + it('should not trigger an XHR when load is called', () => + new Promise((done) => { + resource.load().then((data) => { + expect(data).not.toBeNull(); + done(); + }); + })); + + it('should load a text resource', () => + new Promise((done) => { + const text = new ex.Resource('/src/spec/assets/images/ResourceSpec/textresource.txt', 'text', true); + text.load().then((data) => { + expect(data).not.toBeNull(); + done(); + }); + })); + }); +}); diff --git a/src/spec/vitest/ScaleSpec.ts b/src/spec/vitest/ScaleSpec.ts new file mode 100644 index 00000000..1ad68e36 --- /dev/null +++ b/src/spec/vitest/ScaleSpec.ts @@ -0,0 +1,54 @@ +import * as ex from '@excalibur'; +import { TestUtils } from './util/TestUtils'; +import { Mocks } from './util/Mocks'; + +describe('A scaled and rotated actor', () => { + let actor: ex.Actor; + let engine: ex.Engine; + const mock = new Mocks.Mocker(); + + beforeEach(() => { + actor = new ex.ScreenElement({ x: 50, y: 50, width: 100, height: 50 }); + actor.color = ex.Color.Blue; + actor.body.collisionType = ex.CollisionType.Active; + engine = TestUtils.engine({ width: 800, height: 600 }); + engine.screen.antialiasing = false; + + vi.spyOn(engine.rootScene, 'draw'); + }); + + afterEach(() => { + engine.stop(); + engine.dispose(); + }); + + it('is drawn correctly scaled at 90 degrees', () => + new Promise((done) => { + const clock = engine.clock as ex.TestClock; + const bg = new ex.ImageSource('/src/spec/assets/images/ScaleSpec/logo.png'); + const loader = new ex.Loader([bg]); + TestUtils.runToReady(engine, loader).then(() => { + const actor = new ex.Actor({ + x: engine.halfDrawWidth, + y: engine.halfDrawHeight, + width: 100, + height: 10, + color: ex.Color.Black + }); + actor.graphics.use(bg.toSprite()); + actor.scale.setTo(1, 0.2); + engine.add(actor); + + actor.rotation = Math.PI / 2; + + clock.step(1); + + expect(engine.canvas) + .toEqualImage('/src/spec/assets/images/ScaleSpec/scale.png') + .then(() => { + done(); + engine.dispose(); + }); + }); + })); +}); diff --git a/src/spec/SceneSpec.ts b/src/spec/vitest/SceneSpec.ts similarity index 74% rename from src/spec/SceneSpec.ts rename to src/spec/vitest/SceneSpec.ts index 59f7b17b..cd1421a7 100644 --- a/src/spec/SceneSpec.ts +++ b/src/spec/vitest/SceneSpec.ts @@ -12,7 +12,7 @@ describe('A scene', () => { engine = TestUtils.engine({ width: 100, height: 100 }); scene = new ex.Scene(); - spyOn(scene, 'draw').and.callThrough(); + vi.spyOn(scene, 'draw'); engine.addScene('newScene', scene); engine.goToScene('newScene'); await TestUtils.runToReady(engine); @@ -78,8 +78,8 @@ describe('A scene', () => { expect(scene.timers.length).toBe(1); scene.clear(); - expect(scene.entities.length).withContext('deferred entity removal means entities cleared at end of update').toBe(3); - expect(scene.timers.length).withContext("timers don't have deferred removal").toBe(0); + expect(scene.entities.length, 'deferred entity removal means entities cleared at end of update').toBe(3); + expect(scene.timers.length, "timers don't have deferred removal").toBe(0); scene.update(engine, 100); expect(scene.entities.length).toBe(0); @@ -101,7 +101,7 @@ describe('A scene', () => { height: 10, color: ex.Color.Red }); - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); actor.pos.x = 0; actor.pos.y = 0; @@ -121,7 +121,7 @@ describe('A scene', () => { height: 10, color: ex.Color.Red }); - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); actor.pos.x = -4; actor.pos.y = 0; @@ -129,7 +129,7 @@ describe('A scene', () => { scene.update(engine, 100); scene.draw(engine.graphicsContext, 100); - expect(actor.isOffScreen).withContext('Actor should be onscreen').toBe(false); + expect(actor.isOffScreen, 'Actor should be onscreen').toBe(false); expect(actor.graphics.onPostDraw).toHaveBeenCalled(); }); it('does not draw offscreen Actors left', () => { @@ -139,7 +139,7 @@ describe('A scene', () => { height: 10, color: ex.Color.Red }); - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); actor.pos.x = -6; actor.pos.y = 0; @@ -147,7 +147,7 @@ describe('A scene', () => { scene.update(engine, 100); scene.draw(engine.graphicsContext, 100); - expect(actor.isOffScreen).withContext('Actor should be offscreen').toBe(true); + expect(actor.isOffScreen, 'Actor should be offscreen').toBe(true); expect(actor.graphics.onPostDraw).not.toHaveBeenCalled(); }); @@ -158,7 +158,7 @@ describe('A scene', () => { height: 10, color: ex.Color.Red }); - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); actor.pos.x = 0; actor.pos.y = -4; @@ -166,7 +166,7 @@ describe('A scene', () => { scene.update(engine, 100); scene.draw(engine.graphicsContext, 100); - expect(actor.isOffScreen).withContext('Actor should be onscreen').toBe(false); + expect(actor.isOffScreen, 'Actor should be onscreen').toBe(false); expect(actor.graphics.onPostDraw).toHaveBeenCalled(); }); @@ -177,7 +177,7 @@ describe('A scene', () => { height: 10, color: ex.Color.Red }); - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); actor.pos.x = 0; actor.pos.y = -6; @@ -185,7 +185,7 @@ describe('A scene', () => { scene.update(engine, 100); scene.draw(engine.graphicsContext, 100); - expect(actor.isOffScreen).withContext('Actor should be offscreen').toBe(true); + expect(actor.isOffScreen, 'Actor should be offscreen').toBe(true); expect(actor.graphics.onPostDraw).not.toHaveBeenCalled(); }); @@ -196,7 +196,7 @@ describe('A scene', () => { height: 10, color: ex.Color.Red }); - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); actor.pos.x = 104; actor.pos.y = 0; @@ -204,7 +204,7 @@ describe('A scene', () => { scene.update(engine, 100); scene.draw(engine.graphicsContext, 100); - expect(actor.isOffScreen).withContext('Actor should be onscreen').toBe(false); + expect(actor.isOffScreen, 'Actor should be onscreen').toBe(false); expect(actor.graphics.onPostDraw).toHaveBeenCalled(); }); @@ -215,7 +215,7 @@ describe('A scene', () => { height: 10, color: ex.Color.Red }); - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); actor.pos.x = 106; actor.pos.y = 0; @@ -223,7 +223,7 @@ describe('A scene', () => { scene.update(engine, 100); scene.draw(engine.graphicsContext, 100); - expect(actor.isOffScreen).withContext('Actor should be offscreen').toBe(true); + expect(actor.isOffScreen, 'Actor should be offscreen').toBe(true); expect(actor.graphics.onPostDraw).not.toHaveBeenCalled(); }); @@ -234,7 +234,7 @@ describe('A scene', () => { height: 10, color: ex.Color.Red }); - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); actor.pos.x = 0; actor.pos.y = 104; @@ -242,7 +242,7 @@ describe('A scene', () => { scene.update(engine, 100); scene.draw(engine.graphicsContext, 100); - expect(actor.isOffScreen).withContext('Actor should be onscreen').toBe(false); + expect(actor.isOffScreen, 'Actor should be onscreen').toBe(false); expect(actor.graphics.onPostDraw).toHaveBeenCalled(); }); @@ -253,7 +253,7 @@ describe('A scene', () => { height: 10, color: ex.Color.Red }); - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); actor.pos.x = 0; actor.pos.y = 106; @@ -261,7 +261,7 @@ describe('A scene', () => { scene.update(engine, 100); scene.draw(engine.graphicsContext, 100); - expect(actor.isOffScreen).withContext('Actor should be offscreen').toBe(true); + expect(actor.isOffScreen, 'Actor should be offscreen').toBe(true); expect(actor.graphics.onPostDraw).not.toHaveBeenCalled(); }); @@ -296,7 +296,7 @@ describe('A scene', () => { it('draws visible Actors', () => { engine.goToScene('root'); actor.graphics.visible = true; - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); scene.add(actor); scene.draw(engine.graphicsContext, 100); @@ -307,7 +307,7 @@ describe('A scene', () => { it('does not draw invisible actors', () => { engine.goToScene('root'); actor.graphics.visible = false; - actor.graphics.onPostDraw = jasmine.createSpy('draw'); + actor.graphics.onPostDraw = vi.fn(); scene.add(actor); scene.draw(engine.graphicsContext, 100); @@ -317,7 +317,7 @@ describe('A scene', () => { it('initializes after start or play in first update', async () => { const scene = new ex.Scene(); - spyOn(scene, 'onInitialize'); + vi.spyOn(scene, 'onInitialize'); engine.addScene('otherScene', scene); expect(scene.onInitialize).toHaveBeenCalledTimes(0); @@ -329,9 +329,9 @@ describe('A scene', () => { it('calls onActivate and onDeactivate with the correct args', async () => { const sceneA = new ex.Scene(); - sceneA.onDeactivate = jasmine.createSpy('onDeactivate()'); + sceneA.onDeactivate = vi.fn(); const sceneB = new ex.Scene(); - sceneB.onActivate = jasmine.createSpy('onActivate()'); + sceneB.onActivate = vi.fn(); engine.addScene('sceneA', sceneA); engine.addScene('sceneB', sceneB); @@ -353,65 +353,67 @@ describe('A scene', () => { }); }); - it('fires initialize before activate', (done) => { - engine.stop(); - engine.dispose(); - engine = null; - engine = TestUtils.engine({ width: 100, height: 100 }); - const scene = new ex.Scene(); + it('fires initialize before activate', () => + new Promise((done) => { + engine.stop(); + engine.dispose(); + engine = null; + engine = TestUtils.engine({ width: 100, height: 100 }); + const scene = new ex.Scene(); - engine.removeScene('otherScene'); - engine.addScene('otherScene', scene); + engine.removeScene('otherScene'); + engine.addScene('otherScene', scene); - let initialized = false; - scene.once('initialize', (evt: ex.InitializeEvent) => { - initialized = true; - }); - scene.once('activate', (evt: ex.ActivateEvent) => { - expect(initialized).toBe(true, 'Initialization should happen before activation'); - done(); - }); + let initialized = false; + scene.once('initialize', (evt: ex.InitializeEvent) => { + initialized = true; + }); + scene.once('activate', (evt: ex.ActivateEvent) => { + expect(initialized, 'Initialization should happen before activation').toBe(true); + done(); + }); - engine.goToScene('otherScene'); - engine.start(); - const clock = engine.clock as ex.TestClock; - clock.step(100); - }); + engine.goToScene('otherScene'); + engine.start(); + const clock = engine.clock as ex.TestClock; + clock.step(100); + })); - xit('fires initialize before actor initialize before activate', (done) => { - engine.stop(); - engine.dispose(); - engine = null; - engine = TestUtils.engine({ width: 100, height: 100 }); - scene = new ex.Scene(); + it.skip('fires initialize before actor initialize before activate', () => + new Promise((done) => { + engine.stop(); + engine.dispose(); + engine = null; + engine = TestUtils.engine({ width: 100, height: 100 }); + scene = new ex.Scene(); - engine.removeScene('otherScene'); - engine.addScene('otherScene', scene); + engine.removeScene('otherScene'); + engine.addScene('otherScene', scene); - let sceneInitialized = false; - const sceneActivated = false; - let actorInitialized = false; - scene.once('initialize', (evt) => { - sceneInitialized = true; - expect(actorInitialized).toBe(true, 'Actor should be initialized before scene initialization'); - }); - const actor = new ex.Actor(); - actor.once('initialize', (evt) => { - actorInitialized = true; - }); + let sceneInitialized = false; + const sceneActivated = false; + let actorInitialized = false; + scene.once('initialize', (evt) => { + sceneInitialized = true; + expect(actorInitialized, 'Actor should be initialized before scene initialization').toBe(true); + }); + const actor = new ex.Actor(); + actor.once('initialize', (evt) => { + actorInitialized = true; + }); - scene.once('activate', (evt) => { - expect(actorInitialized).toBe(true, 'Actor should be initialized before scene is activated'); - done(); - }); + scene.once('activate', (evt) => { + expect(actorInitialized, 'Actor should be initialized before scene is activated').toBe(true); + done(); + }); - scene.add(actor); - engine.goToScene('otherScene'); - engine.start(); - const clock = engine.clock as ex.TestClock; - clock.step(100); - engine.dispose(); - }); + scene.add(actor); + engine.goToScene('otherScene'); + engine.start(); + const clock = engine.clock as ex.TestClock; + clock.step(100); + engine.dispose(); + })); it('can only be initialized once', async () => { engine.stop(); @@ -423,7 +425,7 @@ describe('A scene', () => { engine.addScene('newScene', scene); - const initSpy = jasmine.createSpy('init'); + const initSpy = vi.fn(); scene.on('initialize', initSpy); await engine.goToScene('newScene'); @@ -454,7 +456,7 @@ describe('A scene', () => { sceneInit = true; }; actor.onInitialize = () => { - expect(sceneInit).toBe(true, 'Scene should be initialized first before any actors'); + expect(sceneInit, 'Scene should be initialized first before any actors').toBe(true); }; await engine.goToScene('newScene'); @@ -473,7 +475,7 @@ describe('A scene', () => { }); scene.update(engine, 10); - expect(removed).toBe(true, 'Actor postupdate was not called'); + expect(removed, 'Actor postupdate was not called').toBe(true); expect(scene.actors.indexOf(actor)).toBe(-1); }); @@ -486,7 +488,7 @@ describe('A scene', () => { }); scene.update(engine, 10); - expect(removed).toBe(true, 'Actor postupdate was not called'); + expect(removed, 'Actor postupdate was not called').toBe(true); expect(scene.actors.indexOf(actor)).toBe(-1); }); @@ -504,7 +506,7 @@ describe('A scene', () => { }); scene.update(engine, 10); - expect(removed).toBe(true, 'Actor postupdate was not called'); + expect(removed, 'Actor postupdate was not called').toBe(true); expect(scene.actors.indexOf(actor)).toBe(-1); expect(scene.actors.length).toBe(1); }); @@ -522,7 +524,7 @@ describe('A scene', () => { }); scene.update(engine, 10); - expect(removed).toBe(true, 'Actor postupdate was not called'); + expect(removed, 'Actor postupdate was not called').toBe(true); expect(scene.actors.indexOf(actor)).toBe(-1); expect(scene.actors.length).toBe(1); }); @@ -544,8 +546,8 @@ describe('A scene', () => { const scene2 = new ex.Scene(); const actor = new ex.Actor(); - const entityRemoved = jasmine.createSpy('entityremoved'); - const entityAdded = jasmine.createSpy('entityadded'); + const entityRemoved = vi.fn(); + const entityAdded = vi.fn(); scene1.on('entityremoved', entityRemoved); scene2.on('entityadded', entityAdded); @@ -553,14 +555,14 @@ describe('A scene', () => { scene1.add(actor); expect(actor.scene).toBe(scene1); - expect(scene1.contains(actor)).toBeTrue(); - expect(scene2.contains(actor)).toBeFalse(); + expect(scene1.contains(actor)).toBe(true); + expect(scene2.contains(actor)).toBe(false); scene2.transfer(actor); expect(actor.scene).toBe(scene2); - expect(scene1.contains(actor)).toBeFalse(); - expect(scene2.contains(actor)).toBeTrue(); + expect(scene1.contains(actor)).toBe(false); + expect(scene2.contains(actor)).toBe(true); expect(entityAdded).toHaveBeenCalledTimes(1); expect(entityRemoved).toHaveBeenCalledTimes(1); @@ -576,8 +578,8 @@ describe('A scene', () => { interval: 100 }); - const entityRemoved = jasmine.createSpy('entityremoved'); - const entityAdded = jasmine.createSpy('entityadded'); + const entityRemoved = vi.fn(); + const entityAdded = vi.fn(); scene1.on('entityremoved', entityRemoved); scene2.on('entityadded', entityAdded); @@ -585,14 +587,14 @@ describe('A scene', () => { scene1.add(timer); expect(timer.scene).toBe(scene1); - expect(scene1.timers.includes(timer)).toBeTrue(); - expect(scene2.timers.includes(timer)).toBeFalse(); + expect(scene1.timers.includes(timer)).toBe(true); + expect(scene2.timers.includes(timer)).toBe(false); scene2.transfer(timer); expect(timer.scene).toBe(scene2); - expect(scene1.timers.includes(timer)).toBeFalse(); - expect(scene2.timers.includes(timer)).toBeTrue(); + expect(scene1.timers.includes(timer)).toBe(false); + expect(scene2.timers.includes(timer)).toBe(true); expect(entityAdded).toHaveBeenCalledTimes(1); expect(entityRemoved).toHaveBeenCalledTimes(1); @@ -622,11 +624,11 @@ describe('A scene', () => { actor.on('postupdate', () => { updated = true; - expect(initialized).toBe(true, 'Actor was not initialized before calling update'); + expect(initialized, 'Actor was not initialized before calling update').toBe(true); }); actor.on('postdraw', () => { - expect(updated).toBe(true, 'Actor was not updated before calling draw'); - expect(initialized).toBe(true, 'Actor was not initialized before calling draw'); + expect(updated, 'Actor was not updated before calling draw').toBe(true); + expect(initialized, 'Actor was not initialized before calling draw').toBe(true); }); // create Timer @@ -643,9 +645,9 @@ describe('A scene', () => { scene.update(engine, 11); scene.draw(engine.graphicsContext, 11); - expect(scene.actors.indexOf(actor)).toBeGreaterThan(-1, 'Actor was not added to scene'); - expect(initialized).toBe(true, 'Actor was not initialized after timer callback'); - expect(updated).toBe(true, 'Actor was not updated after timer callback'); + expect(scene.actors.indexOf(actor), 'Actor was not added to scene').toBeGreaterThan(-1); + expect(initialized, 'Actor was not initialized after timer callback').toBe(true); + expect(updated, 'Actor was not updated after timer callback').toBe(true); }); it('will update ScreenElement that were added in a Timer callback', () => { @@ -658,11 +660,11 @@ describe('A scene', () => { actor.on('postupdate', () => { updated = true; - expect(initialized).toBe(true, 'ScreenElement was not initialized before calling update'); + expect(initialized, 'ScreenElement was not initialized before calling update').toBe(true); }); actor.on('postdraw', () => { - expect(updated).toBe(true, 'ScreenElement was not updated before calling draw'); - expect(initialized).toBe(true, 'ScreenElement was not initialized before calling draw'); + expect(updated, 'ScreenElement was not updated before calling draw').toBe(true); + expect(initialized, 'ScreenElement was not initialized before calling draw').toBe(true); }); // create Timer @@ -679,15 +681,15 @@ describe('A scene', () => { scene.update(engine, 11); scene.draw(engine.graphicsContext, 11); - expect(scene.actors.indexOf(actor)).toBeGreaterThan(-1, 'ScreenElement was not added to scene'); - expect(initialized).toBe(true, 'ScreenElement was not initialized after timer callback'); - expect(updated).toBe(true, 'ScreenElement was not updated after timer callback'); + expect(scene.actors.indexOf(actor), 'ScreenElement was not added to scene').toBeGreaterThan(-1); + expect(initialized, 'ScreenElement was not initialized after timer callback').toBe(true); + expect(updated, 'ScreenElement was not updated after timer callback').toBe(true); }); it('will kill the actor if the actor is removed from the scene', () => { scene.add(actor); - spyOn(actor, 'kill').and.callThrough(); + vi.spyOn(actor, 'kill'); scene.remove(actor); @@ -699,7 +701,7 @@ describe('A scene', () => { scene.add(actor); actor.active = false; - spyOn(actor, 'kill').and.callThrough(); + vi.spyOn(actor, 'kill'); scene.remove(actor); expect(actor.kill).toHaveBeenCalledTimes(0); @@ -707,7 +709,7 @@ describe('A scene', () => { it('will remove an actor from a scene if actor is killed', () => { scene.add(actor); - spyOn(scene, 'remove').and.callThrough(); + vi.spyOn(scene, 'remove'); actor.kill(); scene.update(engine, 100); @@ -723,7 +725,7 @@ describe('A scene', () => { updated = true; }); tilemap.on('postdraw', () => { - expect(updated).toBe(true, 'TileMap was not updated before calling draw'); + expect(updated, 'TileMap was not updated before calling draw').toBe(true); }); // create Timer @@ -740,8 +742,8 @@ describe('A scene', () => { scene.update(engine, 11); scene.draw(engine.graphicsContext, 11); - expect(scene.tileMaps.indexOf(tilemap)).toBeGreaterThan(-1, 'TileMap was not added to scene'); - expect(updated).toBe(true, 'TileMap was not updated after timer callback'); + expect(scene.tileMaps.indexOf(tilemap), 'TileMap was not added to scene').toBeGreaterThan(-1); + expect(updated, 'TileMap was not updated after timer callback').toBe(true); }); it('will return true if it is the current engine scene', () => { @@ -792,7 +794,7 @@ describe('A scene', () => { initCalled = true; }); - spyOn(scene, 'onInitialize').and.callThrough(); + vi.spyOn(scene, 'onInitialize'); await TestUtils.runToReady(engine); await engine.goToScene('newScene'); @@ -809,8 +811,8 @@ describe('A scene', () => { expect(elapsedMs).toBe(100); }; - spyOn(scene, 'onPostUpdate').and.callThrough(); - spyOn(scene, '_postupdate').and.callThrough(); + vi.spyOn(scene, 'onPostUpdate'); + vi.spyOn(scene, '_postupdate'); scene.update(engine, 100); scene.update(engine, 100); @@ -826,8 +828,8 @@ describe('A scene', () => { expect(elapsedMs).toBe(100); }; - spyOn(scene, 'onPreUpdate').and.callThrough(); - spyOn(scene, '_preupdate').and.callThrough(); + vi.spyOn(scene, 'onPreUpdate'); + vi.spyOn(scene, '_preupdate'); scene.update(engine, 100); scene.update(engine, 100); @@ -844,8 +846,8 @@ describe('A scene', () => { expect(elapsedMs).toBe(100); }; - spyOn(scene, 'onPreDraw').and.callThrough(); - spyOn(scene, '_predraw').and.callThrough(); + vi.spyOn(scene, 'onPreDraw'); + vi.spyOn(scene, '_predraw'); scene.draw(engine.graphicsContext, 100); scene.draw(engine.graphicsContext, 100); @@ -862,8 +864,8 @@ describe('A scene', () => { expect(elapsedMs).toBe(100); }; - spyOn(scene, 'onPostDraw').and.callThrough(); - spyOn(scene, '_postdraw').and.callThrough(); + vi.spyOn(scene, 'onPostDraw'); + vi.spyOn(scene, '_postdraw'); scene.draw(engine.graphicsContext, 100); scene.draw(engine.graphicsContext, 100); diff --git a/src/spec/ScreenAppenderSpec.ts b/src/spec/vitest/ScreenAppenderSpec.ts similarity index 75% rename from src/spec/ScreenAppenderSpec.ts rename to src/spec/vitest/ScreenAppenderSpec.ts index 64934b61..fecbf484 100644 --- a/src/spec/ScreenAppenderSpec.ts +++ b/src/spec/vitest/ScreenAppenderSpec.ts @@ -1,12 +1,7 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; -import { ExcaliburAsyncMatchers } from 'excalibur-jasmine'; describe('A ScreenAppender', () => { - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - it('exists', () => { expect(ex.ScreenAppender).toBeDefined(); }); @@ -34,12 +29,12 @@ describe('A ScreenAppender', () => { sut.log(ex.LogLevel.Info, ['this is a log']); await TestUtils.runOnWindows(async () => { - await expectAsync(sut.canvas).toEqualImage('src/spec/images/ScreenAppenderSpec/screen-log.png'); + await expect(sut.canvas).toEqualImage('/src/spec/assets/images/ScreenAppenderSpec/screen-log.png'); }); // FIXME CI chokes on this one for some reason // await TestUtils.runOnLinux(async () => { - // await expectAsync(sut.canvas).toEqualImage('src/spec/images/ScreenAppenderSpec/screen-log-linux.png'); + // await expect(sut.canvas).toEqualImage('src/spec/assets/images/ScreenAppenderSpec/screen-log-linux.png'); // }); engine.dispose(); }); diff --git a/src/spec/ScreenElementSpec.ts b/src/spec/vitest/ScreenElementSpec.ts similarity index 87% rename from src/spec/ScreenElementSpec.ts rename to src/spec/vitest/ScreenElementSpec.ts index 6c74e8e8..8df59aac 100644 --- a/src/spec/ScreenElementSpec.ts +++ b/src/spec/vitest/ScreenElementSpec.ts @@ -1,4 +1,3 @@ -import { ExcaliburMatchers, ensureImagesLoaded, ExcaliburAsyncMatchers } from 'excalibur-jasmine'; import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; import { ScreenElement } from '@excalibur'; @@ -9,11 +8,6 @@ describe('A ScreenElement', () => { let scene: ex.Scene; let clock: ex.TestClock; - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); - beforeEach(async () => { screenElement = new ex.ScreenElement({ pos: new ex.Vector(50, 50), @@ -41,7 +35,7 @@ describe('A ScreenElement', () => { it('can be constructed with zero args without a warning', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); const sut = new ScreenElement(); @@ -93,7 +87,7 @@ describe('A ScreenElement', () => { it('is drawn when visible', () => { screenElement.graphics.visible = true; - screenElement.graphics.onPostDraw = jasmine.createSpy('draw'); + screenElement.graphics.onPostDraw = vi.fn(); scene.add(screenElement); scene.draw(engine.graphicsContext, 100); @@ -103,7 +97,7 @@ describe('A ScreenElement', () => { it('is not drawn when not visible', () => { screenElement.graphics.visible = false; - screenElement.graphics.onPostDraw = jasmine.createSpy('draw'); + screenElement.graphics.onPostDraw = vi.fn(); scene.add(screenElement); scene.draw(engine.graphicsContext, 100); @@ -128,7 +122,7 @@ describe('A ScreenElement', () => { it('is drawn on the top left with empty constructor', async () => { const game = TestUtils.engine({ width: 720, height: 480 }); const clock = game.clock as ex.TestClock; - const bg = new ex.ImageSource('src/spec/images/ScreenElementSpec/emptyctor.png'); + const bg = new ex.ImageSource('/src/spec/assets/images/ScreenElementSpec/emptyctor.png'); const loader = new ex.Loader([bg]); await TestUtils.runToReady(game, loader); const screenElement = new ex.ScreenElement(); @@ -136,7 +130,7 @@ describe('A ScreenElement', () => { game.add(screenElement); game.currentScene.draw(game.graphicsContext, 100); game.graphicsContext.flush(); - await expectAsync(game.canvas).toEqualImage('src/spec/images/ScreenElementSpec/emptyctor.png'); + await expect(game.canvas).toEqualImage('/src/spec/assets/images/ScreenElementSpec/emptyctor.png'); game.dispose(); }); }); diff --git a/src/spec/ScreenSpec.ts b/src/spec/vitest/ScreenSpec.ts similarity index 97% rename from src/spec/ScreenSpec.ts rename to src/spec/vitest/ScreenSpec.ts index 6356a495..bd74cd1e 100644 --- a/src/spec/ScreenSpec.ts +++ b/src/spec/vitest/ScreenSpec.ts @@ -1,5 +1,5 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; + import { Camera } from '@excalibur'; describe('A Screen', () => { @@ -8,7 +8,6 @@ describe('A Screen', () => { let browser: ex.BrowserEvents; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); // It's important nothing else is hanging out in the dom Array.from(document.body.children).forEach((element) => { document.body.removeChild(element); @@ -429,8 +428,12 @@ describe('A Screen', () => { }); it('will go fullscreen with the canvas element by default', () => { - const mockCanvas = jasmine.createSpyObj('canvas', ['addEventListener', 'removeEventListener', 'requestFullscreen']); - mockCanvas.style = {}; + const mockCanvas = { + addEventListener: vi.fn(), + removeEventListener: vi.fn(), + requestFullscreen: vi.fn(), + style: {} + } as any; const sut = new ex.Screen({ canvas: mockCanvas, context, @@ -458,8 +461,14 @@ describe('A Screen', () => { viewport: { width: 800, height: 600 } }); - const fakeElement = jasmine.createSpyObj('element', ['requestFullscreen', 'getAttribute', 'setAttribute', 'addEventListener']); - spyOn(document, 'getElementById').and.returnValue(fakeElement); + const fakeElement = { + addEventListener: vi.fn(), + removeEventListener: vi.fn(), + requestFullscreen: vi.fn(), + getAttribute: vi.fn(), + setAttribute: vi.fn() + }; + vi.spyOn(document, 'getElementById').mockImplementation(() => fakeElement as any); sut.enterFullscreen('some-id'); @@ -577,7 +586,7 @@ describe('A Screen', () => { sut.applyResolutionAndViewport(); - expect(context.smoothing).toBeFalse(); + expect(context.smoothing).toBe(false); expect(canvas.style.imageRendering).toBe('pixelated'); }); @@ -615,7 +624,7 @@ describe('A Screen', () => { sut.applyResolutionAndViewport(); - expect(context.smoothing).toBeFalse(); + expect(context.smoothing).toBe(false); expect(canvasStub.style.imageRendering).toBe('crisp-edges'); }); @@ -631,7 +640,7 @@ describe('A Screen', () => { sut.applyResolutionAndViewport(); - expect(context.smoothing).toBeTrue(); + expect(context.smoothing).toBe(true); expect(canvas.style.imageRendering).toBe('auto'); }); @@ -914,7 +923,7 @@ describe('A Screen', () => { it('will warn if the resolution is too large', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warnOnce'); + vi.spyOn(logger, 'warnOnce'); const canvasElement = document.createElement('canvas'); canvasElement.width = 100; @@ -935,11 +944,11 @@ describe('A Screen', () => { pixelRatio: 2 }); - spyOn(context, 'checkIfResolutionSupported').and.returnValue(false); + vi.spyOn(context, 'checkIfResolutionSupported').mockImplementation(() => false); sut.resolution = { width: 3000, height: 3000 }; sut.applyResolutionAndViewport(); expect(context.checkIfResolutionSupported).toHaveBeenCalled(); - expect(logger.warnOnce).toHaveBeenCalledOnceWith( + expect(logger.warnOnce).toHaveBeenCalledExactlyOnceWith( `The currently configured resolution (${sut.resolution.width}x${sut.resolution.height}) and pixel ratio (${sut.pixelRatio})` + ' are too large for the platform WebGL implementation, this may work but cause WebGL rendering to behave oddly.' + ' Try reducing the resolution or disabling Hi DPI scaling to avoid this' + @@ -949,7 +958,7 @@ describe('A Screen', () => { it('will warn if the resolution is too large and attempt to recover', () => { const logger = ex.Logger.getInstance(); - const warnOnce = spyOn(logger, 'warnOnce'); + const warnOnce = vi.spyOn(logger, 'warnOnce'); const canvasElement = document.createElement('canvas'); canvasElement.width = 100; @@ -969,18 +978,18 @@ describe('A Screen', () => { viewport: { width: 800, height: 600 } }); - spyOn(context, 'checkIfResolutionSupported').and.callThrough(); + vi.spyOn(context, 'checkIfResolutionSupported'); sut.resolution = { width: 2000, height: 2000 }; (sut as any)._devicePixelRatio = 3; sut.applyResolutionAndViewport(); expect(context.checkIfResolutionSupported).toHaveBeenCalled(); - expect(warnOnce.calls.argsFor(0)).toEqual([ + expect(warnOnce.mock.calls[0]).toEqual([ `The currently configured resolution (${sut.resolution.width}x${sut.resolution.height}) and pixel ratio (3)` + ' are too large for the platform WebGL implementation, this may work but cause WebGL rendering to behave oddly.' + ' Try reducing the resolution or disabling Hi DPI scaling to avoid this' + ' (read more here https://excaliburjs.com/docs/screens#understanding-viewport--resolution).' ]); - expect(warnOnce.calls.argsFor(1)).toEqual([ + expect(warnOnce.mock.calls[1]).toEqual([ 'Scaled resolution too big attempted recovery!' + ` Pixel ratio was automatically reduced to (2) to avoid 4k texture limit.` + ' Setting `ex.Engine({pixelRatio: ...}) will override any automatic recalculation, do so at your own risk.` ' + diff --git a/src/spec/vitest/SemaphoreSpec.ts b/src/spec/vitest/SemaphoreSpec.ts new file mode 100644 index 00000000..373ac55f --- /dev/null +++ b/src/spec/vitest/SemaphoreSpec.ts @@ -0,0 +1,85 @@ +import * as ex from '@excalibur'; + +describe('A Semaphore', () => { + it('should exist', () => { + expect(ex.Semaphore).toBeDefined(); + }); + + it('can be constructed with a count', () => { + const semaphore = new ex.Semaphore(10); + expect(semaphore.count).toBe(10); + }); + + it('a trivial exit does not decrement semaphor', () => { + const semaphore = new ex.Semaphore(10); + for (let i = 0; i < 20; i++) { + semaphore.enter(); + } + expect(semaphore.waiting).toBe(10); + expect(semaphore.count).toBe(0); + semaphore.exit(0); + expect(semaphore.waiting).toBe(10); + expect(semaphore.count).toBe(0); + }); + + it('can limit async calls', () => { + const semaphore = new ex.Semaphore(10); + for (let i = 0; i < 20; i++) { + semaphore.enter(); + } + expect(semaphore.waiting).toBe(10); + semaphore.exit(); + semaphore.exit(); + semaphore.exit(); + expect(semaphore.waiting).toBe(7); + }); + + it('can block async calls', () => + new Promise((done) => { + const mockFuture1 = new ex.Future(); + const mockMethod1 = () => { + return mockFuture1.promise; + }; + + const mockFuture2 = new ex.Future(); + const mockMethod2 = () => { + return mockFuture2.promise; + }; + const semaphore = new ex.Semaphore(1); + + const spy1 = vi.fn(); + const spy2 = vi.fn(); + + semaphore + .enter() + .then(() => { + expect(semaphore.count).toBe(0); + expect(semaphore.waiting).toBe(0); + mockMethod1().then(() => { + spy1(); + semaphore.exit(); + }); + const final = semaphore.enter().then(() => { + mockMethod2().then(() => { + spy2(); + semaphore.exit(); + }); + }); + expect(semaphore.count).toBe(0); + expect(semaphore.waiting).toBe(1); + return final; + }) + .finally(() => { + expect(spy1).toHaveBeenCalled(); + expect(spy2).toHaveBeenCalled(); + expect(spy1).toHaveBeenCalledBefore(spy2); + done(); + }); + + expect(spy1).not.toHaveBeenCalled(); + expect(spy2).not.toHaveBeenCalled(); + + mockFuture1.resolve(); + mockFuture2.resolve(); + })); +}); diff --git a/src/spec/ShaderSpec.ts b/src/spec/vitest/ShaderSpec.ts similarity index 90% rename from src/spec/ShaderSpec.ts rename to src/spec/vitest/ShaderSpec.ts index 06d9aedb..a2208114 100644 --- a/src/spec/ShaderSpec.ts +++ b/src/spec/vitest/ShaderSpec.ts @@ -1,12 +1,8 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A Shader', () => { let gl: WebGL2RenderingContext; let graphicsContext: ex.ExcaliburGraphicsContextWebGL; - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); beforeEach(() => { const canvas = document.createElement('canvas'); @@ -42,7 +38,7 @@ describe('A Shader', () => { expect(sut.compiled).toBe(false); sut.compile(); expect(sut.compiled).toBe(true); - expect(sut.attributes.a_position).withContext('a_position').toEqual({ + expect(sut.attributes.a_position, 'a_position').toEqual({ name: 'a_position', glType: gl.FLOAT, size: 4, @@ -50,7 +46,7 @@ describe('A Shader', () => { location: sut.attributes.a_position.location }); - expect(sut.attributes.a_otherposition).withContext('a_otherposition').toEqual({ + expect(sut.attributes.a_otherposition, 'a_otherposition').toEqual({ name: 'a_otherposition', glType: gl.FLOAT, size: 3, @@ -59,7 +55,7 @@ describe('A Shader', () => { }); const u_bool = sut.getUniformDefinitions()[0]; - expect(u_bool).withContext('u_bool').toEqual({ + expect(u_bool, 'u_bool').toEqual({ name: 'u_bool', glType: gl.BOOL, location: u_bool.location @@ -82,9 +78,7 @@ describe('A Shader', () => { }); expect(() => { sut.compile(); - }).toThrowMatching((e: Error) => { - return e.message.includes('vertex'); - }); + }).toThrowError(/vertex/); }); it('can fail compiling fragment', () => { @@ -103,9 +97,7 @@ describe('A Shader', () => { }); expect(() => { sut.compile(); - }).toThrowMatching((e: Error) => { - return e.message.includes('fragment'); - }); + }).toThrowError(/fragment/); }); it('must be compiled and shader.use() to set uniforms', () => { @@ -228,15 +220,15 @@ describe('A Shader', () => { }` }); const logger = ex.Logger.getInstance(); - const loggerSpy = spyOn(logger, 'warn'); + const loggerSpy = vi.spyOn(logger, 'warn'); sut.trySetUniformInt('u_int', 0); - expect(loggerSpy.calls.argsFor(0)).toEqual(['Must compile shader before setting a uniform uniform1i:u_int']); + expect(loggerSpy.mock.calls[0]).toEqual(['Must compile shader before setting a uniform uniform1i:u_int']); sut.compile(); sut.trySetUniformInt('u_int', 0); - expect(loggerSpy.calls.argsFor(1)).toEqual([ + expect(loggerSpy.mock.calls[1]).toEqual([ 'Currently accessed shader instance is not the current active shader in WebGL, must call `shader.use()` before setting uniforms' ]); sut.use(); @@ -284,8 +276,8 @@ describe('A Shader', () => { sut.compile(); const tex = gl.createTexture(); - spyOn(gl, 'activeTexture').and.callThrough(); - spyOn(gl, 'bindTexture').and.callThrough(); + vi.spyOn(gl, 'activeTexture'); + vi.spyOn(gl, 'bindTexture'); sut.setTexture(5, tex); diff --git a/src/spec/SlideSpec.ts b/src/spec/vitest/SlideSpec.ts similarity index 86% rename from src/spec/SlideSpec.ts rename to src/spec/vitest/SlideSpec.ts index 484a5698..9f6cd47b 100644 --- a/src/spec/SlideSpec.ts +++ b/src/spec/vitest/SlideSpec.ts @@ -1,11 +1,7 @@ import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; -import { ExcaliburAsyncMatchers } from 'excalibur-jasmine'; describe('A Slide transition', () => { - beforeAll(() => { - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); it('exists', () => { expect(ex.Slide).toBeDefined(); }); @@ -29,7 +25,7 @@ describe('A Slide transition', () => { }) ); - const onDeactivateSpy = jasmine.createSpy('onDeactivate'); + const onDeactivateSpy = vi.fn(); engine.director.getSceneInstance('root').onDeactivate = onDeactivateSpy; @@ -50,7 +46,7 @@ describe('A Slide transition', () => { await TestUtils.untilMacrotask(() => engine.currentSceneName !== 'root'); clock.step(500); expect(onDeactivateSpy).toHaveBeenCalledTimes(1); - await expectAsync(engine.canvas).toEqualImage('/src/spec/images/SlideSpec/slide-down.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/SlideSpec/slide-down.png'); engine.stop(); engine.dispose(); }); @@ -68,7 +64,7 @@ describe('A Slide transition', () => { }) ); - const onDeactivateSpy = jasmine.createSpy('onDeactivate'); + const onDeactivateSpy = vi.fn(); engine.director.getSceneInstance('root').onDeactivate = onDeactivateSpy; @@ -89,7 +85,7 @@ describe('A Slide transition', () => { await TestUtils.untilMacrotask(() => engine.currentSceneName !== 'root'); clock.step(500); expect(onDeactivateSpy).toHaveBeenCalledTimes(1); - await expectAsync(engine.canvas).toEqualImage('/src/spec/images/SlideSpec/slide-right.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/SlideSpec/slide-right.png'); engine.stop(); engine.dispose(); }); @@ -107,7 +103,7 @@ describe('A Slide transition', () => { }) ); - const onDeactivateSpy = jasmine.createSpy('onDeactivate'); + const onDeactivateSpy = vi.fn(); engine.director.getSceneInstance('root').onDeactivate = onDeactivateSpy; @@ -128,7 +124,7 @@ describe('A Slide transition', () => { await TestUtils.untilMacrotask(() => engine.currentSceneName !== 'root'); clock.step(500); expect(onDeactivateSpy).toHaveBeenCalledTimes(1); - await expectAsync(engine.canvas).toEqualImage('/src/spec/images/SlideSpec/slide-left.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/SlideSpec/slide-left.png'); engine.stop(); engine.dispose(); }); @@ -146,7 +142,7 @@ describe('A Slide transition', () => { }) ); - const onDeactivateSpy = jasmine.createSpy('onDeactivate'); + const onDeactivateSpy = vi.fn(); engine.director.getSceneInstance('root').onDeactivate = onDeactivateSpy; @@ -167,7 +163,7 @@ describe('A Slide transition', () => { await TestUtils.untilMacrotask(() => engine.currentSceneName !== 'root'); clock.step(500); expect(onDeactivateSpy).toHaveBeenCalledTimes(1); - await expectAsync(engine.canvas).toEqualImage('/src/spec/images/SlideSpec/slide-up.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/SlideSpec/slide-up.png'); engine.stop(); engine.dispose(); }); @@ -185,7 +181,7 @@ describe('A Slide transition', () => { }) ); - const onDeactivateSpy = jasmine.createSpy('onDeactivate'); + const onDeactivateSpy = vi.fn(); engine.director.getSceneInstance('root').onDeactivate = onDeactivateSpy; @@ -210,7 +206,7 @@ describe('A Slide transition', () => { await TestUtils.untilMacrotask(() => engine.currentSceneName !== 'root'); clock.step(700); expect(onDeactivateSpy).toHaveBeenCalledTimes(1); - await expectAsync(engine.canvas).toEqualImage('/src/spec/images/SlideSpec/slide-up-transition.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/SlideSpec/slide-up-transition.png'); engine.stop(); engine.dispose(); }); diff --git a/src/spec/vitest/SoundSpec.ts b/src/spec/vitest/SoundSpec.ts new file mode 100644 index 00000000..4ed415bf --- /dev/null +++ b/src/spec/vitest/SoundSpec.ts @@ -0,0 +1,527 @@ +import * as ex from '@excalibur'; +import { canPlayFile } from '../../engine/Util/Sound'; +import { delay } from '../../engine/Util/Util'; +import { WebAudio } from '../../engine/Util/WebAudio'; +import { TestUtils } from './util/TestUtils'; + +import { page } from '@vitest/browser/context'; + +// beware if running firefox/webkit, audio will play. not sure how to mute those browsers +// also note that webkit cant play ogg files so only use supported formats here! +describe('Sound resource', () => { + let sut: ex.Sound; + + beforeAll(async () => { + // automate user interaction to allow WebAudio to unlock + await page.elementLocator(document.body).click(); + ex.Logger.getInstance().clearAppenders(); + await WebAudio.unlock(); + }); + + beforeEach(() => { + sut = new ex.Sound('/src/spec/assets/images/SoundSpec/test.mp3'); + expect(sut.path).toBe('/src/spec/assets/images/SoundSpec/test.mp3'); + }); + + it('should be able to be constructed', () => { + expect(sut).toBeDefined(); + }); + + it('can detect playability of files', () => { + expect(canPlayFile('coin.mp3')).toBe(true); + }); + + it('can detect playability of files', () => { + expect(canPlayFile('coin.mp3?12234')).toBe(true); + }); + + it('can detect playability of files with multiple dots', () => { + expect(canPlayFile('coin.f74d9d70.mp3')).toBe(true); + }); + + it('can detect playability of files with querystrings', () => { + expect(canPlayFile('coin.f74d9d70.mp3?1678266496281')).toBe(true); + }); + + it('can detect playability of files with hash', () => { + expect(canPlayFile('coin.f74d9d70.mp3#1678266496281')).toBe(true); + }); + + it('can detect playability of files with querystring and hash', () => { + expect(canPlayFile('coin.f74d9d70.mp3?_=1234#1678266496281')).toBe(true); + }); + + it('should fire processed event', async () => { + const processedSpy = vi.fn(); + sut.once('processed', processedSpy); + await sut.load(); + expect(processedSpy).toHaveBeenCalledTimes(1); + }); + + it('should have duration', async () => { + sut = new ex.Sound('/src/spec/assets/images/SoundSpec/preview.mp3'); + sut.duration = 5.0; + await sut.load(); + expect(sut.duration).toBeDefined(); + expect(sut.duration).toBe(5); + }); + + it('should fire playbackstart event', async () => { + const playbackSpy = vi.fn(); + + sut.on('playbackstart', playbackSpy); + + sut.loop = false; + + await sut.load(); + await sut.play(); + + expect(playbackSpy).toHaveBeenCalledTimes(1); + }); + + it('should fire playbackend event', async () => { + const playbackEndSpy = vi.fn(); + + sut.on('playbackend', playbackEndSpy); + + sut.loop = false; + await sut.load(); + await sut.play(); + expect(playbackEndSpy).toHaveBeenCalledTimes(1); + }); + + it('should fire resume event', async () => { + const resumeSpy = vi.fn(); + await sut.load(); + + sut.once('resume', resumeSpy); + + sut.once('playbackstart', () => { + sut.pause(); + sut.play(); + }); + + sut.loop = false; + await sut.play(); + expect(resumeSpy).toHaveBeenCalledTimes(1); + }); + + it('should fire volumechange event', () => { + const volumenChangeSpy = vi.fn(); + + sut.once('volumechange', volumenChangeSpy); + + sut.volume = 0.3; + expect(volumenChangeSpy).toHaveBeenCalledTimes(1); + }); + + it('should fire pause event', () => + new Promise((done) => { + sut.load().then(() => { + const pauseSpy = vi.fn(); + + sut.once('pause', pauseSpy); + + sut.once('playbackstart', () => { + sut.pause(); + expect(pauseSpy).toHaveBeenCalledTimes(1); + done(); + }); + sut.play(); + }); + })); + + it('should fire stop event', () => + new Promise((done) => { + sut.load().then(() => { + const stopSpy = vi.fn(); + + sut.once('stop', stopSpy); + + sut.once('playbackstart', () => { + sut.stop(); + + expect(stopSpy).toHaveBeenCalledTimes(1); + done(); + }); + + sut.play(); + }); + })); + + it('should create a new audio instance when played', () => + new Promise((done) => { + sut.load().then(() => { + vi.spyOn(sut, 'instanceCount'); + + const initialInstancesCnt = sut.instanceCount(); + + sut.once('playbackstart', () => { + expect(sut.instanceCount()).toBeGreaterThan(initialInstancesCnt); + done(); + }); + + sut.loop = false; + sut.play(); + }); + })); + + it('should set tracks loop value same as own', () => + new Promise((done) => { + sut.load().then(() => { + sut.loop = true; + + sut.once('playbackstart', () => { + expect(sut.instances[0].loop).toBe(sut.loop); + done(); + }); + + sut.play(); + }); + })); + + it('should not provide a duration if looping', async () => { + await sut.load(); + + const webaudio = new ex.WebAudioInstance(sut.data); + vi.spyOn(webaudio as any, '_createNewBufferSource').mockImplementation(() => void 0); + const instance = { + start: vi.fn() + } as any; + (webaudio as any)._instance = instance; + webaudio.loop = true; + webaudio.play(); + + expect((webaudio as any)._createNewBufferSource).toHaveBeenCalled(); + expect(instance.start).toHaveBeenCalledWith(0, 0); + }); + + it('should provide a duration if not looping', async () => { + await sut.load(); + + const webaudio = new ex.WebAudioInstance(sut.data); + vi.spyOn(webaudio as any, '_createNewBufferSource').mockImplementation(() => void 0); + const instance = { + start: vi.fn() + } as any; + (webaudio as any)._instance = instance; + webaudio.loop = false; + webaudio.play(); + + expect((webaudio as any)._createNewBufferSource).toHaveBeenCalled(); + expect(instance.start).toHaveBeenCalledWith(0, 0, sut.duration); + }); + + it('should set tracks volume value same as own', () => + new Promise((done) => { + sut.load().then(() => { + sut.volume = 0.5; + + sut.once('playbackstart', () => { + expect(sut.instances[0].volume).toBe(sut.volume); + done(); + }); + + sut.play(); + }); + })); + + it('should set volume with argument sent to play', () => + new Promise((done) => { + sut.load().then(() => { + sut.once('playbackstart', () => { + expect(sut.volume).toBe(0.5); + expect(sut.instances[0].volume).toBe(sut.volume); + done(); + }); + + sut.play(0.5); + }); + })); + + it('should play once and then finish if loop set to false', () => + new Promise((done) => { + sut.load().then(() => { + sut.loop = false; + + sut.once('playbackstart', () => { + expect(sut.isPlaying()).toBe(true); + }); + + sut.play().then(() => { + expect(sut.isPlaying()).toBe(false); + + done(); + }); + }); + })); + + it('should stop all currently playing tracks', () => + new Promise((done) => { + sut.load().then(() => { + sut.once('playbackstart', () => { + expect(sut.isPlaying(), 'track should be playing').toBe(true); + + sut.stop(); + expect(sut.isPlaying(), 'track should be stopped').toBe(false); + + done(); + }); + + sut.play(); + }); + })); + + it('should return the current playback position of the audio track', async () => { + sut = new ex.Sound('/src/spec/assets/images/SoundSpec/preview.mp3'); + await sut.load(); + sut.play(); + await delay(1000); + // appveyor is a little fast for some reason + expect(sut.getPlaybackPosition()).toBeGreaterThanOrEqual(0.98); + }); + + it('should variable playback rate of the audio track', async () => { + sut = new ex.Sound('/src/spec/assets/images/SoundSpec/preview.mp3'); + await sut.load(); + sut.playbackRate = 2.0; + sut.play(); + await delay(1000); + // appveyor is a little fast for some reason + expect(sut.getPlaybackPosition(), 'Twice the speed will be at 2 seconds').toBeGreaterThanOrEqual(1.8); + }); + + // FIXME: issue for flakey test https://github.com/excaliburjs/Excalibur/issues/1547 + it.skip('should stop all tracks even when paused', () => + new Promise((done) => { + sut.play(); + + setTimeout(() => { + sut.once('stop', () => { + done(); + }); + + expect(sut.isPlaying(), 'should be playing').toBe(true); + + // pause + sut.pause(); + + expect(sut.isPlaying(), 'should not be playing').toBe(false); + + // stop and rewind + sut.stop(); + }, 500); + })); + + it('should not have any tracks when stopped', () => + new Promise((done) => { + sut.load().then(() => { + sut.once('playbackstart', () => { + expect(sut.instanceCount(), 'should be one track').toBe(1); + + sut.stop(); + + expect(sut.instanceCount(), 'should be no tracks').toBe(0); + + done(); + }); + sut.play(); + }); + })); + + it('should not remove instance if paused', () => + new Promise((done) => { + sut.load().then(() => { + sut.once('playbackstart', () => { + expect(sut.instanceCount(), 'should be one track').toBe(1); + + sut.pause(); + + expect(sut.instanceCount(), 'should be one track').toBe(1); + + done(); + }); + sut.play(); + }); + })); + + it('should remove tracks as they are done when multiple are playing', () => + new Promise((done) => { + sut.load().then(() => { + sut.loop = false; + // start playing first track + sut.play().then(() => { + expect(sut.instanceCount(), 'should be on track').toBe(1); + }); + + // wait 250ms then play 2nd track + setTimeout(() => { + sut.on('playbackstart', () => { + expect(sut.instanceCount(), 'should be two simultaneous tracks').toBe(2); + }); + + sut.play().then(() => { + expect(sut.instanceCount(), 'should be no tracks').toBe(0); + done(); + }); + }, 250); + }); + })); + + it('should remove multiple tracks when stopped', () => + new Promise((done) => { + sut.load().then(() => { + sut.loop = false; + // start playing first track + + sut.once('playbackstart', (ev: ex.NativeSoundEvent) => { + if (sut.getTrackId(ev.track) === 0) { + sut.play(); + } + sut.stop(); + + expect(sut.instanceCount(), 'should be no tracks').toBe(0); + + done(); + }); + + sut.play(); + }); + })); + + it('can seek to a position in the sound', async () => { + sut = new ex.Sound('/src/spec/assets/images/SoundSpec/preview.mp3'); + await sut.load(); + expect(sut.getPlaybackPosition()).toBe(0); + sut.seek(6.5); + expect(sut.getPlaybackPosition()).toBe(6.5); + }); + + it('can get the total duration of the sound', async () => { + sut = new ex.Sound('/src/spec/assets/images/SoundSpec/preview.mp3'); + await sut.load(); + expect(sut.getTotalPlaybackDuration()).toBeCloseTo(13.01, 1); + }); + + it('can set/get the playback rate', async () => { + sut = new ex.Sound('/src/spec/assets/images/SoundSpec/preview.mp3'); + expect(sut.playbackRate).toBe(1.0); + sut.playbackRate = 2.5; + await sut.load(); + expect(sut.playbackRate).toBe(2.5); + }); + + it('can set the playback rate and seek to the right position', async () => { + sut = new ex.Sound('/src/spec/assets/images/SoundSpec/preview.mp3'); + expect(sut.playbackRate).toBe(1.0); + sut.playbackRate = 2.5; + await sut.load(); + sut.seek(6.5); + expect(sut.getPlaybackPosition()).toBe(6.5); + }); + + describe('wire engine', () => { + let engine: ex.Engine; + + beforeEach(() => { + engine = TestUtils.engine(); + engine.start(); + }); + + afterEach(() => { + engine.stop(); + engine.dispose(); + engine = null; + }); + + it('should stop all tracks when engine is stopped', () => + new Promise((done) => { + sut.load().then(() => { + sut.wireEngine(engine); + + sut.once('playbackstart', () => { + expect(sut.instanceCount(), 'should be one track').toBe(1); + + engine.stop(); + + expect(sut.instanceCount(), 'should be no tracks').toBe(0); + expect(sut.isPlaying(), 'should not be playing').toBe(false); + + done(); + }); + sut.play(); + }); + })); + + it('should not allow playing tracks when engine is stopped', () => + new Promise((done) => { + sut.load().then(() => { + sut.wireEngine(engine); + sut.once('playbackstart', () => { + expect(sut.isPlaying(), 'should be playing').toBe(true); + + engine.stop(); + + sut.play(); + + expect(sut.isPlaying(), 'should not allow playing').toBe(false); + + done(); + }); + sut.play(); + }); + })); + + it('should pause tracks when game is hidden and pauseAudioWhenHidden is true', () => + new Promise((done) => { + sut.load().then(() => { + engine.pauseAudioWhenHidden = true; + sut.wireEngine(engine); + + sut.once('playbackstart', () => { + expect(sut.isPlaying(), 'should be playing').toBe(true); + + setTimeout(() => { + engine.emit('hidden', new ex.HiddenEvent(engine)); + }, 100); + }); + + sut.play(); + + engine.once('hidden', () => { + expect(sut.isPlaying(), 'should pause when hidden').toBe(false); + done(); + }); + }); + })); + + it('should resume tracks when game is visible from hidden and pauseAudioWhenHidden is true', () => + new Promise((done) => { + sut.load().then(() => { + engine.pauseAudioWhenHidden = true; + sut.wireEngine(engine); + + sut.once('playbackstart', () => { + expect(sut.isPlaying(), 'should be playing').toBe(true); + + setTimeout(() => { + engine.emit('hidden', new ex.HiddenEvent(engine)); + }, 100); + }); + + sut.play(); + + engine.once('hidden', () => { + setTimeout(() => { + engine.emit('visible', new ex.VisibleEvent(engine)); + }, 100); + }); + + engine.once('visible', () => { + expect(sut.isPlaying(), 'should resume when visible').toBe(true); + done(); + }); + }); + })); + }); +}); diff --git a/src/spec/SparseHashGridCollisionProcessorSpec.ts b/src/spec/vitest/SparseHashGridCollisionProcessorSpec.ts similarity index 98% rename from src/spec/SparseHashGridCollisionProcessorSpec.ts rename to src/spec/vitest/SparseHashGridCollisionProcessorSpec.ts index 90e1e8d2..a0b1d722 100644 --- a/src/spec/SparseHashGridCollisionProcessorSpec.ts +++ b/src/spec/vitest/SparseHashGridCollisionProcessorSpec.ts @@ -351,19 +351,19 @@ describe('A Sparse Hash Grid Broadphase', () => { sut.track(actor1.collider.get()); const ray = new ex.Ray(ex.vec(0, 0), ex.Vector.Right); - const filter = jasmine.createSpy('filter').and.callFake(() => true); + const filter = vi.fn(() => true); const hits = sut.rayCast(ray, { searchAllColliders: true, filter }); - expect(filter.calls.argsFor(0)).toEqual([ + expect(filter.mock.calls[0]).toEqual([ { point: ex.vec(75, 0), distance: 75, collider: actor1.collider.get(), body: actor1.body, normal: ex.vec(-1, 0) } ]); - expect(filter.calls.argsFor(1)).toEqual([ + expect(filter.mock.calls[1]).toEqual([ { point: ex.vec(77, 0), distance: 77, collider: actor2.collider.get(), body: actor2.body, normal: ex.vec(-1, 0) } ]); - expect(filter.calls.argsFor(2)).toEqual([ + expect(filter.mock.calls[2]).toEqual([ { point: ex.vec(79, 0), distance: 79, collider: actor3.collider.get(), body: actor3.body, normal: ex.vec(-1, -0) } ]); }); diff --git a/src/spec/SpriteSheetSpec.ts b/src/spec/vitest/SpriteSheetSpec.ts similarity index 81% rename from src/spec/SpriteSheetSpec.ts rename to src/spec/vitest/SpriteSheetSpec.ts index 5796d560..714bbafd 100644 --- a/src/spec/SpriteSheetSpec.ts +++ b/src/spec/vitest/SpriteSheetSpec.ts @@ -1,13 +1,9 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; describe('A SpriteSheet for Graphics', () => { let canvasElement: HTMLCanvasElement; let ctx: ex.ExcaliburGraphicsContext; beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - canvasElement = document.createElement('canvas'); canvasElement.width = 120; canvasElement.height = 120; @@ -19,7 +15,7 @@ describe('A SpriteSheet for Graphics', () => { }); it('can be created with a constructor', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await image.load(); const ss = new ex.SpriteSheet({ @@ -32,7 +28,7 @@ describe('A SpriteSheet for Graphics', () => { }); it('can be created from a list of source views', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await image.load(); const ss = ex.SpriteSheet.fromImageSourceWithSourceViews({ @@ -51,7 +47,7 @@ describe('A SpriteSheet for Graphics', () => { }); it('can be created from a grid', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await image.load(); const ss = ex.SpriteSheet.fromImageSource({ @@ -70,7 +66,7 @@ describe('A SpriteSheet for Graphics', () => { }); it('can be created from a grid with interesting spacing', async () => { - const image = new ex.ImageSource('src/spec/images/SpriteSheetSpec/kenny-cards.png'); + const image = new ex.ImageSource('/src/spec/assets/images/SpriteSheetSpec/kenny-cards.png'); await image.load(); @@ -97,11 +93,11 @@ describe('A SpriteSheet for Graphics', () => { expect(ss.sprites.length).toBe(4 * 14); - await expectAsync(canvasElement).toEqualImage('src/spec/images/SpriteSheetSpec/NewSpriteSpacing.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/SpriteSheetSpec/NewSpriteSpacing.png'); }); it('can be created from with spacing using vectors', async () => { - const image = new ex.ImageSource('src/spec/images/SpriteSheetSpec/kenny-cards.png'); + const image = new ex.ImageSource('/src/spec/assets/images/SpriteSheetSpec/kenny-cards.png'); await image.load(); @@ -128,11 +124,11 @@ describe('A SpriteSheet for Graphics', () => { expect(ss.sprites.length).toBe(4 * 14); - await expectAsync(canvasElement).toEqualImage('src/spec/images/SpriteSheetSpec/NewSpriteSpacing.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/SpriteSheetSpec/NewSpriteSpacing.png'); }); it('can retrieve a sprite by x,y', async () => { - const image = new ex.ImageSource('src/spec/images/SpriteSheetSpec/kenny-cards.png'); + const image = new ex.ImageSource('/src/spec/assets/images/SpriteSheetSpec/kenny-cards.png'); await image.load(); @@ -150,8 +146,8 @@ describe('A SpriteSheet for Graphics', () => { } }); - expect(ss.getSprite(0, 0)).withContext('top left sprite').toEqual(ss.sprites[0]); - expect(ss.getSprite(13, 3)).withContext('bottom right sprite').not.toBeNull(); + expect(ss.getSprite(0, 0), 'top left sprite').toEqual(ss.sprites[0]); + expect(ss.getSprite(13, 3), 'bottom right sprite').not.toBeNull(); expect(() => ss.getSprite(13, 4)).toThrowError('No sprite exists in the SpriteSheet at (13, 4), y: 4 should be between 0 and 3 rows'); @@ -167,7 +163,7 @@ describe('A SpriteSheet for Graphics', () => { }); it('can retrieve a sprite by x,y, with options', async () => { - const image = new ex.ImageSource('src/spec/images/SpriteSheetSpec/kenny-cards.png'); + const image = new ex.ImageSource('/src/spec/assets/images/SpriteSheetSpec/kenny-cards.png'); await image.load(); @@ -214,7 +210,7 @@ describe('A SpriteSheet for Graphics', () => { }); it('can be cloned', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await image.load(); const ss = new ex.SpriteSheet({ diff --git a/src/spec/SpriteSpec.ts b/src/spec/vitest/SpriteSpec.ts similarity index 57% rename from src/spec/SpriteSpec.ts rename to src/spec/vitest/SpriteSpec.ts index af0697f5..7546cb59 100644 --- a/src/spec/SpriteSpec.ts +++ b/src/spec/vitest/SpriteSpec.ts @@ -1,15 +1,9 @@ import * as ex from '@excalibur'; import { Logger, TextureLoader } from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; -import { TestUtils } from './util/TestUtils'; describe('A Sprite Graphic', () => { let canvasElement: HTMLCanvasElement; let ctx: ex.ExcaliburGraphicsContext; - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); beforeEach(() => { TextureLoader.filtering = ex.ImageFiltering.Pixel; @@ -30,7 +24,7 @@ describe('A Sprite Graphic', () => { }); it('can be constructed', () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const sut = new ex.Sprite({ image }); @@ -38,7 +32,7 @@ describe('A Sprite Graphic', () => { }); it('can be cloned', () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const sut = new ex.Sprite({ image, sourceView: { @@ -61,7 +55,7 @@ describe('A Sprite Graphic', () => { }); it('correctly calculates size based on scale', () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const sut = new ex.Sprite({ image, sourceView: { @@ -83,7 +77,7 @@ describe('A Sprite Graphic', () => { }); it('correctly sets size based on scale', () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const sut = new ex.Sprite({ image, sourceView: { @@ -113,23 +107,23 @@ describe('A Sprite Graphic', () => { }); it('can specify a source/dest view of an image with default width and height', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const sut = new ex.Sprite({ image, width: 16, height: 16 }); - expect(sut.width).withContext('Graphic width should be 16').toBe(16); - expect(sut.height).withContext('Graphic height should be 16').toBe(16); + expect(sut.width, 'Graphic width should be 16').toBe(16); + expect(sut.height, 'Graphic height should be 16').toBe(16); expect(sut.sourceView.x).toBe(0); expect(sut.sourceView.y).toBe(0); - expect(sut.sourceView.width).withContext('Graphic sourceView width should be 16').toBe(16); - expect(sut.sourceView.height).withContext('Graphic sourceView height should be 16').toBe(16); - expect(sut.destSize.width).withContext('Graphic destSize width should be 16').toBe(16); - expect(sut.destSize.height).withContext('Graphic destSize height should be 16').toBe(16); - expect(sut.localBounds.width).withContext('Graphic local bounds width should be 16').toBe(16); - expect(sut.localBounds.height).withContext('Graphic local bounds height should be 16').toBe(16); + expect(sut.sourceView.width, 'Graphic sourceView width should be 16').toBe(16); + expect(sut.sourceView.height, 'Graphic sourceView height should be 16').toBe(16); + expect(sut.destSize.width, 'Graphic destSize width should be 16').toBe(16); + expect(sut.destSize.height, 'Graphic destSize height should be 16').toBe(16); + expect(sut.localBounds.width, 'Graphic local bounds width should be 16').toBe(16); + expect(sut.localBounds.height, 'Graphic local bounds height should be 16').toBe(16); await image.load(); await image.ready; @@ -138,11 +132,11 @@ describe('A Sprite Graphic', () => { sut.draw(ctx, 50 - sut.width / 2, 50 - sut.width / 2); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsSpriteSpec/source-view.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsSpriteSpec/source-view.png'); }); it('can draw an sprite image with a tint', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsSpriteSpec/icon.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsSpriteSpec/icon.png'); const sut = image.toSprite(); sut.tint = ex.Color.Green; @@ -153,11 +147,11 @@ describe('A Sprite Graphic', () => { sut.draw(ctx, 0, 0); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsSpriteSpec/icon-tint.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsSpriteSpec/icon-tint.png'); }); it('can specify the width and height of a sprite after construction', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png', false, ex.ImageFiltering.Pixel); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png', false, ex.ImageFiltering.Pixel); const sut = new ex.Sprite({ image, sourceView: { @@ -178,11 +172,11 @@ describe('A Sprite Graphic', () => { sut.draw(ctx, 50 - sut.width / 2, 50 - sut.width / 2); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsSpriteSpec/change-size.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsSpriteSpec/change-size.png'); }); it('can specify the width and height and scale', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png', false, ex.ImageFiltering.Pixel); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png', false, ex.ImageFiltering.Pixel); const sut = new ex.Sprite({ image, sourceView: { @@ -206,11 +200,11 @@ describe('A Sprite Graphic', () => { ctx.flush(); expect(sut.width).toBe(128); expect(sut.height).toBe(128); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsSpriteSpec/change-size-and-scale.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsSpriteSpec/change-size-and-scale.png'); }); it('can specify a source view of an image by default is same dimension as the source', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const sut = new ex.Sprite({ image, sourceView: { @@ -221,16 +215,16 @@ describe('A Sprite Graphic', () => { } }); - expect(sut.width).toBe(16, 'Graphic width should be 16'); - expect(sut.height).toBe(16, 'Graphic height should be 16'); + expect(sut.width, 'Graphic width should be 16').toBe(16); + expect(sut.height, 'Graphic height should be 16').toBe(16); expect(sut.sourceView.x).toBe(0); expect(sut.sourceView.y).toBe(0); - expect(sut.sourceView.width).toBe(16, 'Graphic sourceView width should be 16'); - expect(sut.sourceView.height).toBe(16, 'Graphic sourceView height should be 16'); - expect(sut.destSize.width).toBe(16, 'Graphic destSize width should be 16'); - expect(sut.destSize.height).toBe(16, 'Graphic destSize height should be 16'); - expect(sut.localBounds.width).toBe(16, 'Graphic local bounds width should be 16'); - expect(sut.localBounds.height).toBe(16, 'Graphic local bounds height should be 16'); + expect(sut.sourceView.width, 'Graphic sourceView width should be 16').toBe(16); + expect(sut.sourceView.height, 'Graphic sourceView height should be 16').toBe(16); + expect(sut.destSize.width, 'Graphic destSize width should be 16').toBe(16); + expect(sut.destSize.height, 'Graphic destSize height should be 16').toBe(16); + expect(sut.localBounds.width, 'Graphic local bounds width should be 16').toBe(16); + expect(sut.localBounds.height, 'Graphic local bounds height should be 16').toBe(16); await image.load(); await image.ready; @@ -239,11 +233,11 @@ describe('A Sprite Graphic', () => { sut.draw(ctx, 50 - sut.width / 2, 50 - sut.width / 2); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsSpriteSpec/source-view.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsSpriteSpec/source-view.png'); }); it('can specify a source view of an image and a dest view dimension is destination', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png', false, ex.ImageFiltering.Pixel); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png', false, ex.ImageFiltering.Pixel); const sut = new ex.Sprite({ image, sourceView: { @@ -258,16 +252,16 @@ describe('A Sprite Graphic', () => { } }); - expect(sut.width).toBe(50, 'Graphic width should be 50'); - expect(sut.height).toBe(50, 'Graphic height should be 50'); + expect(sut.width, 'Graphic width should be 50').toBe(50); + expect(sut.height, 'Graphic height should be 50').toBe(50); expect(sut.sourceView.x).toBe(0); expect(sut.sourceView.y).toBe(0); - expect(sut.sourceView.width).toBe(16, 'Graphic sourceView width should be 50'); - expect(sut.sourceView.height).toBe(16, 'Graphic sourceView height should be 50'); - expect(sut.destSize.width).toBe(50, 'Graphic destSize width should be 50'); - expect(sut.destSize.height).toBe(50, 'Graphic destSize height should be 50'); - expect(sut.localBounds.width).toBe(50, 'Graphic local bounds width should be 50'); - expect(sut.localBounds.height).toBe(50, 'Graphic local bounds height should be 50'); + expect(sut.sourceView.width, 'Graphic sourceView width should be 50').toBe(16); + expect(sut.sourceView.height, 'Graphic sourceView height should be 50').toBe(16); + expect(sut.destSize.width, 'Graphic destSize width should be 50').toBe(50); + expect(sut.destSize.height, 'Graphic destSize height should be 50').toBe(50); + expect(sut.localBounds.width, 'Graphic local bounds width should be 50').toBe(50); + expect(sut.localBounds.height, 'Graphic local bounds height should be 50').toBe(50); await image.load(); await image.ready; @@ -276,11 +270,11 @@ describe('A Sprite Graphic', () => { sut.draw(ctx, 50 - sut.width / 2, 50 - sut.width / 2); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsSpriteSpec/dest-size.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsSpriteSpec/dest-size.png'); }); it('can specify only a dest view dimension, infers native size for source view', async () => { - const image = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const image = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const sut = new ex.Sprite({ image, destSize: { @@ -289,16 +283,16 @@ describe('A Sprite Graphic', () => { } }); - expect(sut.width).toBe(100, 'Graphic width should be 100'); - expect(sut.height).toBe(100, 'Graphic height should be 100'); + expect(sut.width, 'Graphic width should be 100').toBe(100); + expect(sut.height, 'Graphic height should be 100').toBe(100); expect(sut.sourceView.x).toBe(0); expect(sut.sourceView.y).toBe(0); - expect(sut.sourceView.width).toBe(0, 'Graphic sourceView width should be 0 before image load'); - expect(sut.sourceView.height).toBe(0, 'Graphic sourceView height should be 0 before image load'); - expect(sut.destSize.width).toBe(100, 'Graphic destSize width should be 100'); - expect(sut.destSize.height).toBe(100, 'Graphic destSize height should be 100'); - expect(sut.localBounds.width).toBe(100, 'Graphic local bounds width should be 100'); - expect(sut.localBounds.height).toBe(100, 'Graphic local bounds height should be 100'); + expect(sut.sourceView.width, 'Graphic sourceView width should be 0 before image load').toBe(0); + expect(sut.sourceView.height, 'Graphic sourceView height should be 0 before image load').toBe(0); + expect(sut.destSize.width, 'Graphic destSize width should be 100').toBe(100); + expect(sut.destSize.height, 'Graphic destSize height should be 100').toBe(100); + expect(sut.localBounds.width, 'Graphic local bounds width should be 100').toBe(100); + expect(sut.localBounds.height, 'Graphic local bounds height should be 100').toBe(100); await image.load(); await image.ready; @@ -310,12 +304,12 @@ describe('A Sprite Graphic', () => { sut.draw(ctx, 50 - sut.width / 2, 50 - sut.width / 2); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsSpriteSpec/dest-view.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsSpriteSpec/dest-view.png'); }); it('will log one warning if the imagesource is not loaded', () => { const logger = Logger.getInstance(); - spyOn(logger, 'warnOnce'); + vi.spyOn(logger, 'warnOnce'); const image = new ex.ImageSource('path/to/non/existing/image'); const sut = image.toSprite(); diff --git a/src/spec/StateMachineSpec.ts b/src/spec/vitest/StateMachineSpec.ts similarity index 92% rename from src/spec/StateMachineSpec.ts rename to src/spec/vitest/StateMachineSpec.ts index c657b67d..66314004 100644 --- a/src/spec/StateMachineSpec.ts +++ b/src/spec/vitest/StateMachineSpec.ts @@ -76,8 +76,8 @@ describe('A StateMachine', () => { }); it('can prevent transition onEnter', () => { - const enterSpy = jasmine.createSpy('enter').and.returnValue(false); - const exitSpy = jasmine.createSpy('exit').and.returnValue(false); + const enterSpy = vi.fn(() => false); + const exitSpy = vi.fn(() => false); const machine = ex.StateMachine.create({ start: 'PING', states: { @@ -93,16 +93,16 @@ describe('A StateMachine', () => { }); expect(machine.go('PONG')).toBe(false); - enterSpy.and.returnValue(true); + enterSpy.mockImplementation(() => true); expect(machine.go('PONG')).toBe(true); expect(machine.go('PING')).toBe(false); - exitSpy.and.returnValue(true); + exitSpy.mockImplementation(() => true); expect(machine.go('PING')).toBe(true); }); it('can pass data to states', () => { - const enterSpy = jasmine.createSpy('enter').and.returnValue(true); - const exitSpy = jasmine.createSpy('exit').and.returnValue(true); + const enterSpy = vi.fn(() => true); + const exitSpy = vi.fn(() => true); const machine = ex.StateMachine.create( { start: 'PING', @@ -129,7 +129,7 @@ describe('A StateMachine', () => { }); it('can update the current state', () => { - const updateSpy = jasmine.createSpy('update').and.returnValue(true); + const updateSpy = vi.fn(() => true); const machine = ex.StateMachine.create( { start: 'PING', diff --git a/src/spec/SystemManagerSpec.ts b/src/spec/vitest/SystemManagerSpec.ts similarity index 95% rename from src/spec/SystemManagerSpec.ts rename to src/spec/vitest/SystemManagerSpec.ts index ea23b25a..9b897e33 100644 --- a/src/spec/SystemManagerSpec.ts +++ b/src/spec/vitest/SystemManagerSpec.ts @@ -106,9 +106,9 @@ describe('A SystemManager', () => { const system = new FakeSystemPriority2(world, 'System3', [FakeComponentC], SystemType.Update); system.preupdate = () => {}; // eslint-disable-line @typescript-eslint/no-empty-function system.postupdate = () => {}; // eslint-disable-line @typescript-eslint/no-empty-function - spyOn(system, 'preupdate'); - spyOn(system, 'postupdate'); - spyOn(system, 'update'); + vi.spyOn(system, 'preupdate'); + vi.spyOn(system, 'postupdate'); + vi.spyOn(system, 'update'); sm.addSystem(system); sm.updateSystems(SystemType.Update, null, 10); expect(system.preupdate).toHaveBeenCalledTimes(1); @@ -122,7 +122,7 @@ describe('A SystemManager', () => { const qm = world.queryManager; const em = world.entityManager; const system = new FakeSystemPriority2(world, 'System3', [FakeComponentA, FakeComponentC], SystemType.Update); - spyOn(system, 'update').and.callThrough(); + vi.spyOn(system, 'update'); sm.addSystem(system); const e1 = new ex.Entity(); @@ -154,10 +154,10 @@ describe('A SystemManager', () => { const qm = world.queryManager; const em = world.entityManager; const system1 = new FakeSystemPriority2(world, 'System1', [FakeComponentA, FakeComponentC], SystemType.Update); - spyOn(system1, 'update').and.callThrough(); + vi.spyOn(system1, 'update'); sm.addSystem(system1); const system2 = new FakeSystemPriority2(world, 'System1', [FakeComponentA, FakeComponentC], SystemType.Draw); - spyOn(system2, 'update').and.callThrough(); + vi.spyOn(system2, 'update'); sm.addSystem(system2); sm.updateSystems(SystemType.Draw, null, 10); diff --git a/src/spec/TagQuerySpec.ts b/src/spec/vitest/TagQuerySpec.ts similarity index 63% rename from src/spec/TagQuerySpec.ts rename to src/spec/vitest/TagQuerySpec.ts index bb706e49..940fcb63 100644 --- a/src/spec/TagQuerySpec.ts +++ b/src/spec/vitest/TagQuerySpec.ts @@ -23,8 +23,8 @@ describe('A tag query', () => { const entity2 = new ex.Entity(); entity2.addTag('A'); - expect(entity1.hasAllTags(queryAB.requiredTags)).toBe(true, 'entity1 should match has both components A, B'); - expect(entity2.hasAllTags(queryAB.requiredTags)).toBe(false, 'entity2 should not match, only has 1 component A'); + expect(entity1.hasAllTags(queryAB.requiredTags), 'entity1 should match has both components A, B').toBe(true); + expect(entity2.hasAllTags(queryAB.requiredTags), 'entity2 should not match, only has 1 component A').toBe(false); }); it('can only add entities that match', () => { @@ -62,32 +62,34 @@ describe('A tag query', () => { expect(queryAB.getEntities()).toEqual([]); }); - it('notifies observers of when something is added to the query', (done) => { - const queryAB = new ex.TagQuery(['A', 'B']); - const entity1 = new ex.Entity(); - entity1.addTag('A'); - entity1.addTag('B'); - - queryAB.entityAdded$.subscribe((e) => { - expect(e).toBe(entity1); - done(); - }); - - queryAB.checkAndAdd(entity1); - }); - - it('notifies observers of when something is added to the query', (done) => { - const queryAB = new ex.TagQuery(['A', 'B']); - const entity1 = new ex.Entity(); - entity1.addTag('A'); - entity1.addTag('B'); - queryAB.checkAndAdd(entity1); - - queryAB.entityRemoved$.subscribe((e) => { - expect(e).toBe(entity1); - done(); - }); - - queryAB.removeEntity(entity1); - }); + it('notifies observers of when something is added to the query', () => + new Promise((done) => { + const queryAB = new ex.TagQuery(['A', 'B']); + const entity1 = new ex.Entity(); + entity1.addTag('A'); + entity1.addTag('B'); + + queryAB.entityAdded$.subscribe((e) => { + expect(e).toBe(entity1); + done(); + }); + + queryAB.checkAndAdd(entity1); + })); + + it('notifies observers of when something is added to the query', () => + new Promise((done) => { + const queryAB = new ex.TagQuery(['A', 'B']); + const entity1 = new ex.Entity(); + entity1.addTag('A'); + entity1.addTag('B'); + queryAB.checkAndAdd(entity1); + + queryAB.entityRemoved$.subscribe((e) => { + expect(e).toBe(entity1); + done(); + }); + + queryAB.removeEntity(entity1); + })); }); diff --git a/src/spec/TextSpec.ts b/src/spec/vitest/TextSpec.ts similarity index 71% rename from src/spec/TextSpec.ts rename to src/spec/vitest/TextSpec.ts index 4389e21d..be73905c 100644 --- a/src/spec/TextSpec.ts +++ b/src/spec/vitest/TextSpec.ts @@ -1,28 +1,7 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; -import { delay } from '../engine/Util/Util'; +import { delay } from '../../engine/Util/Util'; +import { inject } from 'vitest'; -/** - * - */ -async function runOnWindows(ctx: () => Promise): Promise { - if (navigator.platform === 'Win32' || navigator.platform === 'Win64') { - await ctx(); - return true; - } - return false; -} - -/** - * - */ -async function runOnLinux(ctx: () => Promise): Promise { - if (navigator.platform.includes('Linux')) { - await ctx(); - return true; - } - return false; -} declare global { interface Document { fonts: FontFaceSet; @@ -67,20 +46,59 @@ export function waitForFontLoad(font: string, timeout = 2000, interval = 100): P }); } -describe('A Text Graphic', () => { - beforeEach(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); +const isWindows = inject('platform') === 'win32'; +const isLinux = inject('platform') === 'linux'; +const isChromium = inject('browser') === 'chromium'; + +/** + * for now, only run the Text tests on Windows + Chromium because + * there are too many subtle differences in rendering text + * across browser/os combos. + * + * Screenshot assertions will need to be split apart by platform + browser. They + * currently only work on Windows + Chromium. If you add a new platform+browser combo, you + * will need to create those screenshots. There are Linux ones left over from before but I am + * not sure if they are the correct ones, as we had issues getting them to pass + * on any Linux+Chrome/Chromium combo after migrating from Karma. + * + * Notes for if we do enable other platforms: + * + * Linux (Chrome): + * - There seems to be +1 height difference per-line in text height. This can + * be accounted for by asserting `expect(height).toBeCloseTo(expectedHeight, -numberOfLines)` + * This could be a legit bug + * + * - Text rendering on Chrome between GitHub Linux vs local Linux are different somehow. Tried + * all kinds of flags, but text quality differs quite a bit. Can be fixed to pass + * some linux screenshots by setting quality of the font to 3, or in one case 10. + */ +describe.runIf(isWindows && isChromium)('A Text Graphic', () => { + let canvasElement: HTMLCanvasElement; + let ctx: ex.ExcaliburGraphicsContext2DCanvas | ex.ExcaliburGraphicsContextWebGL; + beforeAll(async () => { const fontface = document.createElement('link'); - fontface.href = 'src/spec/images/GraphicsTextSpec/fonts.css'; + fontface.href = '/src/spec/assets/images/GraphicsTextSpec/fonts.css'; fontface.rel = 'stylesheet'; document.head.appendChild(fontface); await waitForFontLoad('18px Open Sans'); await waitForFontLoad('bold 18px Open Sans'); await waitForFontLoad('italic bold 18px Open Sans'); await waitForFontLoad('italic 18px Open Sans'); + await document.fonts.ready; + }); + + beforeEach(() => { + if (canvasElement) { + canvasElement.remove(); + } + + canvasElement = document.createElement('canvas'); + canvasElement.width = 100; + canvasElement.height = 100; + document.body.append(canvasElement); + ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); + ctx.clear(); }); it('exists', () => { @@ -138,20 +156,9 @@ describe('A Text Graphic', () => { }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - ctx.clear(); sut.draw(ctx, 10, 50); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/text.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/text-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/text.png'); }); it('can draw multiple lines of text (font)', async () => { @@ -161,30 +168,21 @@ describe('A Text Graphic', () => { font: new ex.Font({ family: 'Open Sans', size: 18, + lineHeight: 18, quality: 1, padding: 0, baseAlign: ex.BaseAlign.Alphabetic }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - ctx.clear(); sut.draw(ctx, 10, 20); expect(sut.width).toBeCloseTo(69.8, -1); - expect(sut.height).toBeCloseTo(18 * 3, 0); expect(sut.localBounds.width).toBeCloseTo(69.8, -1); + expect(sut.height).toBeCloseTo(18 * 3, 0); expect(sut.localBounds.height).toBeCloseTo(18 * 3, 0); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/multi-text.png'); - }); - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/multi-text-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/multi-text-win.png'); }); it('can have width and height', () => { @@ -214,6 +212,7 @@ describe('A Text Graphic', () => { }); const bounds = sut.measureText('some extra long text that we want to measure'); + expect(bounds.width).toBeCloseTo(386.9, -1); expect(bounds.height).toBeCloseTo(18, 0); }); @@ -231,23 +230,11 @@ describe('A Text Graphic', () => { }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.flipHorizontal = true; sut.flipVertical = true; sut.draw(ctx, 10, 50); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/flipped.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/flipped-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/flipped.png'); }); it('can align fonts and reuse a font', async () => { @@ -263,23 +250,11 @@ describe('A Text Graphic', () => { }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.draw(ctx, 10, 20); sut.draw(ctx, 10, 40); sut.draw(ctx, 10, 60); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/font-alignment.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/font-alignment-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/font-alignment.png'); }); it('can rotate text around the middle', async () => { @@ -295,22 +270,10 @@ describe('A Text Graphic', () => { }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.rotation = Math.PI / 2; sut.draw(ctx, 10, 50); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/rotated.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/rotated-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/rotated.png'); }); it('can rotate text around the left', async () => { @@ -326,23 +289,11 @@ describe('A Text Graphic', () => { }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.origin = ex.Vector.Zero; sut.rotation = Math.PI / 2; sut.draw(ctx, 10, 50); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/rotated-left.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/rotated-left-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/rotated-left.png'); }); it('can rotate text around the right', async () => { @@ -358,23 +309,11 @@ describe('A Text Graphic', () => { }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.origin = ex.vec(sut.width, 0); sut.rotation = -Math.PI / 2; sut.draw(ctx, 10, 50); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/rotated-right.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/rotated-right-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/rotated-right.png'); }); it('can be bold', async () => { @@ -391,21 +330,9 @@ describe('A Text Graphic', () => { }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.draw(ctx, 10, 50); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/bold.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/bold-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/bold-win.png'); }); it('can be italic', async () => { @@ -422,21 +349,9 @@ describe('A Text Graphic', () => { }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.draw(ctx, 10, 50); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/italic.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/italic-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/italic.png'); }); it('can have line height', async () => { @@ -452,21 +367,9 @@ describe('A Text Graphic', () => { }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.draw(ctx, 10, 10); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/line-height.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/line-height-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/line-height-win.png'); }); it('can have a shadow', async () => { @@ -487,21 +390,9 @@ describe('A Text Graphic', () => { }) }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.draw(ctx, 10, 50); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/shadow.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/shadow-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/shadow.png'); }); it('can force clear text bitmap cache', () => { @@ -529,12 +420,6 @@ describe('A Text Graphic', () => { font: sut }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); text.draw(ctx, 10, 50); text2.draw(ctx, 10, 50); @@ -568,12 +453,6 @@ describe('A Text Graphic', () => { font: sut }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); text.draw(ctx, 10, 50); text2.draw(ctx, 10, 50); expect(ex.FontCache.cacheSize).toBe(2); @@ -609,12 +488,6 @@ describe('A Text Graphic', () => { font: sut }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); text.draw(ctx, 10, 50); text2.draw(ctx, 10, 50); expect(ex.FontCache.cacheSize).toBe(2); @@ -650,12 +523,6 @@ describe('A Text Graphic', () => { font: sut }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); text.draw(ctx, 10, 50); text2.draw(ctx, 10, 50); expect(ex.FontCache.cacheSize).toBe(2); @@ -679,23 +546,11 @@ describe('A Text Graphic', () => { font: sut }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); text1.draw(ctx, 10, 20); text2.draw(ctx, 10, 40); ctx.flush(); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/reuse-font.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/reuse-font-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/reuse-font-win.png'); }); it('can get text dimension before drawing', () => { @@ -821,22 +676,18 @@ describe('A Text Graphic', () => { baseAlign: ex.BaseAlign.Alphabetic }) }); - - const canvasElement = document.createElement('canvas'); + canvasElement.remove(); + canvasElement = document.createElement('canvas'); canvasElement.width = 1000; canvasElement.height = 1000; - const ctx = new ex.ExcaliburGraphicsContextWebGL({ canvasElement, snapToPixel: false }); + + ctx = new ex.ExcaliburGraphicsContextWebGL({ canvasElement, snapToPixel: false }); ctx.clear(); + sut.draw(ctx, 10, 50); ctx.flush(); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/long-text.png'); - }); - - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/long-text-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/long-text.png'); }); it('can create lots of text without crash', () => { @@ -853,8 +704,22 @@ describe('A Text Graphic', () => { }); describe('with a SpriteFont', () => { + beforeEach(() => { + if (canvasElement) { + canvasElement.remove(); + } + + canvasElement.remove(); + canvasElement = document.createElement('canvas'); + canvasElement.width = 200; + canvasElement.height = 100; + document.body.append(canvasElement); + ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); + ctx.clear(); + }); + it('can be cloned', () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); const spriteFontSheet = ex.SpriteSheet.fromImageSource({ image: spriteFontImage, @@ -884,7 +749,7 @@ describe('A Text Graphic', () => { }); it('can specify a spritefont', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); @@ -910,19 +775,13 @@ describe('A Text Graphic', () => { font: spriteFont }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 200; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.draw(ctx, 0, 50); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/spritefont-text.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/spritefont-text.png'); }); it('can scale a spritefont', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); @@ -949,19 +808,13 @@ describe('A Text Graphic', () => { font: spriteFont }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 200; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.draw(ctx, 0, 50); expect(spriteFont.measureText('some test')).toEqual(ex.BoundingBox.fromDimension((16 - 5) * 9 * 3, 16 * 3, ex.vec(0, 0))); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/spritefont-scaled.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/spritefont-scaled.png'); }); it('can have a custom lineHeight', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); @@ -988,23 +841,17 @@ describe('A Text Graphic', () => { font: spriteFont }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 200; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - - ctx.clear(); sut.draw(ctx, 0, 0); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/sprite-font-line-height.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/sprite-font-line-height.png'); }); }); it('will log warnings when there are issues', async () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warnOnce'); + const warnSpy = vi.spyOn(logger, 'warnOnce'); - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); @@ -1030,31 +877,26 @@ describe('A Text Graphic', () => { font: spriteFont }); - const canvasElement = document.createElement('canvas'); - canvasElement.width = 200; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - sut.text = '~'; sut.draw(ctx, 0, 0); - const warnSpy = logger.warnOnce as jasmine.Spy; - expect(warnSpy.calls.argsFor(0)).toEqual([ + + expect(warnSpy.mock.calls[0]).toEqual([ "SpriteFont - Cannot find letter '~' in configured alphabet '0123456789abcdefghijklmnopqrstuvwxyz,!'&.\"?- '." ]); - expect(warnSpy.calls.argsFor(1)).toEqual([ + expect(warnSpy.mock.calls[1]).toEqual([ 'There maybe be more issues in the SpriteFont configuration. No additional warnings will be logged.' ]); - warnSpy.calls.reset(); + warnSpy.mockReset(); sut.text = '?'; sut.draw(ctx, 0, 0); - expect(warnSpy.calls.argsFor(0)).toEqual(["SpriteFont - Cannot find sprite for '?' at index '42' in configured SpriteSheet"]); - expect(warnSpy.calls.argsFor(1)).toEqual([ + expect(warnSpy.mock.calls[0]).toEqual(["SpriteFont - Cannot find sprite for '?' at index '42' in configured SpriteSheet"]); + expect(warnSpy.mock.calls[1]).toEqual([ 'There maybe be more issues in the SpriteFont configuration. No additional warnings will be logged.' ]); }); it('can do some simple shadowing', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); @@ -1083,19 +925,15 @@ describe('A Text Graphic', () => { font: spriteFont }); - const canvasElement = document.createElement('canvas'); canvasElement.width = 200; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - ctx.clear(); sut.draw(ctx, 0, 50); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/spritefont-shadow.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/spritefont-shadow.png'); }); it('can rotate spritefont text around the middle', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); const spriteFontSheet = ex.SpriteSheet.fromImageSource({ image: spriteFontImage, @@ -1118,20 +956,17 @@ describe('A Text Graphic', () => { font: spriteFont }); - const canvasElement = document.createElement('canvas'); canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - ctx.clear(); + sut.rotation = Math.PI / 2; sut.draw(ctx, 10, 40); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/rotated-spritefont.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/rotated-spritefont.png'); }); it('can align fonts and reuse a spritefont', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); const spriteFontSheet = ex.SpriteSheet.fromImageSource({ image: spriteFontImage, @@ -1154,21 +989,18 @@ describe('A Text Graphic', () => { font: spriteFont }); - const canvasElement = document.createElement('canvas'); canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); - ctx.clear(); + sut.draw(ctx, 0, 20); sut.draw(ctx, 0, 40); sut.draw(ctx, 0, 60); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/spritefont-alignment.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/spritefont-alignment.png'); }); it('can draw multiple lines of text (spritefont)', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); const spriteFontSheet = ex.SpriteSheet.fromImageSource({ image: spriteFontImage, @@ -1192,11 +1024,9 @@ describe('A Text Graphic', () => { font: spriteFont }); - const canvasElement = document.createElement('canvas'); canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); ctx.clear(); + sut.draw(ctx, 10, 20); expect(sut.width).toBeCloseTo(80); @@ -1204,11 +1034,11 @@ describe('A Text Graphic', () => { expect(sut.localBounds.width).toBeCloseTo(80); expect(sut.localBounds.height).toBeCloseTo(48); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/multi-text-spritefont.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/multi-text-spritefont.png'); }); it('can measure text for a spritefont', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); const spriteFontSheet = ex.SpriteSheet.fromImageSource({ image: spriteFontImage, @@ -1233,7 +1063,7 @@ describe('A Text Graphic', () => { }); it('can word wrap text for a spritefont', async () => { - const spriteFontImage = new ex.ImageSource('src/spec/images/GraphicsTextSpec/spritefont.png'); + const spriteFontImage = new ex.ImageSource('/src/spec/assets/images/GraphicsTextSpec/spritefont.png'); await spriteFontImage.load(); const spriteFontSheet = ex.SpriteSheet.fromImageSource({ image: spriteFontImage, @@ -1259,14 +1089,12 @@ describe('A Text Graphic', () => { maxWidth: 100 }); - const canvasElement = document.createElement('canvas'); canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); ctx.clear(); + sut.draw(ctx, 0, 0); - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/sprite-font-text-wrap.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/sprite-font-text-wrap.png'); }); it('can word wrap text for a normal font', async () => { @@ -1283,21 +1111,15 @@ describe('A Text Graphic', () => { maxWidth: 100 }); - const canvasElement = document.createElement('canvas'); canvasElement.width = 100; - canvasElement.height = 100; - const ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement }); + ctx = new ex.ExcaliburGraphicsContext2DCanvas({ canvasElement, multiSampleAntialiasing: false }); ctx.clear(); text1.draw(ctx, 0, 18); ctx.flush(); - await runOnWindows(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/font-text-wrap.png'); - }); + await new Promise((r) => setTimeout(r, 1000)); - await runOnLinux(async () => { - await expectAsync(canvasElement).toEqualImage('src/spec/images/GraphicsTextSpec/font-text-wrap-linux.png'); - }); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/GraphicsTextSpec/font-text-wrap-win.png'); }); }); diff --git a/src/spec/TileMapSpec.ts b/src/spec/vitest/TileMapSpec.ts similarity index 91% rename from src/spec/TileMapSpec.ts rename to src/spec/vitest/TileMapSpec.ts index 82c83362..3183d6fc 100644 --- a/src/spec/TileMapSpec.ts +++ b/src/spec/vitest/TileMapSpec.ts @@ -1,8 +1,7 @@ -import { ExcaliburMatchers, ensureImagesLoaded, ExcaliburAsyncMatchers } from 'excalibur-jasmine'; import * as ex from '@excalibur'; import { TestUtils } from './util/TestUtils'; import { BodyComponent } from '@excalibur'; -import { ColliderComponent } from '../engine/Collision/ColliderComponent'; +import { ColliderComponent } from '../../engine/Collision/ColliderComponent'; const drawWithTransform = (ctx: ex.ExcaliburGraphicsContext, tm: ex.TileMap, elapsedMs: number = 1) => { ctx.save(); @@ -18,8 +17,6 @@ describe('A TileMap', () => { let scene: ex.Scene; let texture: ex.ImageSource; beforeEach(async () => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); engine = TestUtils.engine({ width: 800, height: 200 @@ -28,7 +25,7 @@ describe('A TileMap', () => { engine.addScene('root', scene); await TestUtils.runToReady(engine); const clock = engine.clock as ex.TestClock; - texture = new ex.ImageSource('src/spec/images/TileMapSpec/Blocks.png'); + texture = new ex.ImageSource('/src/spec/assets/images/TileMapSpec/Blocks.png'); await texture.load(); clock.step(1); }); @@ -213,14 +210,14 @@ describe('A TileMap', () => { drawWithTransform(engine.graphicsContext, tm, 99); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/TileMapSpec/TileMapGraphicSquare.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/TileMapSpec/TileMapGraphicSquare.png'); tm.update(engine, 99); drawWithTransform(engine.graphicsContext, tm, 99); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/TileMapSpec/TileMapGraphicCircle.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/TileMapSpec/TileMapGraphicCircle.png'); }); it('should draw the correct proportions', async () => { @@ -250,7 +247,7 @@ describe('A TileMap', () => { drawWithTransform(engine.graphicsContext, tm, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/TileMapSpec/TileMap.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/TileMapSpec/TileMap.png'); }); it('should draw from the bottom', async () => { @@ -276,7 +273,7 @@ describe('A TileMap', () => { drawWithTransform(engine.graphicsContext, tm, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/TileMapSpec/tilemap-from-bottom.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/TileMapSpec/tilemap-from-bottom.png'); }); it('should draw from the top', async () => { @@ -303,7 +300,7 @@ describe('A TileMap', () => { drawWithTransform(engine.graphicsContext, tm, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/TileMapSpec/tilemap-from-top.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/TileMapSpec/tilemap-from-top.png'); }); it('should handle offscreen culling correctly with negative coords', async () => { @@ -335,7 +332,7 @@ describe('A TileMap', () => { drawWithTransform(engine.graphicsContext, tm, 100); engine.graphicsContext.flush(); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/TileMapSpec/TileMapCulling.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/TileMapSpec/TileMapCulling.png'); }); it('should handle offscreen culling correctly when scaled', async () => { @@ -387,7 +384,7 @@ describe('A TileMap', () => { }) ); - await expectAsync(engine.canvas).toEqualImage('src/spec/images/TileMapSpec/tilemap-scaled.png'); + await expect(engine.canvas).toEqualImage('/src/spec/assets/images/TileMapSpec/tilemap-scaled.png'); }); it('can return a tile by xy coord', () => { @@ -443,7 +440,7 @@ describe('A TileMap', () => { }); it('can add and remove graphics on a tile', async () => { - const image = new ex.ImageSource('src/spec/images/TileMapSpec/Blocks.png'); + const image = new ex.ImageSource('/src/spec/assets/images/TileMapSpec/Blocks.png'); await image.load(); const sprite = image.toSprite(); const sut = new ex.TileMap({ @@ -553,10 +550,10 @@ describe('A TileMap', () => { const tile = sut.getTile(0, 0); - const pointerdown = jasmine.createSpy('pointerdown'); - const pointerup = jasmine.createSpy('pointerup'); - const pointermove = jasmine.createSpy('pointermove'); - const pointercancel = jasmine.createSpy('pointercancel'); + const pointerdown = vi.fn(); + const pointerup = vi.fn(); + const pointermove = vi.fn(); + const pointercancel = vi.fn(); tile.on('pointerdown', pointerdown); tile.on('pointerup', pointerup); tile.on('pointermove', pointermove); diff --git a/src/spec/TiledAnimationSpec.ts b/src/spec/vitest/TiledAnimationSpec.ts similarity index 75% rename from src/spec/TiledAnimationSpec.ts rename to src/spec/vitest/TiledAnimationSpec.ts index 77b2caaa..1b508a74 100644 --- a/src/spec/TiledAnimationSpec.ts +++ b/src/spec/vitest/TiledAnimationSpec.ts @@ -1,13 +1,8 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; describe('A TiledAnimation', () => { let canvasElement: HTMLCanvasElement; let ctx: ex.ExcaliburGraphicsContext; - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); beforeEach(() => { ex.TextureLoader.filtering = ex.ImageFiltering.Pixel; @@ -28,7 +23,7 @@ describe('A TiledAnimation', () => { }); it('can be created', async () => { - const cardsImage = new ex.ImageSource('src/spec/images/TiledAnimationSpec/kenny-cards.png'); + const cardsImage = new ex.ImageSource('/src/spec/assets/images/TiledAnimationSpec/kenny-cards.png'); await cardsImage.load(); const cardSpriteSheet = ex.SpriteSheet.fromImageSource({ image: cardsImage, @@ -61,13 +56,13 @@ describe('A TiledAnimation', () => { sut.draw(ctx, 20, 20); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/TiledAnimationSpec/tiled.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/TiledAnimationSpec/tiled.png'); sut.tick(200); ctx.clear(); sut.draw(ctx, 20, 20); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/TiledAnimationSpec/tiled-2.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/TiledAnimationSpec/tiled-2.png'); }); }); diff --git a/src/spec/TiledSpriteSpec.ts b/src/spec/vitest/TiledSpriteSpec.ts similarity index 71% rename from src/spec/TiledSpriteSpec.ts rename to src/spec/vitest/TiledSpriteSpec.ts index 707ad20b..65dce9ee 100644 --- a/src/spec/TiledSpriteSpec.ts +++ b/src/spec/vitest/TiledSpriteSpec.ts @@ -1,13 +1,8 @@ import * as ex from '@excalibur'; -import { ExcaliburAsyncMatchers, ExcaliburMatchers } from 'excalibur-jasmine'; describe('A TiledSprite', () => { let canvasElement: HTMLCanvasElement; let ctx: ex.ExcaliburGraphicsContext; - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - jasmine.addAsyncMatchers(ExcaliburAsyncMatchers); - }); beforeEach(() => { ex.TextureLoader.filtering = ex.ImageFiltering.Pixel; @@ -28,7 +23,7 @@ describe('A TiledSprite', () => { }); it('can be created after load', async () => { - const image = new ex.ImageSource('src/spec/images/TiledSpriteSpec/ground.png'); + const image = new ex.ImageSource('/src/spec/assets/images/TiledSpriteSpec/ground.png'); await image.load(); const sut = new ex.TiledSprite({ @@ -46,11 +41,11 @@ describe('A TiledSprite', () => { sut.draw(ctx, 0, 20); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/TiledSpriteSpec/tiled.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/TiledSpriteSpec/tiled.png'); }); it('can be created before load', async () => { - const image = new ex.ImageSource('src/spec/images/TiledSpriteSpec/ground.png'); + const image = new ex.ImageSource('/src/spec/assets/images/TiledSpriteSpec/ground.png'); const sut = new ex.TiledSprite({ image, @@ -68,11 +63,11 @@ describe('A TiledSprite', () => { sut.draw(ctx, 0, 20); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/TiledSpriteSpec/tiled.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/TiledSpriteSpec/tiled.png'); }); it('can be from a sprite', async () => { - const image = new ex.ImageSource('src/spec/images/TiledSpriteSpec/ground.png'); + const image = new ex.ImageSource('/src/spec/assets/images/TiledSpriteSpec/ground.png'); const sourceSprite = image.toSprite(); sourceSprite.width = 400; sourceSprite.height = 400; @@ -89,11 +84,11 @@ describe('A TiledSprite', () => { sut.draw(ctx, 0, 20); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/TiledSpriteSpec/tiled.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/TiledSpriteSpec/tiled.png'); }); it('can grab a tiled sprite from a sprite sheet', async () => { - const cardsImage = new ex.ImageSource('src/spec/images/TiledAnimationSpec/kenny-cards.png'); + const cardsImage = new ex.ImageSource('/src/spec/assets/images/TiledAnimationSpec/kenny-cards.png'); await cardsImage.load(); const cardSpriteSheet = ex.SpriteSheet.fromImageSource({ image: cardsImage, @@ -120,6 +115,6 @@ describe('A TiledSprite', () => { sut.draw(ctx, 0, 0); ctx.flush(); - await expectAsync(canvasElement).toEqualImage('src/spec/images/TiledSpriteSpec/from-spritesheet.png'); + await expect(canvasElement).toEqualImage('/src/spec/assets/images/TiledSpriteSpec/from-spritesheet.png'); }); }); diff --git a/src/spec/TimerSpec.ts b/src/spec/vitest/TimerSpec.ts similarity index 92% rename from src/spec/TimerSpec.ts rename to src/spec/vitest/TimerSpec.ts index e81d0718..1c6ee345 100644 --- a/src/spec/TimerSpec.ts +++ b/src/spec/vitest/TimerSpec.ts @@ -65,7 +65,7 @@ describe('A Timer', () => { }); it('can be paused and resumed', () => { - const timerSpy = jasmine.createSpy('timer'); + const timerSpy = vi.fn(); const sut = new ex.Timer({ interval: 42, fcn: timerSpy @@ -94,8 +94,8 @@ describe('A Timer', () => { }); it('does not warn when added to a scene', () => { - const warnSpy = spyOn(ex.Logger.getInstance(), 'warn'); - const timerSpy = jasmine.createSpy('timer'); + const warnSpy = vi.spyOn(ex.Logger.getInstance(), 'warn'); + const timerSpy = vi.fn(); const sut = new ex.Timer({ interval: 42, fcn: timerSpy @@ -107,7 +107,7 @@ describe('A Timer', () => { }); it('can be stopped and started', () => { - const timerSpy = jasmine.createSpy('timer'); + const timerSpy = vi.fn(); const sut = new ex.Timer({ interval: 42, fcn: timerSpy @@ -133,7 +133,7 @@ describe('A Timer', () => { }); it('fires after a specific interval', () => { - const timerSpy = jasmine.createSpy('timer'); + const timerSpy = vi.fn(); const sut = new ex.Timer({ interval: 500, fcn: timerSpy @@ -146,7 +146,7 @@ describe('A Timer', () => { }); it('can repeat itself indefinitely at a specified interval', () => { - const timerSpy = jasmine.createSpy('timer'); + const timerSpy = vi.fn(); timer = new ex.Timer({ interval: 500, fcn: timerSpy, @@ -162,7 +162,7 @@ describe('A Timer', () => { }); it('can repeat itself a finite number of times', () => { - const timerSpy = jasmine.createSpy('timer'); + const timerSpy = vi.fn(); timer = new ex.Timer({ interval: 500, fcn: timerSpy, @@ -188,7 +188,7 @@ describe('A Timer', () => { }); it('can be canceled', () => { - const timerSpy = jasmine.createSpy('timer'); + const timerSpy = vi.fn(); timer = new ex.Timer({ interval: 500, fcn: timerSpy, @@ -225,7 +225,7 @@ describe('A Timer', () => { }); it('has no completed state when running forever', () => { - const timerSpy = jasmine.createSpy('timer'); + const timerSpy = vi.fn(); timer = new ex.Timer({ interval: 500, fcn: timerSpy, @@ -251,7 +251,7 @@ describe('A Timer', () => { }); it('can be reset at the same interval', () => { - const timerSpy = jasmine.createSpy('timer'); + const timerSpy = vi.fn(); // non-repeating timer timer = new ex.Timer({ interval: 500, @@ -505,7 +505,7 @@ describe('A Timer', () => { }); scene.add(timer); timer.start(); - expect(timer.complete).toBeFalse(); + expect(timer.complete).toBe(false); scene.update(engine, 100); expect(timer.interval).toBeGreaterThanOrEqual(100); expect(timer.interval).toBeLessThanOrEqual(300); @@ -525,8 +525,9 @@ describe('A Timer', () => { }); it('an Random instance can be passed, if specified', () => { - const randomMock = jasmine.createSpyObj('Random', ['integer']); - randomMock.integer.and.returnValue(11); + const randomMock = { + integer: vi.fn(() => 11) + } as any; const timer = new ex.Timer({ interval: 500, repeats: false, randomRange: [0, 100], random: randomMock }); scene.add(timer); timer.start(); @@ -535,8 +536,14 @@ describe('A Timer', () => { }); it('has a randomly set interval with repetition and Random instance passed', () => { - const randomMock = jasmine.createSpyObj('Random', ['integer']); - randomMock.integer.and.returnValues(11, 5, 2, 99); + const randomMock = { + integer: vi + .fn() + .mockImplementationOnce(() => 11) + .mockImplementationOnce(() => 5) + .mockImplementationOnce(() => 2) + .mockImplementationOnce(() => 99) + } as any; const timer = new ex.Timer({ interval: 500, repeats: true, randomRange: [0, 100], random: randomMock }); scene.add(timer); timer.start(); @@ -550,8 +557,13 @@ describe('A Timer', () => { }); it('is random after reset with Random instance passed and no repeats are added', () => { - const randomMock = jasmine.createSpyObj('Random', ['integer']); - randomMock.integer.and.returnValues(11, 5); + const randomMock = { + integer: vi + .fn() + .mockImplementationOnce(() => 11) + .mockImplementationOnce(() => 5) + } as any; + const timer = new ex.Timer({ interval: 500, repeats: false, randomRange: [0, 100], random: randomMock }); scene.add(timer); timer.start(); @@ -564,8 +576,13 @@ describe('A Timer', () => { }); it('produces random intervals even with new interval passed during reset', () => { - const randomMock = jasmine.createSpyObj('Random', ['integer']); - randomMock.integer.and.returnValues(11, 1, 5); + const randomMock = { + integer: vi + .fn() + .mockImplementationOnce(() => 11) + .mockImplementationOnce(() => 11) + .mockImplementationOnce(() => 5) + } as any; const timer = new ex.Timer({ interval: 500, repeats: true, randomRange: [0, 100], random: randomMock }); scene.add(timer); timer.start(); diff --git a/src/spec/TimescalingSpec.ts b/src/spec/vitest/TimescalingSpec.ts similarity index 87% rename from src/spec/TimescalingSpec.ts rename to src/spec/vitest/TimescalingSpec.ts index 2f0ccf01..008d29c1 100644 --- a/src/spec/TimescalingSpec.ts +++ b/src/spec/vitest/TimescalingSpec.ts @@ -1,5 +1,4 @@ import * as ex from '@excalibur'; -import { Mocks } from './util/Mocks'; import { TestUtils } from './util/TestUtils'; describe('The engine', () => { @@ -40,7 +39,7 @@ describe('The engine', () => { // actor moves twice as fast clock.step(1000); - expect(actor.pos.x).toBe(10, 'actor did not move twice as fast'); + expect(actor.pos.x, 'actor did not move twice as fast').toBe(10); }); it('should run at 1/2 speed when timescale is 0.5', () => { @@ -54,6 +53,6 @@ describe('The engine', () => { // actor moves twice as slow clock.step(2000); - expect(actor.pos.x).toBeCloseTo(5, 0.2, 'actor did not move twice as slow'); + expect(actor.pos.x, 'actor did not move twice as slow').toBeCloseTo(5, 0.2); }); }); diff --git a/src/spec/ToasterSpec.ts b/src/spec/vitest/ToasterSpec.ts similarity index 100% rename from src/spec/ToasterSpec.ts rename to src/spec/vitest/ToasterSpec.ts diff --git a/src/spec/TransformComponentSpec.ts b/src/spec/vitest/TransformComponentSpec.ts similarity index 96% rename from src/spec/TransformComponentSpec.ts rename to src/spec/vitest/TransformComponentSpec.ts index 0328b8f4..1d9d34ed 100644 --- a/src/spec/TransformComponentSpec.ts +++ b/src/spec/vitest/TransformComponentSpec.ts @@ -1,13 +1,8 @@ import * as ex from '@excalibur'; import { TransformComponent } from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; -import { EulerIntegrator } from '../engine/Collision/Integrator'; +import { EulerIntegrator } from '../../engine/Collision/Integrator'; describe('A TransformComponent', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); - it('exists', () => { expect(ex.TransformComponent).toBeDefined(); }); @@ -187,7 +182,7 @@ describe('A TransformComponent', () => { it('can observe a z index change', () => { const tx = new ex.TransformComponent(); - const zSpy = jasmine.createSpy('zSpy'); + const zSpy = vi.fn(); tx.zIndexChanged$.subscribe(zSpy); tx.z = 19; @@ -198,7 +193,7 @@ describe('A TransformComponent', () => { it('will only flag the transform dirty once during integration', () => { const transform = new ex.TransformComponent(); - spyOn(transform.get(), 'flagDirty').and.callThrough(); + vi.spyOn(transform.get(), 'flagDirty'); const motion = new ex.MotionComponent(); EulerIntegrator.integrate(transform, motion, ex.Vector.Zero, 16); @@ -208,7 +203,7 @@ describe('A TransformComponent', () => { it('will only flag dirty if the pos coord is different', () => { const transform = new ex.TransformComponent(); - spyOn(transform.get(), 'flagDirty').and.callThrough(); + vi.spyOn(transform.get(), 'flagDirty'); expect(transform.globalPos).toBeVector(ex.vec(0, 0)); transform.pos.x = 0; @@ -223,7 +218,7 @@ describe('A TransformComponent', () => { it('will only flag dirty if the rotation coord is different', () => { const transform = new ex.TransformComponent(); - spyOn(transform.get(), 'flagDirty').and.callThrough(); + vi.spyOn(transform.get(), 'flagDirty'); expect(transform.globalRotation).toBe(0); transform.rotation = 0; @@ -236,7 +231,7 @@ describe('A TransformComponent', () => { it('will only flag dirty if the scale coord is different', () => { const transform = new ex.TransformComponent(); - spyOn(transform.get(), 'flagDirty').and.callThrough(); + vi.spyOn(transform.get(), 'flagDirty'); expect(transform.globalScale).toBeVector(ex.vec(1, 1)); transform.scale.x = 1; @@ -309,7 +304,7 @@ describe('A TransformComponent', () => { it('children inherit the top most parent coordinate plane', () => { const logger = ex.Logger.getInstance(); - spyOn(logger, 'warn'); + vi.spyOn(logger, 'warn'); const child1 = new ex.Entity([new TransformComponent()]); const child2 = new ex.Entity([new TransformComponent()], 'child2'); const parent = new ex.Entity([new TransformComponent()]); diff --git a/src/spec/TransistionSpec.ts b/src/spec/vitest/TransitionSpec.ts similarity index 84% rename from src/spec/TransistionSpec.ts rename to src/spec/vitest/TransitionSpec.ts index 4e0a4770..c827a212 100644 --- a/src/spec/TransistionSpec.ts +++ b/src/spec/vitest/TransitionSpec.ts @@ -47,9 +47,9 @@ describe('A Transition', () => { it('can be started with execute()', () => { const engine = TestUtils.engine(); const sut = new ex.Transition({ duration: 3000 }); - const onUpdateSpy = jasmine.createSpy('onUpdate'); - const onStartSpy = jasmine.createSpy('onStart'); - const onEndSpy = jasmine.createSpy('onEnd'); + const onUpdateSpy = vi.fn(); + const onStartSpy = vi.fn(); + const onEndSpy = vi.fn(); sut.onUpdate = onUpdateSpy; sut.onStart = onStartSpy; sut.onEnd = onEndSpy; @@ -63,11 +63,11 @@ describe('A Transition', () => { sut.updateTransition(engine, 16); sut._execute(); - expect(onUpdateSpy.calls.argsFor(1)).toEqual([16 / 3000]); + expect(onUpdateSpy.mock.calls[1]).toEqual([16 / 3000]); sut.updateTransition(engine, 16); sut._execute(); - expect(onUpdateSpy.calls.argsFor(2)).toEqual([32 / 3000]); + expect(onUpdateSpy.mock.calls[2]).toEqual([32 / 3000]); sut.updateTransition(engine, 3200 - 32); sut._execute(); @@ -86,9 +86,9 @@ describe('A Transition', () => { it('can be reset()', () => { const engine = TestUtils.engine(); const sut = new ex.Transition({ duration: 3000 }); - const onUpdateSpy = jasmine.createSpy('onUpdate'); - const onStartSpy = jasmine.createSpy('onStart'); - const onEndSpy = jasmine.createSpy('onEnd'); + const onUpdateSpy = vi.fn(); + const onStartSpy = vi.fn(); + const onEndSpy = vi.fn(); sut.onUpdate = onUpdateSpy; sut.onStart = onStartSpy; sut.onEnd = onEndSpy; @@ -102,11 +102,11 @@ describe('A Transition', () => { sut.updateTransition(engine, 16); sut._execute(); - expect(onUpdateSpy.calls.argsFor(1)).toEqual([16 / 3000]); + expect(onUpdateSpy.mock.calls[1]).toEqual([16 / 3000]); sut.updateTransition(engine, 16); sut._execute(); - expect(onUpdateSpy.calls.argsFor(2)).toEqual([32 / 3000]); + expect(onUpdateSpy.mock.calls[2]).toEqual([32 / 3000]); sut.updateTransition(engine, 3200 - 32); sut._execute(); @@ -118,7 +118,7 @@ describe('A Transition', () => { expect(sut.complete).toBe(true); - sut.onReset = jasmine.createSpy('onReset'); + sut.onReset = vi.fn(); sut.reset(); expect(sut.complete).toBe(false); diff --git a/src/spec/TriggerSpec.ts b/src/spec/vitest/TriggerSpec.ts similarity index 88% rename from src/spec/TriggerSpec.ts rename to src/spec/vitest/TriggerSpec.ts index 9497f766..cfbff7f4 100644 --- a/src/spec/TriggerSpec.ts +++ b/src/spec/vitest/TriggerSpec.ts @@ -1,5 +1,4 @@ import * as ex from '@excalibur'; -import { Mocks } from './util/Mocks'; import { TestUtils } from './util/TestUtils'; describe('A Trigger', () => { @@ -29,7 +28,7 @@ describe('A Trigger', () => { expect(ex.Trigger).toBeDefined(); }); - xit('can be triggered once', () => { + it.skip('can be triggered once', () => { // Arrange const trigger = new ex.Trigger({ pos: new ex.Vector(0, 100), @@ -42,7 +41,7 @@ describe('A Trigger', () => { actor.vel.y = 10; engine.currentScene.add(trigger); engine.currentScene.add(actor); - spyOn(trigger, 'action'); + vi.spyOn(trigger, 'action'); // Act actor.vel = ex.vec(0, 10); @@ -65,7 +64,7 @@ describe('A Trigger', () => { expect(trigger.isKilled()).toBe(true); }); - xit('can be triggered multiple times', () => { + it.skip('can be triggered multiple times', () => { // Arrange const trigger = new ex.Trigger({ pos: new ex.Vector(0, 100), @@ -74,8 +73,8 @@ describe('A Trigger', () => { repeat: 3 }); trigger.collider.update(); - const enterSpy = jasmine.createSpy('enter'); - const exitSpy = jasmine.createSpy('exit'); + const enterSpy = vi.fn(); + const exitSpy = vi.fn(); trigger.on('enter', enterSpy); trigger.on('exit', exitSpy); @@ -84,7 +83,7 @@ describe('A Trigger', () => { actor.vel.y = 10; engine.currentScene.add(trigger); engine.currentScene.add(actor); - spyOn(trigger, 'action').and.callThrough(); + vi.spyOn(trigger, 'action'); // Act // Enter trigger first @@ -127,7 +126,7 @@ describe('A Trigger', () => { expect(trigger.isKilled()).toBe(true); }); - xit('fires an event when an actor enters the trigger once', () => { + it.skip('fires an event when an actor enters the trigger once', () => { // Arrange let fired = 0; @@ -157,7 +156,7 @@ describe('A Trigger', () => { expect(fired).toBe(1); }); - xit('fires an event when the actor exits the trigger', () => { + it.skip('fires an event when the actor exits the trigger', () => { // Arrange const trigger = new ex.Trigger({ pos: new ex.Vector(0, 100), @@ -173,8 +172,8 @@ describe('A Trigger', () => { engine.add(trigger); engine.add(actor); - const exitSpy = jasmine.createSpy('exit'); - const collisionEnd = jasmine.createSpy('collisionend'); + const exitSpy = vi.fn(); + const collisionEnd = vi.fn(); trigger.events.on('exit', exitSpy); trigger.events.on('collisionend', collisionEnd); @@ -197,7 +196,7 @@ describe('A Trigger', () => { engine.add(trigger); - trigger.graphics.onPostDraw = jasmine.createSpy('draw'); + trigger.graphics.onPostDraw = vi.fn(); // Act clock.run(2, 1000); @@ -217,7 +216,7 @@ describe('A Trigger', () => { engine.add(trigger); - trigger.graphics.onPostDraw = jasmine.createSpy('draw'); + trigger.graphics.onPostDraw = vi.fn(); // Act clock.run(2, 1000); @@ -241,7 +240,7 @@ describe('A Trigger', () => { engine.add(trigger); engine.add(actor); - spyOn(trigger, 'action'); + vi.spyOn(trigger, 'action'); // Act clock.run(2, 1000); @@ -250,7 +249,7 @@ describe('A Trigger', () => { expect(trigger.action).not.toHaveBeenCalled(); }); - xit('will not only trigger if the filter is true', () => { + it.skip('will not only trigger if the filter is true', () => { // Arrange const trigger = new ex.Trigger({ pos: new ex.Vector(0, 100), @@ -267,7 +266,7 @@ describe('A Trigger', () => { engine.add(trigger); engine.add(actor); - spyOn(trigger, 'action').and.callThrough(); + vi.spyOn(trigger, 'action'); // Act clock.run(2, 1000); @@ -291,7 +290,7 @@ describe('A Trigger', () => { engine.add(trigger); engine.add(actor2); - spyOn(trigger, 'action'); + vi.spyOn(trigger, 'action'); // Act clock.run(2, 1000); diff --git a/src/spec/UtilSpec.ts b/src/spec/vitest/UtilSpec.ts similarity index 94% rename from src/spec/UtilSpec.ts rename to src/spec/vitest/UtilSpec.ts index ddb98976..b7cd09e2 100644 --- a/src/spec/UtilSpec.ts +++ b/src/spec/vitest/UtilSpec.ts @@ -1,5 +1,5 @@ import * as ex from '@excalibur'; -import { watchDeep } from '../engine/Util/Watch'; +import { watchDeep } from '../../engine/Util/Watch'; describe('Utility functions', () => { it('can watch deep', () => { @@ -13,7 +13,7 @@ describe('Utility functions', () => { } }; - const changed = jasmine.createSpy('changed'); + const changed = vi.fn(); const watched = watchDeep(deepObject, changed); watched.top.oneLevel.twoLevel.value = false; diff --git a/src/spec/VectorViewSpec.ts b/src/spec/vitest/VectorViewSpec.ts similarity index 88% rename from src/spec/VectorViewSpec.ts rename to src/spec/vitest/VectorViewSpec.ts index 0dfe0938..09ba1dd8 100644 --- a/src/spec/VectorViewSpec.ts +++ b/src/spec/vitest/VectorViewSpec.ts @@ -1,11 +1,6 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A VectorView', () => { - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); - it('exists', () => { expect(ex.VectorView).toBeDefined(); }); diff --git a/src/spec/VertexBufferSpec.ts b/src/spec/vitest/VertexBufferSpec.ts similarity index 84% rename from src/spec/VertexBufferSpec.ts rename to src/spec/vitest/VertexBufferSpec.ts index 398ed4f0..2701a788 100644 --- a/src/spec/VertexBufferSpec.ts +++ b/src/spec/vitest/VertexBufferSpec.ts @@ -1,11 +1,7 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A VertexBuffer', () => { let gl: WebGL2RenderingContext; - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); beforeEach(() => { const canvas = document.createElement('canvas'); @@ -48,7 +44,7 @@ describe('A VertexBuffer', () => { gl, size: 42 }); - spyOn(gl, 'bindBuffer').and.callThrough(); + vi.spyOn(gl, 'bindBuffer'); sut.bind(); expect(gl.bindBuffer).toHaveBeenCalledWith(gl.ARRAY_BUFFER, sut.buffer); @@ -59,8 +55,8 @@ describe('A VertexBuffer', () => { gl, size: 42 }); - spyOn(gl, 'bindBuffer').and.callThrough(); - spyOn(gl, 'bufferData').and.callThrough(); + vi.spyOn(gl, 'bindBuffer'); + vi.spyOn(gl, 'bufferData'); sut.upload(); expect(gl.bindBuffer).toHaveBeenCalledWith(gl.ARRAY_BUFFER, sut.buffer); diff --git a/src/spec/VertexLayoutSpec.ts b/src/spec/vitest/VertexLayoutSpec.ts similarity index 84% rename from src/spec/VertexLayoutSpec.ts rename to src/spec/vitest/VertexLayoutSpec.ts index 6be5b0e7..ad4964ec 100644 --- a/src/spec/VertexLayoutSpec.ts +++ b/src/spec/vitest/VertexLayoutSpec.ts @@ -1,12 +1,8 @@ import * as ex from '@excalibur'; -import { ExcaliburMatchers } from 'excalibur-jasmine'; describe('A VertexLayout', () => { let gl: WebGL2RenderingContext; let graphicsContext: ex.ExcaliburGraphicsContextWebGL; - beforeAll(() => { - jasmine.addMatchers(ExcaliburMatchers); - }); beforeEach(() => { const canvas = document.createElement('canvas'); @@ -167,7 +163,7 @@ describe('A VertexLayout', () => { vertexBuffer, attributes: [['a_invalid', 2]] }); - }).toThrowMatching((e: Error) => e.message.includes('attribute named: a_invalid size 2 not found')); + }).toThrowError(/(attribute named: a_invalid size 2 not found)/); }); it('will throw on invalid attribute size', () => { @@ -197,18 +193,14 @@ describe('A VertexLayout', () => { vertexBuffer, attributes: [['a_position', 4]] }); - }).toThrowMatching((e: Error) => e.message.includes('VertexLayout size definition for attribute: [a_position, 4]')); + }).toThrowError(new RegExp('VertexLayout size definition for attribute: \\[a_position, 4\\]')); }); it('will calculate vertex size and webgl vbo correctly', () => { - spyOn(gl, 'createVertexArray').and.callThrough(); - const createVertexArray = gl.createVertexArray as jasmine.Spy; - spyOn(gl, 'bindVertexArray').and.callThrough(); - const bindVertexArray = gl.bindVertexArray as jasmine.Spy; - spyOn(gl, 'vertexAttribPointer').and.callThrough(); - const vertexAttribPointerSpy = gl.vertexAttribPointer as jasmine.Spy; - spyOn(gl, 'enableVertexAttribArray').and.callThrough(); - const enableVertexAttribArraySpy = gl.enableVertexAttribArray as jasmine.Spy; + const createVertexArray = vi.spyOn(gl, 'createVertexArray'); + const bindVertexArray = vi.spyOn(gl, 'bindVertexArray'); + const vertexAttribPointerSpy = vi.spyOn(gl, 'vertexAttribPointer'); + const enableVertexAttribArraySpy = vi.spyOn(gl, 'enableVertexAttribArray'); const shader = new ex.Shader({ graphicsContext, @@ -243,7 +235,8 @@ describe('A VertexLayout', () => { ['a_uv', 2] ] }); - expect(sut.totalVertexSizeBytes).withContext('pos is 2x4 + uv is 2x4').toBe(16); + + expect(sut.totalVertexSizeBytes, 'pos is 2x4 + uv is 2x4').toBe(16); sut.initialize(); @@ -251,10 +244,10 @@ describe('A VertexLayout', () => { const uv = shader.attributes.a_uv; expect(createVertexArray).toHaveBeenCalledTimes(1); expect(bindVertexArray).toHaveBeenCalledTimes(2); - expect(vertexAttribPointerSpy.calls.argsFor(0)).toEqual([pos.location, 2, gl.FLOAT, false, 16, 0]); - expect(enableVertexAttribArraySpy.calls.argsFor(0)).toEqual([pos.location]); - expect(vertexAttribPointerSpy.calls.argsFor(1)).toEqual([uv.location, 2, gl.FLOAT, false, 16, 8]); - expect(enableVertexAttribArraySpy.calls.argsFor(1)).toEqual([uv.location]); + expect(vertexAttribPointerSpy.mock.calls[0]).toEqual([pos.location, 2, gl.FLOAT, false, 16, 0]); + expect(enableVertexAttribArraySpy.mock.calls[0]).toEqual([pos.location]); + expect(vertexAttribPointerSpy.mock.calls[1]).toEqual([uv.location, 2, gl.FLOAT, false, 16, 8]); + expect(enableVertexAttribArraySpy.mock.calls[1]).toEqual([uv.location]); expect(gl.vertexAttribPointer).toHaveBeenCalledTimes(2); expect(gl.enableVertexAttribArray).toHaveBeenCalledTimes(2); diff --git a/src/spec/WebAudioInstanceSpec.ts b/src/spec/vitest/WebAudioInstanceSpec.ts similarity index 71% rename from src/spec/WebAudioInstanceSpec.ts rename to src/spec/vitest/WebAudioInstanceSpec.ts index 99736f35..bfb28f57 100644 --- a/src/spec/WebAudioInstanceSpec.ts +++ b/src/spec/vitest/WebAudioInstanceSpec.ts @@ -13,11 +13,12 @@ describe('A webaudio instance', () => { }); beforeEach(() => { - ex.AudioContextFactory.create = jasmine.createSpy('create'); - mockGainNode = jasmine.createSpyObj('GainNode', ['connect']); - - mockGainNode.gain = { - setTargetAtTime: jasmine.createSpy('setTargetAtTime') + vi.spyOn(ex.AudioContextFactory, 'create'); + mockGainNode = { + connect: vi.fn(), + gain: { + setTargetAtTime: vi.fn() + } }; mockBufferSource = { @@ -41,13 +42,11 @@ describe('A webaudio instance', () => { mockAudioContext = { currentTime: 0, - createGain: jasmine.createSpy('createGain'), - createBufferSource: jasmine.createSpy('createBufferSource') + createGain: vi.fn(() => mockGainNode), + createBufferSource: vi.fn(() => mockBufferSource) }; - mockAudioContext.createGain.and.returnValue(mockGainNode); - mockAudioContext.createBufferSource.and.returnValue(mockBufferSource); - (ex.AudioContextFactory.create).and.returnValue(mockAudioContext); + ex.AudioContextFactory.create = vi.fn(() => mockAudioContext); webaudio = new ex.WebAudioInstance(RealAudioContext.createBuffer(1, 1, 22050)); }); diff --git a/src/spec/WebGLUtilSpec.ts b/src/spec/vitest/WebGLUtilSpec.ts similarity index 100% rename from src/spec/WebGLUtilSpec.ts rename to src/spec/vitest/WebGLUtilSpec.ts diff --git a/src/spec/WorldSpec.ts b/src/spec/vitest/WorldSpec.ts similarity index 73% rename from src/spec/WorldSpec.ts rename to src/spec/vitest/WorldSpec.ts index a305ba64..6bc2dba4 100644 --- a/src/spec/WorldSpec.ts +++ b/src/spec/vitest/WorldSpec.ts @@ -15,6 +15,10 @@ class FakeSystem extends ex.System { } describe('A World', () => { + afterEach(() => { + vi.restoreAllMocks(); + }); + it('should exist', () => { expect(ex.World).toBeDefined(); }); @@ -26,7 +30,7 @@ describe('A World', () => { it('can add entities', () => { const world = new ex.World(null); - world.entityManager = jasmine.createSpyObj('EntityManager', ['addEntity']); + vi.spyOn(world.entityManager, 'addEntity'); const entity = new ex.Entity(); @@ -36,7 +40,7 @@ describe('A World', () => { it('can remove entities', () => { const world = new ex.World(null); - world.entityManager = jasmine.createSpyObj('EntityManager', ['addEntity', 'removeEntity']); + vi.spyOn(world.entityManager, 'removeEntity'); const entity = new ex.Entity(); @@ -47,7 +51,7 @@ describe('A World', () => { it('can add systems', () => { const world = new ex.World(null); - world.systemManager = jasmine.createSpyObj('SystemManager', ['addSystem']); + vi.spyOn(world.systemManager, 'addSystem'); const system = new FakeSystem(world); @@ -57,7 +61,7 @@ describe('A World', () => { it('can remove systems', () => { const world = new ex.World(null); - world.systemManager = jasmine.createSpyObj('SystemManager', ['addSystem', 'removeSystem']); + vi.spyOn(world.systemManager, 'removeSystem'); const system = new FakeSystem(world); @@ -68,8 +72,8 @@ describe('A World', () => { it('can clear entities and systems', () => { const world = new ex.World(null); - world.entityManager = jasmine.createSpyObj('EntityManager', ['clear']); - world.systemManager = jasmine.createSpyObj('SystemManager', ['clear']); + vi.spyOn(world.systemManager, 'clear'); + vi.spyOn(world.entityManager, 'clear'); world.clearSystems(); world.clearEntities(); @@ -81,13 +85,11 @@ describe('A World', () => { it('can update', () => { const scene = new ex.Scene(); const world = new ex.World(scene); - world.entityManager = jasmine.createSpyObj('EntityManager', [ - 'processEntityRemovals', - 'findEntitiesForRemoval', - 'processComponentRemovals', - 'updateEntities' - ]); - world.systemManager = jasmine.createSpyObj('SystemManager', ['updateSystems']); + vi.spyOn(world.systemManager, 'updateSystems'); + vi.spyOn(world.entityManager, 'processComponentRemovals'); + vi.spyOn(world.entityManager, 'processEntityRemovals'); + vi.spyOn(world.entityManager, 'updateEntities'); + vi.spyOn(world.systemManager, 'updateSystems'); world.update(SystemType.Update, 100); diff --git a/src/spec/vitest/__reporters__/engine-instance.setup.ts b/src/spec/vitest/__reporters__/engine-instance.setup.ts new file mode 100644 index 00000000..5b6b1e33 --- /dev/null +++ b/src/spec/vitest/__reporters__/engine-instance.setup.ts @@ -0,0 +1,25 @@ +// this is in a separate file because this is executed in the browser +import * as ex from '@excalibur'; + +/** + * Logs the data needed for the engine instance reporter. Should + * be run once in setup file. + */ +export function setupEngineInstanceReporter() { + let currentEngines = ex.Engine.InstanceCount; + + afterEach((ctx) => { + ctx.task.meta.engineInstanceLeaks ??= []; + + if (currentEngines < ex.Engine.InstanceCount) { + // eslint-disable-next-line no-console + console.log(`Spec ${ctx.task.name} Engine increased: ${ex.Engine.InstanceCount}`); + + ctx.task.meta.engineInstanceLeaks.push({ + testName: ctx.task.name, + engineCount: ex.Engine.InstanceCount + }); + } + currentEngines = ex.Engine.InstanceCount; + }); +} diff --git a/src/spec/vitest/__reporters__/engine-instance.ts b/src/spec/vitest/__reporters__/engine-instance.ts new file mode 100644 index 00000000..ef38510b --- /dev/null +++ b/src/spec/vitest/__reporters__/engine-instance.ts @@ -0,0 +1,39 @@ +/* eslint-disable no-console */ +import type { Reporter, TestCase, TestModule } from 'vitest/node'; + +export class EngineInstanceReporter implements Reporter { + leaks: string[] = []; + + onWatcherRerun(files: string[], trigger?: string) { + this.leaks = []; + } + + onTestCaseResult(testCase: TestCase) { + const { engineInstanceLeaks } = testCase.meta(); + + if (engineInstanceLeaks) { + for (const leak of engineInstanceLeaks) { + this.leaks.push(`Spec ${leak.testName} Engine increased: ${leak.engineCount}`); + } + } + } + + onTestRunEnd(testModules: TestModule[]) { + if (this.leaks.length > 0) { + let leakString = '============ Engine leaks ==================\n'; + for (const leak of this.leaks) { + leakString += leak + '\n'; + } + console.log(leakString); // eslint-disable-line + } + } +} + +declare module 'vitest' { + interface TaskMeta { + engineInstanceLeaks: Array<{ + testName: string; + engineCount: number; + }>; + } +} diff --git a/src/spec/vitest/__reporters__/memory.setup.ts b/src/spec/vitest/__reporters__/memory.setup.ts new file mode 100644 index 00000000..5a008392 --- /dev/null +++ b/src/spec/vitest/__reporters__/memory.setup.ts @@ -0,0 +1,23 @@ +// this is in a separate file because this is executed in the browser + +/** + * Logs the data needed for the memory reporter. Should + * be run once in setup file. + */ +export function setupMemoryReporter() { + if (window.performance && window.performance.memory) { + let previousMemory = window.performance.memory; + + afterEach(async (ctx) => { + // run garbage collector if exposed in browser + if ('gc' in window) { + await window.gc({ execution: 'async' }); + } + + const currentMemory = window.performance.memory; + const megabytes = (currentMemory.usedJSHeapSize - previousMemory.usedJSHeapSize) * 0.000001; + ctx.task.meta.memory = { mb: megabytes }; + previousMemory = currentMemory; + }); + } +} diff --git a/src/spec/vitest/__reporters__/memory.ts b/src/spec/vitest/__reporters__/memory.ts new file mode 100644 index 00000000..dfd815bd --- /dev/null +++ b/src/spec/vitest/__reporters__/memory.ts @@ -0,0 +1,54 @@ +/* eslint-disable no-console */ +import type { Reporter, TestCase, TestModule } from 'vitest/node'; + +export class MemoryReporter implements Reporter { + specs: Array<{ + name: string; + memory: number; + }> = []; + + onWatcherRerun() { + this.specs = []; + } + + onTestCaseResult(testCase: TestCase) { + const { memory } = testCase.meta(); + + if (memory && memory.mb > 1) { + this.specs.push({ + name: testCase.name, + memory: memory.mb + }); + } + } + + onTestRunEnd(testModules: TestModule[]) { + this.specs.sort((a, b) => { + return b.memory - a.memory; + }); + + for (const test of this.specs.slice(0, 20)) { + console.warn(`Spec ${test.name} MB: ${test.memory}`); // eslint-disable-line + } + } +} + +declare module 'vitest' { + interface TaskMeta { + memory: { + mb: number; + }; + } +} + +declare global { + interface Window { + performance: { + memory: { + usedJSHeapSize: number; + totalJSHeapSize: number; + jsHeapSizeLimit: number; + }; + }; + } +} diff --git a/src/spec/vitest/__setup__/matchers/convert.ts b/src/spec/vitest/__setup__/matchers/convert.ts new file mode 100644 index 00000000..d5fbc852 --- /dev/null +++ b/src/spec/vitest/__setup__/matchers/convert.ts @@ -0,0 +1,71 @@ +/* eslint-disable no-console */ +type ImageVisual = HTMLCanvasElement | CanvasRenderingContext2D | HTMLImageElement | string; +const convertSourceVisualToImageData = async (visual: ImageVisual): Promise => { + if (visual instanceof HTMLCanvasElement) { + return convertCanvas(visual); + } + if (visual instanceof CanvasRenderingContext2D) { + return convertContext(visual); + } + if (visual instanceof HTMLImageElement) { + return await convertImage(visual); + } + if (typeof visual === 'string') { + return await convertFilePath(visual); + } +}; + +const convertContext = (visual: CanvasRenderingContext2D): ImageData => { + return visual.getImageData(0, 0, visual.canvas.width, visual.canvas.height); +}; + +const convertCanvas = (canvas: HTMLCanvasElement): ImageData => { + const ctx = canvas.getContext('2d'); + const data = ctx.getImageData(0, 0, canvas.width, canvas.height); + return data; +}; + +const convertFilePath = async (imagePath: string, baseImagePath: string = ''): Promise => { + const canvas = document.createElement('canvas'); + const ctx = canvas.getContext('2d'); + + const img = new Image(); + img.decoding = 'sync'; + if (imagePath) { + img.src = baseImagePath + imagePath + '?_=' + Math.random(); + try { + await img.decode(); + } catch { + console.warn(`Image could not be decoded, check image src: ${img.src}`); + } + } + + canvas.width = img.width; + canvas.height = img.height; + + ctx.drawImage(img, 0, 0); + return ctx.getImageData(0, 0, img.width, img.height); +}; + +const convertImage = async (image: HTMLImageElement): Promise => { + const canvas = document.createElement('canvas'); + image.decoding = 'sync'; + + if (image.src) { + try { + await image.decode(); + } catch { + console.warn(`Image could not be decoded, check image src: ${image.src}`); + } + } + + canvas.width = image.width; + canvas.height = image.height; + const ctx = canvas.getContext('2d'); + ctx.drawImage(image, 0, 0); + + return ctx.getImageData(0, 0, image.width, image.height); +}; + +export type { ImageVisual }; +export { convertSourceVisualToImageData }; diff --git a/src/spec/vitest/__setup__/matchers/expect.ts b/src/spec/vitest/__setup__/matchers/expect.ts new file mode 100644 index 00000000..117a95a4 --- /dev/null +++ b/src/spec/vitest/__setup__/matchers/expect.ts @@ -0,0 +1,204 @@ +/* eslint-disable no-console */ +// port of excalibur-jasmine for jest. might be a good idea to publish this as its own package. +import { convertSourceVisualToImageData, ImageVisual } from './convert'; +import pixelmatch from 'pixelmatch'; + +import type * as ex from '@excalibur'; +import { expect } from 'vitest'; + +// seems to not exist in pixelmatch? +type PixelmatchOptions = any; + +export declare type ExcaliburVisual = string | HTMLImageElement | HTMLCanvasElement | CanvasRenderingContext2D; + +export type Visual = string | HTMLImageElement | HTMLCanvasElement | CanvasRenderingContext2D | ImageData; +export type DiffOptions = PixelmatchOptions; + +const flushSourceToImageData = async (source: Visual) => { + const canvas = document.createElement('canvas'); + const context = canvas.getContext('2d')!; + + if (source instanceof ImageData) { + context.canvas.width = source.width; + context.canvas.height = source.height; + context.imageSmoothingEnabled = false; + context.putImageData(source, 0, 0); + } else if (source instanceof HTMLImageElement) { + source.decoding = 'sync'; + + if (source.src) { + try { + await source.decode(); + } catch { + console.warn(`Image could not be decoded, check image src: ${source.src}`); + } + } + context.canvas.width = source.naturalWidth || source.width; + context.canvas.height = source.naturalHeight || source.height; + context.imageSmoothingEnabled = false; + context.drawImage(source, 0, 0); + } else if (source instanceof HTMLCanvasElement) { + context.canvas.width = source.width; + context.canvas.height = source.height; + context.imageSmoothingEnabled = false; + context.drawImage(source, 0, 0); + } else if (source instanceof CanvasRenderingContext2D) { + const imageData = source.getImageData(0, 0, source.canvas.width, source.canvas.height); + context.canvas.width = source.canvas.width; + context.canvas.height = source.canvas.height; + context.imageSmoothingEnabled = false; + context.putImageData(imageData, 0, 0); + } else if (typeof source === 'string') { + // load image + const img = new Image(); + + const loaded = new Promise((resolve, _) => { + img.onload = () => resolve(); + }); + // force path to be relative to vitest root server, not iframe + const baseImagePath = ''; + img.decoding = 'sync'; + if (source) { + img.src = baseImagePath + source + '?_=' + Math.random(); + try { + await loaded; + await img.decode(); + } catch { + console.warn(`Image could not be decoded, check image src: ${img.src}`); + } + } + + context.canvas.width = img.width; + context.canvas.height = img.height; + context.imageSmoothingEnabled = false; + + context.drawImage(img, 0, 0); + } + return [context.getImageData(0, 0, context.canvas.width, context.canvas.height), context] as const; +}; + +const compareImageData = async (actual: Visual, expected: Visual, tolerance: number) => { + const [actualData, actualCtx] = await flushSourceToImageData(actual); + const [expectedData, expectedCtx] = await flushSourceToImageData(expected); + + const diffCanvas = document.createElement('canvas'); + const diffContext = diffCanvas.getContext('2d')!; + + if (actualData.width !== expectedData.width || actualData.height !== expectedData.height) { + return { + pass: false, + message: () => + `Expected image dimension to be (${expectedData.width}x${expectedData.height}), but got (${actualData.width}x${actualData.height})` + }; + } + + const { width, height } = expectedData; + diffContext.canvas.width = width; + diffContext.canvas.height = height; + const diffData = diffContext.createImageData(width, height); + + const length = actualData.data.length; + const totalPixels = length / 4; + const pixelsDiff = pixelmatch(actualData.data, expectedData.data, diffData.data, width, height); + const percentDiff = (totalPixels - pixelsDiff) / totalPixels; + diffContext.putImageData(diffData, 0, 0); + + const actualBase64 = actualCtx.canvas.toDataURL('image/png', 1); + const expectedBase64 = expectedCtx.canvas.toDataURL('image/png', 1); + const diffBase64 = diffContext.canvas.toDataURL('image/png', 1); + + if (percentDiff < tolerance) { + return { + pass: false, + message: () => + `Expected image to match within ${tolerance * 100}%, but only matched ${(percentDiff * 100).toFixed(2)}%. ${pixelsDiff} pixels different.\r\n\r\n` + + `Expected: ${actualBase64}\r\n\r\n` + + `To be: ${expectedBase64}\r\n\r\n` + + `Diff: ${diffBase64}\r\n\r\n` + }; + } else { + return { + pass: true, + message: () => `Expected image matches actual within tolerance (${(percentDiff * 100).toFixed(2)})` + }; + } +}; + +expect.extend({ + toEqualImage: async (actual: Visual, expected: Visual, tolerance: number = 0.995) => { + return await compareImageData(actual, expected, tolerance); + }, + + toBeVector: (actual: ex.Vector, expected: ex.Vector, delta: number = 0.01) => { + const distance = actual.distance(expected); + if (distance <= delta) { + return { + pass: true, + message: () => `Vector within delta ${distance} <= ${delta}` + }; + } else { + return { + pass: false, + message: () => + `Expected ex.Vector${actual.toString()} to be within ${delta} of ex.Vector${expected.toString()}, but was ${distance} distance apart` + }; + } + }, + toHaveValues: (actual: ex.Actor, expected: ex.ActorArgs) => { + let message = 'Expected actor to have properties:\r\n\r\n'; + let passed = true; + for (const key in expected) { + if (actual[key] !== expected[key]) { + passed = false; + message += `Expected actor.${key} to be ${expected[key]}, but got ${actual[key]}\r\n`; + } + } + + return { + pass: passed, + message: () => (passed ? 'Actor properties match' : message) + }; + }, + toHaveLoadedImages: async (actual: HTMLCanvasElement, images: ExcaliburVisual[], tolerance: number = 0.995) => { + const results: Promise[] = []; + for (const image of images) { + results.push(convertSourceVisualToImageData(image)); + } + + const data = await Promise.all(results); + + let pass = true; + let msg: string | undefined; + + for (const imgData of data) { + const result = await compareImageData(actual, imgData, tolerance); + if (!result.pass) { + pass = false; + msg = result.message(); + break; + } + } + + return { + pass, + message: () => msg + }; + } +}); + +interface CustomMatchers { + /** + * Compare two images for pixel equality + * @param expected - The expected image to compare against + * @param tolerance - The difference tolerance level. Default is 0.995 + */ + toEqualImage(expected: Visual, tolerance?: number): Promise; + toBeVector(expected: ex.Vector, delta?: number): R; + toHaveValues(expected: ex.ActorArgs): R; + toHaveLoadedImages(images: ExcaliburVisual[], tolerance?: number): Promise; +} + +declare module 'vitest' { + interface Assertion extends CustomMatchers {} + interface AsymmetricMatchersContaining extends CustomMatchers {} +} diff --git a/src/spec/vitest/__setup__/setup.ts b/src/spec/vitest/__setup__/setup.ts new file mode 100644 index 00000000..d38bdeb5 --- /dev/null +++ b/src/spec/vitest/__setup__/setup.ts @@ -0,0 +1,15 @@ +import * as ex from '@excalibur'; +import { beforeAll } from 'vitest'; +import './matchers/expect'; +import { setupEngineInstanceReporter } from '../__reporters__/engine-instance.setup'; +import { setupMemoryReporter } from '../__reporters__/memory.setup'; + +setupEngineInstanceReporter(); +setupMemoryReporter(); + +// add any global hooks here +beforeAll(() => { + ex.Flags.enable('suppress-obsolete-message'); + // ensure consistent toEqualImage() resolution when running on hidpi displays + window.devicePixelRatio = 1; +}); diff --git a/src/spec/images/SpriteSpec/icon.png b/src/spec/vitest/icon.png similarity index 100% rename from src/spec/images/SpriteSpec/icon.png rename to src/spec/vitest/icon.png diff --git a/src/spec/logo.png b/src/spec/vitest/logo.png similarity index 100% rename from src/spec/logo.png rename to src/spec/vitest/logo.png diff --git a/src/spec/tsconfig.json b/src/spec/vitest/tsconfig.json similarity index 62% rename from src/spec/tsconfig.json rename to src/spec/vitest/tsconfig.json index 0090f2ab..d16e66ca 100644 --- a/src/spec/tsconfig.json +++ b/src/spec/vitest/tsconfig.json @@ -1,6 +1,6 @@ { "compilerOptions": { - "types": ["@types/jasmine", "@types/webpack-env"], + "types": ["@vitest/browser/providers/playwright", "vitest/globals"], "moduleResolution": "node", "sourceMap": true, "experimentalDecorators": true, @@ -9,6 +9,7 @@ "noImplicitAny": false, "noUnusedLocals": false, "downlevelIteration": true, + "allowSyntheticDefaultImports": true, "lib": [ "dom", "dom.iterable", @@ -23,11 +24,11 @@ "es2018" ], "baseUrl": ".", - "rootDir": "../", + "rootDir": "../../../", "paths": { - "@excalibur": ["../engine/"] + "@excalibur": ["../../engine/"] } }, - "include": ["./**/*Spec.ts"], - "files": ["_boot.ts", "../engine/files.d.ts", "../engine/globals.d.ts"] + "include": ["./**/*.ts", "./__setup__/**/*.ts"], + "files": ["../../engine/files.d.ts", "../../engine/globals.d.ts", "../../../vitest.config.ts"] } diff --git a/src/spec/util/Mocks.ts b/src/spec/vitest/util/Mocks.ts similarity index 100% rename from src/spec/util/Mocks.ts rename to src/spec/vitest/util/Mocks.ts diff --git a/src/spec/util/TestUtils.ts b/src/spec/vitest/util/TestUtils.ts similarity index 100% rename from src/spec/util/TestUtils.ts rename to src/spec/vitest/util/TestUtils.ts diff --git a/src/stories/Actions.stories.ts b/src/stories/Actions.stories.ts index 72fde223..a90458dc 100644 --- a/src/stories/Actions.stories.ts +++ b/src/stories/Actions.stories.ts @@ -1,4 +1,4 @@ -import { Meta, StoryObj } from '@storybook/html'; +import type { Meta, StoryObj } from '@storybook/html'; import { Actor, Loader, EasingFunctions, RotationType } from '../engine'; import { ImageSource } from '../engine/Graphics'; import { enumToControlSelectLabels, enumToControlSelectOptions, withEngine } from './utils'; diff --git a/src/stories/Anchors.stories.ts b/src/stories/Anchors.stories.ts index fb4b7911..6c98e9c6 100644 --- a/src/stories/Anchors.stories.ts +++ b/src/stories/Anchors.stories.ts @@ -1,4 +1,4 @@ -import { Meta, StoryObj } from '@storybook/html'; +import type { Meta, StoryObj } from '@storybook/html'; import { Loader, Color, Actor, Vector, vec, toRadians } from '../engine'; import { ImageSource, Canvas } from '../engine/Graphics'; import { withEngine } from './utils'; diff --git a/src/stories/Animations.stories.ts b/src/stories/Animations.stories.ts index 849134a9..50b9c428 100644 --- a/src/stories/Animations.stories.ts +++ b/src/stories/Animations.stories.ts @@ -1,4 +1,4 @@ -import { Meta, StoryObj } from '@storybook/html'; +import type { Meta, StoryObj } from '@storybook/html'; import { Actor, Color, Loader, range } from '../engine'; import { ImageSource, SpriteSheet, Animation, AnimationStrategy, Rectangle } from '../engine/Graphics'; import { enumToControlSelectLabels, enumToControlSelectOptions, withEngine } from './utils'; diff --git a/src/stories/Audio.stories.ts b/src/stories/Audio.stories.ts index 3eebdfc8..13f56c8b 100644 --- a/src/stories/Audio.stories.ts +++ b/src/stories/Audio.stories.ts @@ -1,10 +1,11 @@ /* eslint-disable storybook/context-in-play-function */ -import { Meta, StoryObj } from '@storybook/html'; +import type { Meta, StoryObj } from '@storybook/html'; import { action } from '@storybook/addon-actions'; import playIcon from '@fortawesome/fontawesome-free/svgs/solid/play.svg'; import pauseIcon from '@fortawesome/fontawesome-free/svgs/solid/pause.svg'; import stopIcon from '@fortawesome/fontawesome-free/svgs/solid/stop.svg'; -import { Actor, Sound, Loader, Color, NativeSoundEvent, EasingFunctions, NativeSoundProcessedEvent } from '../engine'; +import type { NativeSoundEvent, NativeSoundProcessedEvent } from '../engine'; +import { Actor, Sound, Loader, Color, EasingFunctions } from '../engine'; import { ImageSource, Sprite } from '../engine/Graphics'; import { withEngine } from './utils'; diff --git a/src/stories/Engine.stories.ts b/src/stories/Engine.stories.ts index 020bd85c..e7fed2dd 100644 --- a/src/stories/Engine.stories.ts +++ b/src/stories/Engine.stories.ts @@ -1,4 +1,4 @@ -import { Meta, StoryObj } from '@storybook/html'; +import type { Meta, StoryObj } from '@storybook/html'; import { Actor, Color, Loader, Logger } from '../engine'; import { BaseAlign, Font, ImageSource, Text } from '../engine/Graphics'; import { withEngine } from './utils'; diff --git a/src/stories/Keyboard.stories.ts b/src/stories/Keyboard.stories.ts index adf50485..b32ba2ee 100644 --- a/src/stories/Keyboard.stories.ts +++ b/src/stories/Keyboard.stories.ts @@ -1,5 +1,6 @@ -import { Meta, StoryObj } from '@storybook/html'; -import { Label, Color, Keys } from '../engine'; +import type { Meta, StoryObj } from '@storybook/html'; +import type { Keys } from '../engine'; +import { Label, Color } from '../engine'; import { withEngine } from './utils'; export default { diff --git a/src/stories/ParticleEmitter.stories.ts b/src/stories/ParticleEmitter.stories.ts index 0ff9a06d..8b2170d9 100644 --- a/src/stories/ParticleEmitter.stories.ts +++ b/src/stories/ParticleEmitter.stories.ts @@ -1,4 +1,4 @@ -import { Meta, StoryObj } from '@storybook/html'; +import type { Meta, StoryObj } from '@storybook/html'; import { ParticleEmitter, EmitterType, Color, Vector } from '../engine'; import { withEngine, enumToControlSelectOptions } from './utils'; diff --git a/src/stories/Pointers.stories.ts b/src/stories/Pointers.stories.ts index d590a22c..1072f15d 100644 --- a/src/stories/Pointers.stories.ts +++ b/src/stories/Pointers.stories.ts @@ -1,4 +1,4 @@ -import { Meta, StoryObj } from '@storybook/html'; +import type { Meta, StoryObj } from '@storybook/html'; import * as ex from '../engine'; import { withEngine } from './utils'; diff --git a/src/stories/utils.ts b/src/stories/utils.ts index b23e51ab..43a24c27 100644 --- a/src/stories/utils.ts +++ b/src/stories/utils.ts @@ -1,4 +1,5 @@ -import { DisplayMode, Engine, EngineOptions, KeyEvent, Keys, Logger, PointerScope } from '../engine'; +import type { EngineOptions, KeyEvent } from '../engine'; +import { DisplayMode, Engine, Keys, Logger, PointerScope } from '../engine'; interface HTMLCanvasElement { gameRef?: Engine; diff --git a/tsconfig.json b/tsconfig.json new file mode 100644 index 00000000..0967ef42 --- /dev/null +++ b/tsconfig.json @@ -0,0 +1 @@ +{} diff --git a/vitest.config.ts b/vitest.config.ts new file mode 100644 index 00000000..bca1f592 --- /dev/null +++ b/vitest.config.ts @@ -0,0 +1,141 @@ +/// + +import type { Plugin } from 'vitest/config'; +import { defineConfig } from 'vitest/config'; +import * as path from 'path'; +import * as os from 'os'; +import { EngineInstanceReporter } from './src/spec/vitest/__reporters__/engine-instance'; +import { MemoryReporter } from './src/spec/vitest/__reporters__/memory'; + +const versioner = require('./version'); +const version = process.env.release ? versioner.getReleaseVersion() : versioner.getAlphaVersion(); + +const isArmMacOS = process.platform === 'darwin' && process.arch === 'arm64'; +const HEADLESS = process.env.HEADLESS === 'true' || process.env.CI === 'true'; + +export default defineConfig({ + plugins: [importAs('glsl', '?raw'), importAs('css', '?inline')], + optimizeDeps: { + include: ['jasmine'] + }, + resolve: { + alias: { + '@excalibur': path.resolve(__dirname, './src/engine/') + } + }, + define: { + 'process.env.__EX_VERSION': JSON.stringify(version), + 'process.env.NODE_ENV': JSON.stringify('development'), + __dirname: JSON.stringify(__dirname) + }, + esbuild: { + target: 'es2018', + tsconfigRaw: { + compilerOptions: { + verbatimModuleSyntax: false + } + } + }, + test: { + globals: true, + setupFiles: ['./src/spec/vitest/__setup__/setup.ts'], + include: ['src/spec/vitest/**/*Spec.ts'], + reporters: [['default', { summary: false }], new EngineInstanceReporter(), new MemoryReporter()], + // enable with --coverage param + coverage: { + include: ['src/engine/**/*.ts'], + provider: 'istanbul', + reporter: [['html'], ['lcov', { projectRoot: __dirname }], ['text-summary']], + reportsDirectory: path.join(__dirname, 'coverage') + }, + pool: 'threads', + browser: { + enabled: true, + provider: 'playwright', + // this will give each test their own environment. disabling this + // actually ended up breaking WebGL contexts in some cases + isolate: true, + + // this slows down the run but helps keep tests stable with how often + // we are opening and closing WebGL contexts + fileParallelism: false, + + headless: HEADLESS, + + // https://vitest.dev/guide/browser/playwright + // run `vitest --browser ` to run tests in a specific browser + instances: [ + { + browser: 'chromium', + provide: { + browser: 'chromium', + platform: os.platform() + }, + launch: { + channel: 'chrome', + ignoreDefaultArgs: ['--disable-render-backgrounding', '--disable-remote-fonts', '--font-render-hinting'], + args: [ + '--no-default-browser-check', + '--no-first-run', + '--disable-default-apps', + '--disable-popup-blocking', + '--disable-translate', + '--disable-background-timer-throttling', + !isArmMacOS && '--disable-gpu', + '--disable-dev-shm-usage', + + // on macOS, disable-background-timer-throttling is not enough + // and we need disable-renderer-backgrounding too + // see https://github.com/karma-runner/karma-chrome-launcher/issues/123 + '--disable-renderer-backgrounding', + '--disable-device-discovery-notifications', + + '--autoplay-policy=no-user-gesture-required', + '--mute-audio', + '--no-sandbox', + '--enable-precise-memory-info', + '--js-flags="--max_old_space_size=8192" --expose-gc' + ].filter(Boolean) + } + }, + { + browser: 'firefox', + provide: { + browser: 'firefox', + platform: os.platform() + } + }, + { + browser: 'webkit', + provide: { + browser: 'webkit', + platform: os.platform() + } + } + ] + } + } +}); + +/** + * Changes the default import behavior for certain file types to + * use the provided query string (e.g. `?raw`) + */ +function importAs(ext: string, query: string): Plugin { + return { + name: 'raw', + enforce: 'pre', + resolveId(id, importer) { + if (id.endsWith(ext)) { + return this.resolve(id + query, importer); + } + } + }; +} + +declare module 'vitest' { + export interface ProvidedContext { + browser: 'chromium' | 'firefox' | 'webkit'; + platform: NodeJS.Platform; + } +}

%FyaD&0Hr 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 literal 0 HcmV?d00001 diff --git a/src/spec/images/GraphicsTextSpec/multi-text-spritefont.png b/src/spec/assets/images/GraphicsTextSpec/multi-text-spritefont.png similarity index 100% rename from src/spec/images/GraphicsTextSpec/multi-text-spritefont.png rename to src/spec/assets/images/GraphicsTextSpec/multi-text-spritefont.png diff --git a/src/spec/assets/images/GraphicsTextSpec/multi-text-win.png b/src/spec/assets/images/GraphicsTextSpec/multi-text-win.png new file mode 100644 index 0000000000000000000000000000000000000000..3c97e33a813d81a8fafc1070f79e4c49b8366283 GIT binary patch literal 3169 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 literal 0 HcmV?d00001 diff --git a/src/spec/images/GraphicsTextSpec/multi-text.png b/src/spec/assets/images/GraphicsTextSpec/multi-text.png similarity index 100% rename from src/spec/images/GraphicsTextSpec/multi-text.png rename to src/spec/assets/images/GraphicsTextSpec/multi-text.png diff --git a/src/spec/assets/images/GraphicsTextSpec/reuse-font-linux.png b/src/spec/assets/images/GraphicsTextSpec/reuse-font-linux.png new file mode 100644 index 0000000000000000000000000000000000000000..5560d48e5f9e6b0082239d5f576dc88eba4c6726 GIT binary patch literal 2295 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 literal 0 HcmV?d00001 diff --git a/src/spec/images/GraphicsTextSpec/reuse-font.png b/src/spec/assets/images/GraphicsTextSpec/reuse-font.png similarity index 100% rename from src/spec/images/GraphicsTextSpec/reuse-font.png rename to src/spec/assets/images/GraphicsTextSpec/reuse-font.png diff --git a/src/spec/images/GraphicsTextSpec/rotated-left-linux.png b/src/spec/assets/images/GraphicsTextSpec/rotated-left-linux.png similarity index 100% rename from src/spec/images/GraphicsTextSpec/rotated-left-linux.png rename to src/spec/assets/images/GraphicsTextSpec/rotated-left-linux.png diff --git a/src/spec/images/GraphicsTextSpec/rotated-left.png b/src/spec/assets/images/GraphicsTextSpec/rotated-left.png similarity index 100% rename from src/spec/images/GraphicsTextSpec/rotated-left.png rename to src/spec/assets/images/GraphicsTextSpec/rotated-left.png diff --git a/src/spec/assets/images/GraphicsTextSpec/rotated-linux.png b/src/spec/assets/images/GraphicsTextSpec/rotated-linux.png new file mode 100644 index 0000000000000000000000000000000000000000..55b6f9627f5a4cc9342f9a8f14e2a17579867afe GIT binary patch literal 2341 zcmeAS@N?(olHy`uVBq!ia0y~yU`PRB4mJh`hJr^^Ll_ts7>k44ofy`glX=O&z;WNx z#WAEJ?(N*lk}Fq5kMG}q(>VKEM^~uQQ-v3aE4v~BR&uWh*uudiq^ThwsI=wEvQQRR zvFQs0jy!ft1@Jx`z z_y1f$2Rd#=hab9M%&#(E^4QeAgeUr7q)$eE8*L{(>5qG{h{Y2HK zX#wXrJvOn;npN_mzohy9qw@*3$|aTD4l-7=@gf$#(nKM}ztb+da(pT;FzxZdgCNWy;)U4u{zN-yiHv<2DkrQ)~G1 zB<<26@zY}cuCG3CPO!MqZ5O($MC8&m@k_5S>~s&T{6BwU=np27Jn6mihPwj|_2qBY zM`$*vFmY_=_`O>Ab)$!o*YrDbtV*w&G~z47FUiL<#73$My??(?-1H~+MC01I43jt% zu6{qa_~7k72YF2A8&axh>%=6I>WR z^4;p$_3w5%3b2^@{s#7S-IF@vW^IiHf1d zY38hp_!Z{FIo_N0v3uWzu(X5Q68A7HVwsSZ>S1KF|0YZPep!#&WdgTWt@)o_dP{50 zZ@tx9>#vml{@f7}>rq>{Y{P_WQ#VfI1_({ zOy9`#Kec`0%cM#s$|QHF1gE@vy?gR9zlfYgYfm)3yv%r^zL-&b+C&=%70GjjryuP8 z;_Oi;Y$B)atCeMAR#bh~y6wQWhkkhr3i1`_y*4{!yM|@j+U07gSUi3Y^Q+ zR?GblR!_=bzw4GvarNy@52Iu#6W;G)Zi+s%_p?_x|vf=Uz9w)wmVB7!o^~ zXBAg3UBKA3UT;x|j8yt8p{p-9@VsOH>X8*%quR3d!WAp4H401R57-JU6`ht*$>g!f z^v=2G+zM|)A{N=}HK;@#ep~bJJoAZ{KP7IjR9I?1?~6kOm%3SP(yi*99nK=zv6Faa zJ>0ru7E9;BJI)2Yb$pVayZqjM4lTSV{7$z;RlT^kQtaU8K9lqFOCu9?zZ~Cv;L|zX zDS67Xg2Fb2T{d&P!@P2yo%lk(`-k?_YRLZR(OtON?|}7-+#A>ZlsI+?KNptRD)z2% zifC{1*SCQN`^$sxgvnPw3s|cl^=hh!gN!!Utha3(9H%wHH-v4yd*x+sOSMAIn}qaB zkzC8vCiiS|@!s+9jM0mIuh*14Uhu1sf62f76Eww>A53Q#IQMVfwHsTXrXMW$k+eZF zekduG19o=$5u_sUtJ9_I2(^yhioC-2pI{zG+&hh_3V zVWtkD#Th>rb#BO!^E~d&1WT zMTv@D28prL9tNz>C~DA{&?MyL8dn@Hcvtn%wX2mMw(XF2zTAmuy{nvV7YjM$qgfwSCa-eeO%gc)f`|Fk0%yv88>%ND1`=P(LO;7xLe4434$TnQz zy8zGs*Y_5!D2QU+a&@Lx$nwKRJGM`_%>K3FR)XiRzqMtZA&+JAv~p_?oXoJP_!s`w zT0EKS_U5C6Wm@)5w6FSGsonE7QD!#PfW#n<}hIk#_jp7n2L-OS&5+BbJ_DrhNdHE<|s zU2ZtFN?FH+A#f&JNSJJ*B2&jHlLebzac~Pdge+s68tNX=ajM}D$L8Gixq4q7crY+9 OFnGH9xvXk44ofy`glX=O&z!vN2 z;uum9_jXQZPDrRk+kNZk^jj}W8vR5guSjVx4K(23)KY9(p`pRS*0n;%i-kps(Urxg zM?~on1%HH{iTYrD{`{P{u z+-1+_eSTW|Yu?x0i&M_)1s`nfVd7#|JnY1F$RXong2Iss0|7QCU&f@5A7lzd&o2+^l!@ zO>ODh6|!HlDI{fmEoWQAJfUmrR($D*((RoFEo$V&>?S=xfU#9!6;*(eE zb8}!^HGMzZ^=;va*3*~2^ee4+sHxGE#kue{yS$OW-UbuCyX^0cRReS#4~S%zx%E8s z`m(;|Y{AqsO@EIF_{z#{5_0tjTo}dt;r?&oSMfi1PTKc0J@i+ZVYLxo!Yfv*SI6LwGF zzAnBwab4l*yu*>&;swn2Zo-#QnGgmyd^d85v*yftT6Nk{srDwZPu z!-WqDEz13ygf?YaJx|SlRJq{Q-|4CiSM<{l{QJD%e^^jg*Rh574_Q~SpV=B&Q?jV} zo8jy=vo}hun|nFw{V`Ed#qXj!Z@t=9q^e)d+qh^&ZXQ=_^^u2*gq|p#7LYTy%9N^* zIB54=z;nIpseKza#Jp2>?5uS8llN&?1)pJ4M;7m*ylY%6MdwVckBT_{YBSHj*MCJ! zula3F{Lb0^asNIoS;wq+eu>f#b{W@O&wg(BJFmaXUrl-M3tpAKw`vlf)^6fy+*6dY zuCD*Nfb5s+CXs*N>D=h&+r5)>O@#GEQGxpZ@=rJ2*qdR@Y{=yC^myHZ z=Eo0`3uLM#OuNOD*H*}#`6~Ir?&H*$)TQ}R4NERFR|c84bXdII`(8ron7HzrUDsaq z-F@QSTKvAaKt}H1^1W>bGAeInfA%(S*&Tku|7_^?LuF?CUH8u|-|KdWTh@YQg_FUJ))uyw?tjhsgzx} z>E(ubuU8Ak=u|)TO`H=FY!`Edal#FWuK#t#rDeCjD;fSuQ?O!~=zZ7hlI!hPlNw(z zF5%8KnxNOQ{PlmdNO`uXLOqr<+N8f&E7M){ zZPMOTq56!^3U;sk(3`khNOeWikF4IlDJ$}sg!(^BxGMONXU$=U5|QXV;zDm~{gP*IohI V|6)~HI|c>@22WQ%mvv4FO#txT2b%x@ literal 0 HcmV?d00001 diff --git a/src/spec/images/GraphicsTextSpec/rotated-right.png b/src/spec/assets/images/GraphicsTextSpec/rotated-right.png similarity index 100% rename from src/spec/images/GraphicsTextSpec/rotated-right.png rename to src/spec/assets/images/GraphicsTextSpec/rotated-right.png diff --git a/src/spec/images/GraphicsTextSpec/rotated-spritefont.png b/src/spec/assets/images/GraphicsTextSpec/rotated-spritefont.png similarity index 100% rename from src/spec/images/GraphicsTextSpec/rotated-spritefont.png rename to src/spec/assets/images/GraphicsTextSpec/rotated-spritefont.png diff --git a/src/spec/images/GraphicsTextSpec/rotated.png b/src/spec/assets/images/GraphicsTextSpec/rotated.png similarity index 100% rename from src/spec/images/GraphicsTextSpec/rotated.png rename to src/spec/assets/images/GraphicsTextSpec/rotated.png diff --git a/src/spec/assets/images/GraphicsTextSpec/shadow-linux.png b/src/spec/assets/images/GraphicsTextSpec/shadow-linux.png new file mode 100644 index 0000000000000000000000000000000000000000..7aee7a4e6c112762aaf583a49e1c710523c82a20 GIT binary patch literal 4053 zcmeAS@N?(olHy`uVBq!ia0y~yU`PRB4mJh`hJr^^Ll_ts7>k44ofy`glX=O&z~Arb z;uum9_ckW8L?l$~->Oy9OD=h;vjha1rN(@;;8W03esJhf$BKi2cLao(I~*NZSOi(p zr?_5eSnx(ePK>cp(#34Mq(h*Dteb3rjHqCM@Fc%Wp6f%4@2&p6YV~9W*F!6V)1Q5v zKjB^U`+L9kRqwC9znbroB>(=Ej(cR98&o(7dBjZw96L7u5NNUJ;dks%IFiX>p(A(E znMIM$`9R{s4lcnK3m(SyR%I<0fky@`GGcuz1ROgK3lv0HEOMfcB4NcS+xlEh&*k$C z-!0#_l~s{J>20|)pIPJU2Ro0u{x1;-zMHFjsjRd$WUk}iIb}|-POk_)t1fh<^O_-h z?$L8zK3lKrRR8f@@^+8hK3Q|7Svyrs8vbj|{n0=5=d9yj-}gP5{+wN*Jjig$q-QOB z9$iuF>)1j&9$t~L>7DL=zR5mv=jYizj0?kh(iHrzp6gj?DRy~Q);Gf`HlGcQri&ih zzSr8s)HK6WZOMdIpC?zQm#Qo3+$m(&ViQyTellD`ah96nw~z=l6L(jIZZ^ zlCbUF^oF!3>!P2>S5!Pm&6wwLs`iP`49=$k*;<+t{j3FEZI?3OrUw--3+(;C{lu@T^VgI0UH>*~`t9@=U%c$LTGwnp9qy$@+-HyLWmqUK(Q-0h z@3i80l+=XppU-t{wQN|mXKBD@?}?`QDpL+WchIwBK6qT+p{r`5#b@;$`*%vr)35iI zt^OXfw7KTG(v_0CJonl6KKS>}yd&-d>!Is;uD_1$I}uU7o-rjsjrf8b@nHqN_pXX_Q9Uz^u|AR@b{;hxV9Cn}7e@quY^!=Z2$M%2I)Z%^5m!6no z&lFV2C-C(^`I5Zzn{*;uCM5g!GzQ(`X$(K^;C-S&Yw@#Py(@O*>oEz(x4b^kYO^Ya$=b z*h_ZLeEjflx_Xqsk~7)21slAd-DT9A({?A2yJ1E6d*)d!tA5A3?szR`q8pK|E%FMM@y`UK+|&L#8DGlg)z zOMBY8dcviXt_AhQf=1$e>_SFcTADn5+pdr?6`U!Ye&Fxb)GLlpgOdg9^X-ecuBmuW zIqCZ1-_DMbn{8^&VK3$zen=9pY3$-${9wMJ;5`5JZl(Wsc9h)pdfRhs{izkX?hRV8 zMcR9IuWzb9mr?5*x@e}{&X2h*Txm+_AG}UXWpqe$5pbHqqL3X>>=kIWRp8&z!w>FO z8E=`$nbm9?>+QsIVwtaE?HEH1#flrZ7H#`^E{YQAm z_t>r*uGJH5pM{>-Qu+G3#LG>hq0R9QWfy}y+@mg}e4Fz(`!L5t-#we&XLH1V)-wuw za(MIWs1=!4Iqq7^e=PegAhAbgh39g)tQd*^Ql2qI@Sxn=SgaP?CcuigT$>xVnp{ zLy;;&cvBdsYRa$X5BfDM^K|!0Dsm~+hAmw7;OXOE<@GhXe}dIt3$0jj!ALtG&Zgnt znFtG>duMCE)Oo}UDP7NX%Xm@3(xzj~@o}5oEe@v}Ey8d98!3g?op^PD{rtN7%DFck zJldlq8C(9@FwI&oHFNQEiC&-c1`D#@RH)pNb2zr=Vb!MzrJXJUoL3m0CPdGQT=?cwZhoxdC_53tSA+QhcDp=OH5G@ks~%Du`i#qNQ>u5kP?yUTYy ze7e&=f9s5^b{U1@Q#rNlC$(KD?sxipRiXIGoF&d~9=`u%T&mW(pZiZRY0rQDKH zSKpcS$zw(Oe~$CNZ3WLox1CvZUE%+YS$F%}BED}AwEbh5A}Zt*b>XX&ug8wZWg$Ej zk~@E9FTA?Mv3u87q4eGf%_TKXCM%x5cRu<>(IdK6zUK6&$=8LQe%Li<{AP_`m=$KX zM_bN8>ST?uZZQelbfP1|tV+gc8edz@3Q=CURNn