AutoCompleteFunction is back.

This commit is contained in:
Andrey Petrov 2014-12-25 00:37:50 -08:00
parent d3b0a56d78
commit 3bb4bbf991
2 changed files with 31 additions and 15 deletions

View File

@ -83,3 +83,14 @@ func (ch *Channel) Topic() string {
func (ch *Channel) SetTopic(s string) { func (ch *Channel) SetTopic(s string) {
ch.topic = s ch.topic = s
} }
// NamesPrefix lists all members' names with a given prefix, used to query
// for autocompletion purposes.
func (ch *Channel) NamesPrefix(prefix string) []string {
users := ch.users.ListPrefix(prefix)
names := make([]string, len(users))
for i, u := range users {
names[i] = u.(*User).Name()
}
return names
}

35
host.go
View File

@ -3,6 +3,7 @@ package main
import ( import (
"fmt" "fmt"
"io" "io"
"strings"
"github.com/shazow/ssh-chat/chat" "github.com/shazow/ssh-chat/chat"
"github.com/shazow/ssh-chat/sshd" "github.com/shazow/ssh-chat/sshd"
@ -29,7 +30,7 @@ func (h *Host) Connect(term *sshd.Terminal) {
defer term.Close() defer term.Close()
name := term.Conn.User() name := term.Conn.User()
term.SetPrompt(fmt.Sprintf("[%s] ", name)) term.SetPrompt(fmt.Sprintf("[%s] ", name))
// TODO: term.AutoCompleteCallback = ... term.AutoCompleteCallback = h.AutoCompleteFunction
user := chat.NewUserScreen(name, term) user := chat.NewUserScreen(name, term)
defer user.Close() defer user.Close()
@ -70,30 +71,34 @@ func (h *Host) Serve() {
} }
} }
/* TODO: ... // AutoCompleteFunction is a callback for terminal autocompletion
func (h *Host) AutoCompleteFunction(line string, pos int, key rune) (newLine string, newPos int, ok bool) { func (h *Host) AutoCompleteFunction(line string, pos int, key rune) (newLine string, newPos int, ok bool) {
if key != 9 { if key != 9 {
return return
} }
shortLine := strings.Split(line[:pos], " ") fields := strings.Fields(line[:pos])
partialNick := shortLine[len(shortLine)-1] partial := fields[len(fields)-1]
nicks := h.channel.users.ListPrefix(&partialNick) names := h.channel.NamesPrefix(partial)
if len(nicks) == 0 { if len(names) == 0 {
// Didn't find anything
return return
} }
nick := nicks[len(nicks)-1] name := names[len(names)-1]
posPartialNick := pos - len(partialNick) posPartial := pos - len(partial)
if len(shortLine) < 2 {
nick += ": " // Append suffix separator
if len(fields) < 2 {
name += ": "
} else { } else {
nick += " " name += " "
} }
newLine = strings.Replace(line[posPartialNick:], partialNick, nick, 1)
newLine = line[:posPartialNick] + newLine // Reposition the cursor
newPos = pos + (len(nick) - len(partialNick)) newLine = strings.Replace(line[posPartial:], partial, name, 1)
newLine = line[:posPartial] + newLine
newPos = pos + (len(name) - len(partial))
ok = true ok = true
return return
} }
*/