mirror of
https://github.com/kovidgoyal/kitty
synced 2026-07-23 00:38:10 +02:00
Prefer lowercase entries
Also recurse to depth 1 by default. This matches behavior of GUI file select dialogs and prevents perf problems
This commit is contained in:
@@ -249,6 +249,7 @@ func main(_ *cli.Command, opts *Options, args []string) (rc int, err error) {
|
|||||||
default:
|
default:
|
||||||
return 1, fmt.Errorf("Can only specify one directory to search in")
|
return 1, fmt.Errorf("Can only specify one directory to search in")
|
||||||
}
|
}
|
||||||
|
default_cwd = utils.Expanduser(default_cwd)
|
||||||
lp.OnInitialize = handler.OnInitialize
|
lp.OnInitialize = handler.OnInitialize
|
||||||
lp.OnResize = func(old, new_size loop.ScreenSize) (err error) {
|
lp.OnResize = func(old, new_size loop.ScreenSize) (err error) {
|
||||||
handler.init_sizes(new_size)
|
handler.init_sizes(new_size)
|
||||||
|
|||||||
@@ -34,7 +34,7 @@ opt('+exclude_directory', '^/dev$', add_to_default=True)
|
|||||||
opt('+exclude_directory', '^/sys$', add_to_default=True)
|
opt('+exclude_directory', '^/sys$', add_to_default=True)
|
||||||
opt('+exclude_directory', '/__pycache__$', add_to_default=True)
|
opt('+exclude_directory', '/__pycache__$', add_to_default=True)
|
||||||
|
|
||||||
opt('max_depth', '4', option_type='positive_int', long_text='''
|
opt('max_depth', '1', option_type='positive_int', long_text='''
|
||||||
The maximum depth to which to scan the filesystem for matches. Using large values will slow things down considerably. The better
|
The maximum depth to which to scan the filesystem for matches. Using large values will slow things down considerably. The better
|
||||||
approach is to use a small value and first change to the directory of interest then actually select the file of interest.
|
approach is to use a small value and first change to the directory of interest then actually select the file of interest.
|
||||||
''')
|
''')
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ import (
|
|||||||
"sort"
|
"sort"
|
||||||
"strings"
|
"strings"
|
||||||
"sync"
|
"sync"
|
||||||
|
"unicode"
|
||||||
|
|
||||||
"github.com/kovidgoyal/kitty/tools/tui/subseq"
|
"github.com/kovidgoyal/kitty/tools/tui/subseq"
|
||||||
"github.com/kovidgoyal/kitty/tools/utils"
|
"github.com/kovidgoyal/kitty/tools/utils"
|
||||||
@@ -106,11 +107,14 @@ func sort_items_without_search_text(items []ResultItem) (ans []*ResultItem) {
|
|||||||
d := utils.Map(func(x ResultItem) s {
|
d := utils.Map(func(x ResultItem) s {
|
||||||
return s{strings.ToLower(x.text), strings.Count(x.text, "/"), x.dir_entry.IsDir(), hidden_pat.MatchString(x.abspath), &x}
|
return s{strings.ToLower(x.text), strings.Count(x.text, "/"), x.dir_entry.IsDir(), hidden_pat.MatchString(x.abspath), &x}
|
||||||
}, items)
|
}, items)
|
||||||
sort.Slice(d, func(i, j int) bool {
|
sort.SliceStable(d, func(i, j int) bool {
|
||||||
a, b := d[i], d[j]
|
a, b := d[i], d[j]
|
||||||
if a.num_of_slashes == b.num_of_slashes {
|
if a.num_of_slashes == b.num_of_slashes {
|
||||||
if a.is_dir == b.is_dir {
|
if a.is_dir == b.is_dir {
|
||||||
if a.is_hidden == b.is_hidden {
|
if a.is_hidden == b.is_hidden {
|
||||||
|
if a.ltext == b.ltext {
|
||||||
|
return count_uppercase(a.r.text) < count_uppercase(b.r.text)
|
||||||
|
}
|
||||||
return a.ltext < b.ltext
|
return a.ltext < b.ltext
|
||||||
}
|
}
|
||||||
return b.is_hidden
|
return b.is_hidden
|
||||||
@@ -131,6 +135,16 @@ func get_modified_score(r *ResultItem, score float64, score_patterns []ScorePatt
|
|||||||
return score
|
return score
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func count_uppercase(s string) int {
|
||||||
|
count := 0
|
||||||
|
for _, r := range s {
|
||||||
|
if unicode.IsUpper(r) {
|
||||||
|
count++
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return count
|
||||||
|
}
|
||||||
|
|
||||||
func (sc *ScanCache) scan(root_dir, search_text string, max_depth int, exclude_patterns []*regexp.Regexp, score_patterns []ScorePattern) (ans []*ResultItem) {
|
func (sc *ScanCache) scan(root_dir, search_text string, max_depth int, exclude_patterns []*regexp.Regexp, score_patterns []ScorePattern) (ans []*ResultItem) {
|
||||||
seen := make(map[string]bool, 1024)
|
seen := make(map[string]bool, 1024)
|
||||||
matches := sc.fs_scan(root_dir, root_dir, max_depth, exclude_patterns, seen)
|
matches := sc.fs_scan(root_dir, root_dir, max_depth, exclude_patterns, seen)
|
||||||
@@ -155,7 +169,16 @@ func (sc *ScanCache) scan(root_dir, search_text string, max_depth int, exclude_p
|
|||||||
x.positions = m.Positions
|
x.positions = m.Positions
|
||||||
return s{x, get_modified_score(x, m.Score, score_patterns)}
|
return s{x, get_modified_score(x, m.Score, score_patterns)}
|
||||||
}, matches2)
|
}, matches2)
|
||||||
slices.SortFunc(ss, func(a, b s) int { return cmp.Compare(b.score, a.score) })
|
slices.SortStableFunc(ss, func(a, b s) int {
|
||||||
|
ans := cmp.Compare(b.score, a.score)
|
||||||
|
if ans == 0 {
|
||||||
|
ans = cmp.Compare(len(a.r.text), len(b.r.text))
|
||||||
|
if ans == 0 {
|
||||||
|
ans = cmp.Compare(count_uppercase(a.r.text), count_uppercase(b.r.text))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return ans
|
||||||
|
})
|
||||||
return utils.Map(func(s s) *ResultItem { return s.r }, ss)
|
return utils.Map(func(s s) *ResultItem { return s.r }, ss)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -175,7 +198,7 @@ func (h *Handler) get_results() (ans []*ResultItem, in_progress bool) {
|
|||||||
search_text := h.state.SearchText()
|
search_text := h.state.SearchText()
|
||||||
sc.root_dir = root_dir
|
sc.root_dir = root_dir
|
||||||
sc.search_text = search_text
|
sc.search_text = search_text
|
||||||
md, ep, sp := h.state.MaxDepth(), h.state.ExcludePatterns(), h.state.ScorePatterns()
|
md, ep, sp := max(0, h.state.MaxDepth()-1), h.state.ExcludePatterns(), h.state.ScorePatterns()
|
||||||
go func() {
|
go func() {
|
||||||
results := sc.scan(root_dir, search_text, md, ep, sp)
|
results := sc.scan(root_dir, search_text, md, ep, sp)
|
||||||
sc.mutex.Lock()
|
sc.mutex.Lock()
|
||||||
|
|||||||
Reference in New Issue
Block a user