diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 24d602d3..580d65eb 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -75,8 +75,7 @@ jobs: NODE_ENV: production run: | cd frontend - # npm run lint - echo "💥 Frontend linting is temporarily disabled until it can be set up again with Svelte 💥" + npm run lint - name: 🔬 Check Rust formatting run: | diff --git a/.prettierrc b/.prettierrc index 54721570..91210d5a 100644 --- a/.prettierrc +++ b/.prettierrc @@ -3,6 +3,7 @@ "useTabs": true, "tabWidth": 4, "printWidth": 200, + "plugins": ["prettier-plugin-svelte"], "overrides": [ { "files": ["*.yml", "*.yaml"], @@ -10,6 +11,12 @@ "useTabs": false, "tabWidth": 2 } + }, + { + "files": ["*.svelte"], + "options": { + "parser": "svelte" + } } ] } diff --git a/.vscode/settings.json b/.vscode/settings.json index 1da69fa9..e8c14083 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -6,7 +6,7 @@ "editor.defaultFormatter": "rust-lang.rust-analyzer" }, // Web: save on format - "[typescript][javascript]": { + "[javascript][typescript][svelte]": { "editor.codeActionsOnSave": { "source.fixAll.eslint": true }, @@ -39,7 +39,7 @@ // ESLint config "eslint.format.enable": true, "eslint.workingDirectories": ["./frontend", "./website/other/bezier-rs-demos", "./website"], - "eslint.validate": ["javascript", "typescript"], + "eslint.validate": ["javascript", "typescript", "svelte"], // VS Code config "html.format.wrapLineLength": 200, "files.eol": "\n", diff --git a/frontend/.eslintrc.js b/frontend/.eslintrc.cjs similarity index 56% rename from frontend/.eslintrc.js rename to frontend/.eslintrc.cjs index 2382cd2d..acbaae23 100644 --- a/frontend/.eslintrc.js +++ b/frontend/.eslintrc.cjs @@ -1,24 +1,25 @@ - module.exports = { root: true, - env: { - browser: true, - node: true, - es2020: true, - }, - parserOptions: { - ecmaVersion: 2020, - }, + env: { browser: true, node: true }, extends: [ - // General Prettier defaults + "eslint:recommended", + "plugin:import/recommended", + "plugin:@typescript-eslint/recommended", + "plugin:import/typescript", + "plugin:svelte/recommended", + "plugin:svelte/prettier", "prettier", ], + plugins: ["import", "@typescript-eslint", "prettier"], settings: { - // https://github.com/import-js/eslint-plugin-import#resolvers - "import/resolver": { - // `node` must be listed first! - node: {}, - }, + "import/parsers": { "@typescript-eslint/parser": [".ts", ".tsx"] }, + "import/resolver": { typescript: true, node: true }, + }, + parser: "@typescript-eslint/parser", + parserOptions: { + ecmaVersion: "latest", + project: "./tsconfig.json", + extraFileExtensions: [".svelte"], }, ignorePatterns: [ // Ignore generated directories @@ -26,13 +27,24 @@ module.exports = { "dist/", "pkg/", "wasm/pkg/", - // Don't ignore JS and TS dotfiles in this folder "!.*.js", "!.*.ts", ], + overrides: [ + { + files: ["*.js"], + rules: { "@typescript-eslint/explicit-function-return-type": ["off"] }, + }, + { + files: ["*.svelte"], + parser: "svelte-eslint-parser", + // Parse the ` @@ -214,7 +215,7 @@ {#if sectionIndex > 0} {/if} - {#each virtualScrollingEntryHeight ? section.slice(virtualScrollingStartIndex, virtualScrollingEndIndex) : section as entry, entryIndex (entryIndex + (virtualScrollingEntryHeight ? virtualScrollingStartIndex : 0))} + {#each virtualScrollingEntryHeight ? section.slice(virtualScrollingStartIndex, virtualScrollingEndIndex) : section as entry, entryIndex (entryIndex + startIndex)} diff --git a/frontend/src/components/layout/FloatingMenu.svelte b/frontend/src/components/layout/FloatingMenu.svelte index 1013942f..665663e9 100644 --- a/frontend/src/components/layout/FloatingMenu.svelte +++ b/frontend/src/components/layout/FloatingMenu.svelte @@ -137,9 +137,9 @@ floatingMenuContentDiv.style.setProperty("min-height", "unset"); } - // Gets the client bounds of the elements and apply relevant styles to them - // TODO: Use DOM attribute bindings more whilst not causing recursive updates - // Turning measuring on and off both causes the component to change, which causes the `afterUpdate()` Svelte event to fire extraneous times (hurting performance and sometimes causing an infinite loop) + // Gets the client bounds of the elements and apply relevant styles to them. + // TODO: Use DOM attribute bindings more whilst not causing recursive updates. Turning measuring on and off both causes the component to change, + // TODO: which causes the `afterUpdate()` Svelte event to fire extraneous times (hurting performance and sometimes causing an infinite loop). if (!measuringOngoingGuard) positionAndStyleFloatingMenu(); }); @@ -237,7 +237,7 @@ } // To be called by the parent component. Measures the actual width of the floating menu content element and returns it in a promise. - export async function measureAndEmitNaturalWidth(): Promise { + export async function measureAndEmitNaturalWidth() { if (!measuringOngoingGuard) return; // Wait for the changed content which fired the `afterUpdate()` Svelte event to be put into the DOM @@ -297,7 +297,7 @@ } } - function hoverTransfer(self: HTMLDivElement | undefined, ownSpawner: HTMLElement | undefined, targetSpawner: HTMLElement | undefined): void { + function hoverTransfer(self: HTMLDivElement | undefined, ownSpawner: HTMLElement | undefined, targetSpawner: HTMLElement | undefined) { // Algorithm pseudo-code to detect and transfer to hover-transferrable floating menu spawners // Accompanying diagram: // diff --git a/frontend/src/components/panels/Document.svelte b/frontend/src/components/panels/Document.svelte index 5b961909..9375211a 100644 --- a/frontend/src/components/panels/Document.svelte +++ b/frontend/src/components/panels/Document.svelte @@ -1,8 +1,10 @@ @@ -241,4 +243,5 @@ } } } + // paddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpaddingpadding diff --git a/frontend/src/components/widgets/buttons/PopoverButton.svelte b/frontend/src/components/widgets/buttons/PopoverButton.svelte index 13a3ea16..3687d364 100644 --- a/frontend/src/components/widgets/buttons/PopoverButton.svelte +++ b/frontend/src/components/widgets/buttons/PopoverButton.svelte @@ -1,5 +1,6 @@ - dispatch("checked", inputElement?.checked)} {disabled} tabindex={disabled ? -1 : 0} bind:this={inputElement} /> + dispatch("checked", inputElement?.checked)} {disabled} tabindex={disabled ? -1 : 0} bind:this={inputElement} />