From bb00bdce65e84a6a1bd73865ca61a34f68ee454a Mon Sep 17 00:00:00 2001 From: Sebastian Herrlinger Date: Wed, 27 May 2026 00:28:50 +0200 Subject: [PATCH] first/last --- .../src/cli/cmd/tui/routes/session/index.tsx | 7 ++++++ .../opencode/test/cli/tui/keymap.test.tsx | 22 ++++++++++++++----- 2 files changed, 24 insertions(+), 5 deletions(-) diff --git a/packages/opencode/src/cli/cmd/tui/routes/session/index.tsx b/packages/opencode/src/cli/cmd/tui/routes/session/index.tsx index b6ad8beb86..6af3ca16d2 100644 --- a/packages/opencode/src/cli/cmd/tui/routes/session/index.tsx +++ b/packages/opencode/src/cli/cmd/tui/routes/session/index.tsx @@ -156,6 +156,8 @@ const sessionGlobalBindingCommands = [ "session.half.page.down", ] as const +const sessionGlobalUnfocusedBindingCommands = ["session.first", "session.last"] as const + const context = createContext<{ width: number sessionID: string @@ -1068,6 +1070,11 @@ export function Session() { bindings: tuiConfig.keybinds.gather("session.global", sessionGlobalBindingCommands), })) + useBindings(() => ({ + enabled: () => renderer.currentFocusedEditor === null, + bindings: tuiConfig.keybinds.gather("session.global.unfocused", sessionGlobalUnfocusedBindingCommands), + })) + useBindings(() => ({ mode: OPENCODE_BASE_MODE, bindings: tuiConfig.keybinds.gather("session", sessionBindingCommands), diff --git a/packages/opencode/test/cli/tui/keymap.test.tsx b/packages/opencode/test/cli/tui/keymap.test.tsx index b9300ba4dd..d1ebefb4c1 100644 --- a/packages/opencode/test/cli/tui/keymap.test.tsx +++ b/packages/opencode/test/cli/tui/keymap.test.tsx @@ -71,8 +71,14 @@ test("mode-less bindings stay active when opencode mode changes", async () => { { name: "session.list", run() {} }, { name: "session.new", run() {} }, { name: "session.page.up", run() {} }, + { name: "session.first", run() {} }, ], - bindings: config.keybinds.gather("test.global", ["session.list", "session.new", "session.page.up"]), + bindings: config.keybinds.gather("test.global", [ + "session.list", + "session.new", + "session.page.up", + "session.first", + ]), }) const offBase = keymap.registerLayer({ mode: OPENCODE_BASE_MODE, @@ -84,7 +90,7 @@ test("mode-less bindings stay active when opencode mode changes", async () => { Array.from( keymap.getCommandBindings({ visibility: "active", - commands: ["session.list", "session.new", "session.page.up", "model.list"], + commands: ["session.list", "session.new", "session.page.up", "session.first", "model.list"], }), ([command, bindings]) => [command, bindings.length], ), @@ -114,9 +120,15 @@ test("mode-less bindings stay active when opencode mode changes", async () => { const app = await testRender(() => ) try { expect(counts).toEqual({ - base: { "session.list": 1, "session.new": 1, "session.page.up": 2, "model.list": 1 }, - question: { "session.list": 1, "session.new": 1, "session.page.up": 2, "model.list": 0 }, - autocomplete: { "session.list": 1, "session.new": 1, "session.page.up": 2, "model.list": 0 }, + base: { "session.list": 1, "session.new": 1, "session.page.up": 2, "session.first": 2, "model.list": 1 }, + question: { "session.list": 1, "session.new": 1, "session.page.up": 2, "session.first": 2, "model.list": 0 }, + autocomplete: { + "session.list": 1, + "session.new": 1, + "session.page.up": 2, + "session.first": 2, + "model.list": 0, + }, }) } finally { app.renderer.destroy()