From 16460ce5570435e37d46385bced06e23f744c745 Mon Sep 17 00:00:00 2001 From: Krasilnikov Roman Date: Thu, 6 Jun 2024 18:37:07 +0300 Subject: [PATCH] Vim mode --- bun.lockb | Bin 290278 -> 290668 bytes package.json | 1 + src/adapters/storage.svelte.ts | 18 +++++ src/components/editor/editor-surface.svelte | 24 ++++-- src/components/editor/editor.svelte | 2 + src/components/editor/model.ts | 8 ++ src/components/editor/testing-panel.svelte | 12 ++- src/components/editor/vim-mode.svelte | 25 ++++++ src/monaco-vim.d.ts | 85 ++++++++++++++++++++ 9 files changed, 167 insertions(+), 8 deletions(-) create mode 100644 src/adapters/storage.svelte.ts create mode 100644 src/components/editor/vim-mode.svelte create mode 100644 src/monaco-vim.d.ts diff --git a/bun.lockb b/bun.lockb index d43683f56e0f7e8ad0d7d6a1960be7894a9eccdd..0133c139cb51f97320cc29095ba48b0a248e6290 100755 GIT binary patch delta 53092 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 EUqPtzyZ`_I diff --git a/package.json b/package.json index 21e2ed6..cb3dc29 100644 --- a/package.json +++ b/package.json @@ -21,6 +21,7 @@ "astro-icon": "^1.1.0", "fast-deep-equal": "^3.1.3", "monaco-editor": "^0.49.0", + "monaco-vim": "^0.4.1", "pyodide": "^0.26.0", "tailwindcss": "^3.4.4", "typescript": "^5.4.5" diff --git a/src/adapters/storage.svelte.ts b/src/adapters/storage.svelte.ts new file mode 100644 index 0000000..83090b1 --- /dev/null +++ b/src/adapters/storage.svelte.ts @@ -0,0 +1,18 @@ +import type { SyncStorage } from "@/shared"; + +export interface StorageState { + value: T; +} + +export function reactive(storage: SyncStorage): StorageState { + let value = $state(storage.load()); + return { + get value() { + return value; + }, + set value(newValue) { + value = newValue; + storage.save(newValue); + }, + }; +} diff --git a/src/components/editor/editor-surface.svelte b/src/components/editor/editor-surface.svelte index 3cd2f19..8a8d895 100644 --- a/src/components/editor/editor-surface.svelte +++ b/src/components/editor/editor-surface.svelte @@ -45,7 +45,7 @@ }; }); - let ed: editor.IStandaloneCodeEditor; + let ed = $state() let editorElement: HTMLDivElement; $effect(() => { @@ -53,14 +53,21 @@ ed = editor.create(editorElement, { model, theme: "vs-dark", + fixedOverflowWidgets: true, + lineNumbers: "on", + tabSize: 2, + insertSpaces: true, + fontSize: 16, minimap: { enabled: false, }, }); untrack(() => { - ed.layout({ width, height }); + ed?.layout({ width, height }); }) - return () => ed.dispose(); + return () => { + ed?.dispose(); + } }); let panelHeight = $derived(window.innerHeight - height); @@ -68,6 +75,9 @@ let isCollapsed = $derived(panelHeight <= MIN_PANEL_HEIGHT) const api: SurfaceApi = { + get editor() { + return ed + }, get width() { return width }, @@ -89,7 +99,7 @@ return false } height = normalizeHeight(window.innerHeight - newHeight - PANEL_BORDER_HEIGHT) - ed.layout({ width, height }, true) + ed?.layout({ width, height }, true) return true }, hidePanel() { @@ -97,7 +107,7 @@ return false } height = normalizeHeight(window.innerHeight) - ed.layout({ width, height }, true) + ed?.layout({ width, height }, true) return true }, } @@ -111,7 +121,7 @@ }} onMove={(e) => { width = normalizeWidth(start.x - e.clientX + start.y) - ed.layout({ width, height }, true) + ed?.layout({ width, height }, true) }} onMoveEnd={() => { widthStorage.save(width) @@ -126,7 +136,7 @@ }} onMove={(e) => { height = normalizeHeight(start.x - (start.y - e.clientY)) - ed.layout({ width, height }, true) + ed?.layout({ width, height }, true) }} /> {/snippet} diff --git a/src/components/editor/editor.svelte b/src/components/editor/editor.svelte index c88a25d..cf1bf50 100644 --- a/src/components/editor/editor.svelte +++ b/src/components/editor/editor.svelte @@ -12,6 +12,7 @@ import EditorSurface from "./editor-surface.svelte"; import LangSelect from "./lang-select.svelte"; import TestingPanel from "./testing-panel.svelte"; + import VimMode from './vim-mode.svelte'; interface Props { initialValue?: string; @@ -75,6 +76,7 @@ children={resizer} > {#snippet header()} + {/snippet} diff --git a/src/components/editor/model.ts b/src/components/editor/model.ts index 8d2c3c8..0dd01cd 100644 --- a/src/components/editor/model.ts +++ b/src/components/editor/model.ts @@ -1,4 +1,10 @@ +import type { editor } from 'monaco-editor'; + +import { createSyncStorage } from '@/adapters/storage'; +import { reactive } from '@/adapters/storage.svelte' + export interface SurfaceApi { + editor: editor.IStandaloneCodeEditor | undefined; width: number; panelHeight: number; isPanelCollapsed: boolean; @@ -6,3 +12,5 @@ export interface SurfaceApi { hidePanel(): boolean; togglePanel(height: number): boolean; } + +export const vimState = reactive(createSyncStorage(localStorage, 'editor-vim', false)); diff --git a/src/components/editor/testing-panel.svelte b/src/components/editor/testing-panel.svelte index 51b5d55..71f951a 100644 --- a/src/components/editor/testing-panel.svelte +++ b/src/components/editor/testing-panel.svelte @@ -13,7 +13,7 @@ type TestRunnerFactory, } from "@/lib/testing"; - import type { SurfaceApi } from './model'; + import { type SurfaceApi, vimState } from './model'; import { makeTheme } from './terminal' interface Props { @@ -189,6 +189,16 @@ class="grow pl-4 mt-4" class:hidden={selectedTab !== Tab.Output} > +
+
+
+ +
+
+
{@render children()} diff --git a/src/components/editor/vim-mode.svelte b/src/components/editor/vim-mode.svelte new file mode 100644 index 0000000..0dc8f24 --- /dev/null +++ b/src/components/editor/vim-mode.svelte @@ -0,0 +1,25 @@ + + +
diff --git a/src/monaco-vim.d.ts b/src/monaco-vim.d.ts new file mode 100644 index 0000000..0d8bf75 --- /dev/null +++ b/src/monaco-vim.d.ts @@ -0,0 +1,85 @@ +// Copied from `typehero` project licensed under AGPL-3.0 +// https://github.com/typehero/typehero/blob/main/packages/monaco/monaco-vim.d.ts + +declare module 'monaco-vim' { + import type * as monaco from 'monaco-editor'; + + export function initVimMode( + editor: monaco.editor.IStandaloneCodeEditor, + statusbarNode?: Element | null, + ): CMAdapter; + + type VimModes = 'insert' | 'normal' | 'visual'; + + class CMAdapter { + /** removes the attached vim bindings */ + dispose(): void; + + attached: boolean; + + editor: monaco.editor.IStandaloneCodeEditor; + + statusBar: { + clear(): void; + node: HTMLElement; + }; + + /** @see https://codemirror.net/5/doc/manual.html#vimapi */ + static Vim: { + map(lhs: string, rhs: string, ctx: VimModes): void; + unmap(lhs: string, ctx: VimModes | false): boolean; + noremap(lhs: string, rhs: string, ctx: VimModes): void; + + mapCommand( + keys: string, + type: 'action', + name: string, + args?: Record, + extra?: Record, + ): void; + + defineAction( + name: string, + fn: ( + ctx: CMAdapter, + // TODO: Document other args + ...args: [unknown, unknown] + ) => void, + ): void; + + defineEx( + name: string, + prefix: string | undefined, + fn: ( + ctx: CMAdapter, + data: { + commandName: string; + input: string; + } & ( + | { + argString: string; + args: [string, ...string[]]; + } + | { argString?: never; args?: never } + ) & + ({ line: undefined } | { line: number; lineEnd: number }), + ) => void, + ): void; + + /** clears user created mappings */ + mapclear(ctx?: VimModes): void; + + /** call this before `VimMode.Vim.handleKey` */ + maybeInitVimState_(cma: CMAdapter): void; + + /** + * calls an ex command, equivalent to `:` in vim + * + * *If it fails with `vim is null` call `VimMode.Vim.maybeInitVimState_` first* + */ + handleEx(cma: CMAdapter, ex: string): void; + }; + } + + export { CMAdapter as VimMode, type CMAdapter }; +}