feat: add an opt for case insensitive completion

insensitive-tab-2
TorchedSammy 2022-11-30 19:03:45 -04:00
parent b37715f483
commit 8b4766028a
Signed by: sammyette
GPG Key ID: 904FC49417B44DCD
5 changed files with 42 additions and 23 deletions

View File

@ -72,13 +72,13 @@ func splitForFile(str string) []string {
return split return split
} }
func fileComplete(query, ctx string, fields []string) ([]string, string) { func fileComplete(query, ctx string, fields []string, caseInsensitive bool) ([]string, string) {
q := splitForFile(ctx) q := splitForFile(ctx)
return matchPath(q[len(q) - 1]) return matchPath(q[len(q) - 1], caseInsensitive)
} }
func binaryComplete(query, ctx string, fields []string) ([]string, string) { func binaryComplete(query, ctx string, fields []string, caseInsensitive bool) ([]string, string) {
q := splitForFile(ctx) q := splitForFile(ctx)
query = q[len(q) - 1] query = q[len(q) - 1]
@ -87,7 +87,7 @@ func binaryComplete(query, ctx string, fields []string) ([]string, string) {
prefixes := []string{"./", "../", "/", "~/"} prefixes := []string{"./", "../", "/", "~/"}
for _, prefix := range prefixes { for _, prefix := range prefixes {
if strings.HasPrefix(query, prefix) { if strings.HasPrefix(query, prefix) {
fileCompletions, filePref := matchPath(query) fileCompletions, filePref := matchPath(query, caseInsensitive)
if len(fileCompletions) != 0 { if len(fileCompletions) != 0 {
for _, f := range fileCompletions { for _, f := range fileCompletions {
fullPath, _ := filepath.Abs(util.ExpandHome(query + strings.TrimPrefix(f, filePref))) fullPath, _ := filepath.Abs(util.ExpandHome(query + strings.TrimPrefix(f, filePref)))
@ -132,7 +132,7 @@ func binaryComplete(query, ctx string, fields []string) ([]string, string) {
return completions, query return completions, query
} }
func matchPath(query string) ([]string, string) { func matchPath(query string, caseInsensitive bool) ([]string, string) {
oldQuery := query oldQuery := query
query = strings.TrimPrefix(query, "\"") query = strings.TrimPrefix(query, "\"")
var entries []string var entries []string
@ -148,9 +148,17 @@ func matchPath(query string) ([]string, string) {
baseName = filepath.Base(query) baseName = filepath.Base(query)
} }
if caseInsensitive {
baseName = strings.ToLower(baseName)
}
files, _ := os.ReadDir(path) files, _ := os.ReadDir(path)
for _, file := range files { for _, file := range files {
if strings.HasPrefix(strings.ToLower(file.Name()), strings.ToLower(baseName)) { fname := file.Name()
if caseInsensitive {
fname = strings.ToLower(fname)
}
if strings.HasPrefix(fname, baseName) {
entry := file.Name() entry := file.Name()
if file.IsDir() { if file.IsDir() {
entry = entry + string(os.PathSeparator) entry = entry + string(os.PathSeparator)
@ -174,8 +182,8 @@ func escapeFilename(fname string) string {
func completionLoader(rtm *rt.Runtime) *rt.Table { func completionLoader(rtm *rt.Runtime) *rt.Table {
exports := map[string]util.LuaExport{ exports := map[string]util.LuaExport{
"files": {luaFileComplete, 3, false}, "files": {luaFileComplete, 3, true},
"bins": {luaBinaryComplete, 3, false}, "bins": {luaBinaryComplete, 3, true},
"call": {callLuaCompleter, 4, false}, "call": {callLuaCompleter, 4, false},
"handler": {completionHandler, 2, false}, "handler": {completionHandler, 2, false},
} }
@ -231,12 +239,12 @@ func callLuaCompleter(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
} }
func luaFileComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) { func luaFileComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
query, ctx, fds, err := getCompleteParams(t, c) query, ctx, fds, insensitive, err := getCompleteParams(t, c)
if err != nil { if err != nil {
return nil, err return nil, err
} }
completions, pfx := fileComplete(query, ctx, fds) completions, pfx := fileComplete(query, ctx, fds, insensitive)
luaComps := rt.NewTable() luaComps := rt.NewTable()
for i, comp := range completions { for i, comp := range completions {
@ -247,12 +255,12 @@ func luaFileComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
} }
func luaBinaryComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) { func luaBinaryComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
query, ctx, fds, err := getCompleteParams(t, c) query, ctx, fds, insensitive, err := getCompleteParams(t, c)
if err != nil { if err != nil {
return nil, err return nil, err
} }
completions, pfx := binaryComplete(query, ctx, fds) completions, pfx := binaryComplete(query, ctx, fds, insensitive)
luaComps := rt.NewTable() luaComps := rt.NewTable()
for i, comp := range completions { for i, comp := range completions {
@ -262,21 +270,30 @@ func luaBinaryComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
return c.PushingNext(t.Runtime, rt.TableValue(luaComps), rt.StringValue(pfx)), nil return c.PushingNext(t.Runtime, rt.TableValue(luaComps), rt.StringValue(pfx)), nil
} }
func getCompleteParams(t *rt.Thread, c *rt.GoCont) (string, string, []string, error) { func getCompleteParams(t *rt.Thread, c *rt.GoCont) (string, string, []string, bool, error) {
if err := c.CheckNArgs(3); err != nil { if err := c.CheckNArgs(3); err != nil {
return "", "", []string{}, err return "", "", []string{}, false, err
} }
query, err := c.StringArg(0) query, err := c.StringArg(0)
if err != nil { if err != nil {
return "", "", []string{}, err return "", "", []string{}, false, err
} }
ctx, err := c.StringArg(1) ctx, err := c.StringArg(1)
if err != nil { if err != nil {
return "", "", []string{}, err return "", "", []string{}, false, err
} }
fields, err := c.TableArg(2) fields, err := c.TableArg(2)
if err != nil { if err != nil {
return "", "", []string{}, err return "", "", []string{}, false, err
}
var insensitive bool
if len(c.Etc()) != 0 {
typ := c.Etc()[0]
var ok bool
insensitive, ok = typ.TryBool()
if !ok {
return "", "", []string{}, false, errors.New("bad argument #4 (expected bool, got " + typ.TypeName() + ")")
}
} }
var fds []string var fds []string
@ -286,5 +303,5 @@ func getCompleteParams(t *rt.Thread, c *rt.GoCont) (string, string, []string, er
} }
}) })
return query, ctx, fds, err return query, ctx, fds, insensitive, err
} }

View File

@ -36,9 +36,9 @@ then there is the `files` function, which is mentioned below.
# Completion Interface # Completion Interface
## Functions ## Functions
- `files(query, ctx, fields)` -> table, prefix: get file completions, based - `files(query, ctx, fields, caseInsensitive)` -> table, prefix: get file completions, based
on the user's query. on the user's query.
- `bins(query, ctx, fields)` -> table, prefix: get binary/executable - `bins(query, ctx, fields, caseInsensitive)` -> table, prefix: get binary/executable
completions, based on user query. completions, based on user query.
- `call(scope, query, ctx, fields)` -> table, prefix: call a completion handler - `call(scope, query, ctx, fields)` -> table, prefix: call a completion handler
with `scope`, usually being in the form of `command.<name>` with `scope`, usually being in the form of `command.<name>`

View File

@ -15,7 +15,7 @@ function hilbish.completion.handler(line, pos)
local query = fields[#fields] local query = fields[#fields]
if #fields == 1 then if #fields == 1 then
local comps, pfx = hilbish.completion.bins(query, ctx, fields) local comps, pfx = hilbish.completion.bins(query, ctx, fields, hilbish.opts.insensitive)
local compGroup = { local compGroup = {
items = comps, items = comps,
type = 'grid' type = 'grid'
@ -29,7 +29,7 @@ function hilbish.completion.handler(line, pos)
return compGroups, pfx return compGroups, pfx
end end
local comps, pfx = hilbish.completion.files(query, ctx, fields) local comps, pfx = hilbish.completion.files(query, ctx, fields, hilbish.opts.insensitive)
local compGroup = { local compGroup = {
items = comps, items = comps,
type = 'grid' type = 'grid'

View File

@ -25,7 +25,8 @@ local defaultOpts = {
greeting = string.format([[Welcome to {magenta}Hilbish{reset}, {cyan}%s{reset}. greeting = string.format([[Welcome to {magenta}Hilbish{reset}, {cyan}%s{reset}.
The nice lil shell for {blue}Lua{reset} fanatics! The nice lil shell for {blue}Lua{reset} fanatics!
]], hilbish.user), ]], hilbish.user),
motd = true motd = true,
insensitive = true
} }
for optsName, default in pairs(defaultOpts) do for optsName, default in pairs(defaultOpts) do

View File

@ -0,0 +1 @@
-- noop