Implement completion for the save file entry prompt

This commit is contained in:
Kovid Goyal
2025-07-11 20:44:51 +05:30
parent 564195f94f
commit 2bd8534df9
2 changed files with 56 additions and 6 deletions

View File

@@ -21,8 +21,6 @@ import (
"github.com/kovidgoyal/kitty/tools/utils"
)
// TODO: save file name completion
var _ = fmt.Print
var debugprintln = tty.DebugPrintln
@@ -378,7 +376,15 @@ func (h *Handler) accept_idx(idx CollectionIndex) (accepted bool, err error) {
return false, nil
}
if s.IsDir() {
return true, h.change_to_current_dir_if_possible()
if h.state.mode.CanSelectNonExistent() {
name := h.state.suggested_save_file_name
if h.state.SearchText() != "" {
name = h.state.SearchText()
}
h.initialize_save_file_name(name)
return true, h.draw_screen()
}
return false, nil
}
}
@@ -721,9 +727,10 @@ func main(_ *cli.Command, opts *Options, args []string) (rc int, err error) {
return 1, err
}
lp.MouseTrackingMode(loop.FULL_MOUSE_TRACKING)
handler := Handler{lp: lp, err_chan: make(chan error, 8), rl: readline.New(lp, readline.RlInit{
Prompt: "> ", ContinuationPrompt: ". ",
})}
handler := Handler{lp: lp, err_chan: make(chan error, 8)}
handler.rl = readline.New(lp, readline.RlInit{
Prompt: "> ", ContinuationPrompt: ". ", Completer: handler.complete_save_prompt,
})
if err = handler.set_state_from_config(conf, opts); err != nil {
return 1, err
}

View File

@@ -4,13 +4,56 @@ import (
"fmt"
"os"
"path/filepath"
"strings"
"github.com/kovidgoyal/kitty/tools/cli"
"github.com/kovidgoyal/kitty/tools/tui/loop"
"github.com/kovidgoyal/kitty/tools/utils"
)
var _ = fmt.Print
func (h *Handler) complete_save_prompt(before_cursor, after_cursor string) *cli.Completions {
path := before_cursor
prefix := ""
if idx := strings.Index(path, string(os.PathSeparator)); idx > -1 {
prefix = filepath.Dir(path) + string(os.PathSeparator)
}
if !filepath.IsAbs(path) {
path = filepath.Join(h.state.CurrentDir(), path)
}
dir := filepath.Dir(path)
if strings.HasSuffix(before_cursor, string(os.PathSeparator)) {
dir = path
}
entries, err := os.ReadDir(dir)
if err != nil {
return nil
}
ans := cli.NewCompletions()
dirs := ans.AddMatchGroup("Directories")
dirs.IsFiles = true
dirs.NoTrailingSpace = true
files := ans.AddMatchGroup("Files")
files.IsFiles = true
files.NoTrailingSpace = true
leading, _ := filepath.Rel(dir, path)
if leading == "." {
leading = ""
}
for _, e := range entries {
word := e.Name()
if leading == "" || strings.HasPrefix(word, leading) {
collection := utils.IfElse(e.Type().IsDir(), dirs, files)
if prefix != "" {
word = prefix + word
}
collection.Matches = append(collection.Matches, &cli.Match{Word: word})
}
}
return ans
}
func (h *Handler) current_save_file_path() string {
ans := h.rl.AllText()
if ans != "" {