on main help sign in
chore: change open editor
commit28be096bae6c2dd042256d0f8c9980848326fdc0 authorKujtim Hoxha <kujtimii.h@gmail.com> dateTue 29 Jul 2025, 13:15 (1 year ago) parent87bd72b
5 files changed+44−4
internal/tui/components/chat/editor/editor.go+12 internal/tui/components/chat/editor/keys.go+2−2 internal/tui/components/dialogs/commands/commands.go+16 internal/tui/page/chat/chat.go+11−2 internal/tui/tui.go+3
internal/tui/components/chat/editor/editor.go+12
@@ -22,6 +22,7 @@ import (
2222 "github.com/charmbracelet/crush/internal/tui/components/completions"
2323 "github.com/charmbracelet/crush/internal/tui/components/core/layout"
2424 "github.com/charmbracelet/crush/internal/tui/components/dialogs"
25+ "github.com/charmbracelet/crush/internal/tui/components/dialogs/commands"
2526 "github.com/charmbracelet/crush/internal/tui/components/dialogs/filepicker"
2627 "github.com/charmbracelet/crush/internal/tui/components/dialogs/quit"
2728 "github.com/charmbracelet/crush/internal/tui/styles"
@@ -38,6 +39,7 @@ type Editor interface {
3839
3940 SetSession(session session.Session) tea.Cmd
4041 IsCompletionsOpen() bool
42+ HasAttachments() bool
4143 Cursor() *tea.Cursor
4244}
4345
@@ -206,6 +208,12 @@ func (m *editorCmp) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
206208 m.completionsStartIndex = 0
207209 }
208210 }
211+
212+ case commands.OpenExternalEditorMsg:
213+ if m.app.CoderAgent.IsSessionBusy(m.session.ID) {
214+ return m, util.ReportWarn("Agent is working, please wait...")
215+ }
216+ return m, m.openEditor(m.textarea.Value())
209217 case OpenEditorMsg:
210218 m.textarea.SetValue(msg.Text)
211219 m.textarea.MoveToEnd()
@@ -482,6 +490,10 @@ func (c *editorCmp) IsCompletionsOpen() bool {
482490 return c.isCompletionsOpen
483491}
484492
493+func (c *editorCmp) HasAttachments() bool {
494+ return len(c.attachments) > 0
495+}
496+
485497func New(app *app.App) Editor {
486498 t := styles.CurrentTheme()
487499 ta := textarea.New()
internal/tui/components/chat/editor/keys.go+2−2
@@ -22,8 +22,8 @@ func DefaultEditorKeyMap() EditorKeyMap {
2222 key.WithHelp("enter", "send"),
2323 ),
2424 OpenEditor: key.NewBinding(
25− key.WithKeys("ctrl+v"),
26− key.WithHelp("ctrl+v", "open editor"),
25+ key.WithKeys("ctrl+o"),
26+ key.WithHelp("ctrl+o", "open editor"),
2727 ),
2828 Newline: key.NewBinding(
2929 key.WithKeys("shift+enter", "ctrl+j"),
internal/tui/components/dialogs/commands/commands.go+16
@@ -1,6 +1,8 @@
11package commands
22
33import (
4+ "os"
5+
46 "github.com/charmbracelet/bubbles/v2/help"
57 "github.com/charmbracelet/bubbles/v2/key"
68 tea "github.com/charmbracelet/bubbletea/v2"
@@ -66,6 +68,7 @@ type (
6668 ToggleHelpMsg struct{}
6769 ToggleCompactModeMsg struct{}
6870 ToggleThinkingMsg struct{}
71+ OpenExternalEditorMsg struct{}
6972 CompactMsg struct {
7073 SessionID string
7174 }
@@ -343,6 +346,19 @@ func (c *commandDialogCmp) defaultCommands() []Command {
343346 }
344347 }
345348
349+ // Add external editor command if $EDITOR is available
350+ if os.Getenv("EDITOR") != "" {
351+ commands = append(commands, Command{
352+ ID: "open_external_editor",
353+ Title: "Open External Editor",
354+ Shortcut: "ctrl+o",
355+ Description: "Open external editor to compose message",
356+ Handler: func(cmd Command) tea.Cmd {
357+ return util.CmdHandler(OpenExternalEditorMsg{})
358+ },
359+ })
360+ }
361+
346362 return append(commands, []Command{
347363 {
348364 ID: "toggle_help",
internal/tui/page/chat/chat.go+11−2
@@ -204,6 +204,10 @@ func (p *chatPage) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
204204 return p, tea.Batch(p.SetSize(p.width, p.height), cmd)
205205 case commands.ToggleThinkingMsg:
206206 return p, p.toggleThinking()
207+ case commands.OpenExternalEditorMsg:
208+ u, cmd := p.editor.Update(msg)
209+ p.editor = u.(editor.Editor)
210+ return p, cmd
207211 case pubsub.Event[session.Session]:
208212 u, cmd := p.header.Update(msg)
209213 p.header = u.(header.Header)
@@ -896,9 +900,13 @@ func (p *chatPage) Help() help.KeyMap {
896900 key.WithHelp("/", "add file"),
897901 ),
898902 key.NewBinding(
899− key.WithKeys("ctrl+v"),
900− key.WithHelp("ctrl+v", "open editor"),
903+ key.WithKeys("ctrl+o"),
904+ key.WithHelp("ctrl+o", "open editor"),
901905 ),
906+ })
907+
908+ if p.editor.HasAttachments() {
909+ fullList = append(fullList, []key.Binding{
902910 key.NewBinding(
903911 key.WithKeys("ctrl+r"),
904912 key.WithHelp("ctrl+r+{i}", "delete attachment at index i"),
@@ -912,6 +920,7 @@ func (p *chatPage) Help() help.KeyMap {
912920 key.WithHelp("esc", "cancel delete mode"),
913921 ),
914922 })
923+ }
915924 }
916925 shortList = append(shortList,
917926 // Quit
internal/tui/tui.go+3
@@ -3,6 +3,7 @@ package tui
33import (
44 "context"
55 "fmt"
6+ "log/slog"
67 "strings"
78 "time"
89
@@ -258,6 +259,8 @@ func (a *appModel) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
258259 return a, tea.Batch(cmds...)
259260 // Key Press Messages
260261 case tea.KeyPressMsg:
262+
263+ slog.Info("TUI Update", "msg", msg, "key", msg.String())
261264 return a, a.handleKeyPressMsg(msg)
262265
263266 case tea.MouseWheelMsg: