aerc: replace tcell keys with vaxis keys

Replace all instances of tcell key usage with vaxis keys

Signed-off-by: Tim Culverhouse <tim@timculverhouse.com>
Acked-by: Robin Jarry <robin@jarry.cc>
This commit is contained in:
Tim Culverhouse
2024-02-12 06:26:19 -06:00
committed by Robin Jarry
parent f001f65240
commit cdc90afbaa
12 changed files with 370 additions and 347 deletions

View File

@@ -13,7 +13,6 @@ import (
"sync"
"github.com/emersion/go-message/mail"
"github.com/gdamore/tcell/v2"
"github.com/go-ini/ini"
"golang.org/x/sys/unix"
@@ -750,13 +749,11 @@ func (wizard *AccountWizard) Focus(focus bool) {
func (wizard *AccountWizard) Event(event vaxis.Event) bool {
interactive := wizard.getInteractive()
if event, ok := event.(*tcell.EventKey); ok {
switch event.Key() {
case tcell.KeyUp:
fallthrough
case tcell.KeyBacktab:
fallthrough
case tcell.KeyCtrlK:
if key, ok := event.(vaxis.Key); ok {
switch {
case key.Matches('k', vaxis.ModCtrl),
key.Matches(vaxis.KeyTab, vaxis.ModShift),
key.Matches(vaxis.KeyUp):
if interactive != nil {
interactive[wizard.focus].Focus(false)
wizard.focus--
@@ -767,11 +764,10 @@ func (wizard *AccountWizard) Event(event vaxis.Event) bool {
}
wizard.Invalidate()
return true
case tcell.KeyDown:
fallthrough
case tcell.KeyTab:
fallthrough
case tcell.KeyCtrlJ:
case key.Matches('j', vaxis.ModCtrl),
key.Matches(vaxis.KeyTab),
key.Matches(vaxis.KeyDown):
if interactive != nil {
interactive[wizard.focus].Focus(false)
wizard.focus++

View File

@@ -9,6 +9,7 @@ import (
"sort"
"strings"
"time"
"unicode"
"git.sr.ht/~rjarry/go-opt"
"git.sr.ht/~rockorager/vaxis"
@@ -230,7 +231,7 @@ func (aerc *Aerc) HumanReadableBindings() []string {
}
result = append(result, fmt.Sprintf(fmtStr,
"$ex",
fmt.Sprintf("'%c'", binds.ExKey.Rune), "",
fmt.Sprintf("'%c'", binds.ExKey.Key), "",
))
result = append(result, fmt.Sprintf(fmtStr,
"Globals",
@@ -288,8 +289,23 @@ func (aerc *Aerc) simulate(strokes []config.KeyStroke) {
aerc.simulating += 1
for _, stroke := range strokes {
simulated := tcell.NewEventKey(
stroke.Key, stroke.Rune, stroke.Modifiers)
simulated := vaxis.Key{
Keycode: stroke.Key,
Modifiers: stroke.Modifiers,
}
if unicode.IsUpper(stroke.Key) {
simulated.Keycode = unicode.ToLower(stroke.Key)
simulated.Modifiers |= vaxis.ModShift
}
// If none of these mods are present, set the text field to
// enable matching keys like ":"
if stroke.Modifiers&vaxis.ModCtrl == 0 &&
stroke.Modifiers&vaxis.ModAlt == 0 &&
stroke.Modifiers&vaxis.ModSuper == 0 &&
stroke.Modifiers&vaxis.ModHyper == 0 {
simulated.Text = string(stroke.Key)
}
aerc.Event(simulated)
complete = stroke == bindings.CompleteKey
}
@@ -301,10 +317,7 @@ func (aerc *Aerc) simulate(strokes []config.KeyStroke) {
})
if complete {
// force completion now
exline.Event(tcell.NewEventKey(
bindings.CompleteKey.Key,
bindings.CompleteKey.Rune,
bindings.CompleteKey.Modifiers))
exline.Event(vaxis.Key{Keycode: vaxis.KeyTab})
}
}
}
@@ -319,7 +332,8 @@ func (aerc *Aerc) Event(event vaxis.Event) bool {
}
switch event := event.(type) {
case *tcell.EventKey:
// TODO: more vaxis events handling
case vaxis.Key:
// If we are in a bracketed paste, don't process the keys for
// bindings
if aerc.pasting {
@@ -330,11 +344,17 @@ func (aerc *Aerc) Event(event vaxis.Event) bool {
return false
}
aerc.statusline.Expire()
aerc.pendingKeys = append(aerc.pendingKeys, config.KeyStroke{
Modifiers: event.Modifiers(),
Key: event.Key(),
Rune: event.Rune(),
})
stroke := config.KeyStroke{
Modifiers: event.Modifiers,
}
switch {
case event.ShiftedCode != 0:
stroke.Key = event.ShiftedCode
stroke.Modifiers &^= vaxis.ModShift
default:
stroke.Key = event.Keycode
}
aerc.pendingKeys = append(aerc.pendingKeys, stroke)
ui.Invalidate()
bindings := aerc.getBindings()
incomplete := false
@@ -887,12 +907,8 @@ func errorScreen(s string) ui.Drawable {
return grid
}
func (aerc *Aerc) isExKey(event *tcell.EventKey, exKey config.KeyStroke) bool {
if event.Key() == tcell.KeyRune {
// Compare runes if it's a KeyRune
return event.Modifiers() == exKey.Modifiers && event.Rune() == exKey.Rune
}
return event.Modifiers() == exKey.Modifiers && event.Key() == exKey.Key
func (aerc *Aerc) isExKey(key vaxis.Key, exKey config.KeyStroke) bool {
return key.Matches(exKey.Key, exKey.Modifiers)
}
// CmdFallbackSearch checks cmds for the first executable availabe in PATH. An error is

View File

@@ -1,8 +1,6 @@
package app
import (
"github.com/gdamore/tcell/v2"
"git.sr.ht/~rjarry/aerc/config"
"git.sr.ht/~rjarry/aerc/lib"
"git.sr.ht/~rjarry/aerc/lib/ui"
@@ -83,20 +81,20 @@ func (ex *ExLine) Focus(focus bool) {
}
func (ex *ExLine) Event(event vaxis.Event) bool {
if event, ok := event.(*tcell.EventKey); ok {
switch event.Key() {
case tcell.KeyEnter, tcell.KeyCtrlJ:
if key, ok := event.(vaxis.Key); ok {
switch {
case key.Matches(vaxis.KeyEnter), key.Matches('j', vaxis.ModCtrl):
cmd := ex.input.String()
ex.input.Focus(false)
ex.commit(cmd)
ex.finish()
case tcell.KeyUp:
case key.Matches(vaxis.KeyUp):
ex.input.Set(ex.cmdHistory.Prev())
ex.Invalidate()
case tcell.KeyDown:
case key.Matches(vaxis.KeyDown):
ex.input.Set(ex.cmdHistory.Next())
ex.Invalidate()
case tcell.KeyEsc, tcell.KeyCtrlC:
case key.Matches(vaxis.KeyEsc), key.Matches('c', vaxis.ModCtrl):
ex.input.Focus(false)
ex.cmdHistory.Reset()
ex.finish()

View File

@@ -3,8 +3,6 @@ package app
import (
"fmt"
"github.com/gdamore/tcell/v2"
"git.sr.ht/~rjarry/aerc/config"
"git.sr.ht/~rjarry/aerc/lib/ui"
"git.sr.ht/~rockorager/vaxis"
@@ -47,12 +45,12 @@ func (gp *GetPasswd) Invalidate() {
func (gp *GetPasswd) Event(event vaxis.Event) bool {
switch event := event.(type) {
case *tcell.EventKey:
switch event.Key() {
case tcell.KeyEnter:
case vaxis.Key:
switch {
case event.Matches(vaxis.KeyEnter):
gp.input.Focus(false)
gp.callback(gp.input.String(), nil)
case tcell.KeyEsc:
case event.Matches(vaxis.KeyEsc):
gp.input.Focus(false)
gp.callback("", fmt.Errorf("no password provided"))
default:

View File

@@ -231,59 +231,79 @@ func (lb *ListBox) Invalidate() {
func (lb *ListBox) Event(event vaxis.Event) bool {
showFilter := lb.showFilterField()
if event, ok := event.(*tcell.EventKey); ok {
switch event.Key() {
case tcell.KeyLeft:
if key, ok := event.(vaxis.Key); ok {
switch {
case key.Matches(vaxis.KeyLeft):
if showFilter {
break
}
lb.moveHorizontal(-1)
lb.Invalidate()
return true
case tcell.KeyRight:
case key.Matches(vaxis.KeyRight):
if showFilter {
break
}
lb.moveHorizontal(+1)
lb.Invalidate()
return true
case tcell.KeyCtrlA, tcell.KeyHome:
case key.Matches('b', vaxis.ModCtrl):
line := lb.selected[:lb.horizPos]
fds := strings.Fields(line)
if len(fds) > 1 {
lb.moveHorizontal(
strings.LastIndex(line,
fds[len(fds)-1]) - lb.horizPos - 1)
} else {
lb.horizPos = 0
}
lb.Invalidate()
return true
case key.Matches('w', vaxis.ModCtrl):
line := lb.selected[lb.horizPos+1:]
fds := strings.Fields(line)
if len(fds) > 1 {
lb.moveHorizontal(strings.Index(line, fds[1]))
}
lb.Invalidate()
return true
case key.Matches('a', vaxis.ModCtrl), key.Matches(vaxis.KeyHome):
if showFilter {
break
}
lb.horizPos = 0
lb.Invalidate()
return true
case tcell.KeyCtrlE, tcell.KeyEnd:
case key.Matches('e', vaxis.ModCtrl), key.Matches(vaxis.KeyEnd):
if showFilter {
break
}
lb.horizPos = len(lb.selected)
lb.Invalidate()
return true
case tcell.KeyCtrlP, tcell.KeyUp, tcell.KeyBacktab:
case key.Matches('p', vaxis.ModCtrl), key.Matches(vaxis.KeyUp):
lb.moveCursor(-1)
lb.Invalidate()
return true
case tcell.KeyCtrlN, tcell.KeyDown, tcell.KeyTab:
case key.Matches('n', vaxis.ModCtrl), key.Matches(vaxis.KeyDown):
lb.moveCursor(+1)
lb.Invalidate()
return true
case tcell.KeyPgUp:
case key.Matches(vaxis.KeyPgUp):
if lb.jump >= 0 {
lb.moveCursor(-lb.jump)
lb.Invalidate()
}
return true
case tcell.KeyPgDn:
case key.Matches(vaxis.KeyPgDown):
if lb.jump >= 0 {
lb.moveCursor(+lb.jump)
lb.Invalidate()
}
return true
case tcell.KeyEnter:
case key.Matches(vaxis.KeyEnter):
return lb.quit(lb.selected)
case tcell.KeyEsc:
case key.Matches(vaxis.KeyEsc):
return lb.quit("")
}
}

View File

@@ -4,7 +4,6 @@ import (
"fmt"
"strings"
"github.com/gdamore/tcell/v2"
"github.com/mattn/go-runewidth"
"git.sr.ht/~rjarry/aerc/config"
@@ -145,11 +144,11 @@ func (sel *Selector) Focus(focus bool) {
}
func (sel *Selector) Event(event vaxis.Event) bool {
if event, ok := event.(*tcell.EventKey); ok {
switch event.Key() {
case tcell.KeyCtrlH:
if key, ok := event.(vaxis.Key); ok {
switch {
case key.Matches('h', vaxis.ModCtrl):
fallthrough
case tcell.KeyLeft:
case key.Matches(vaxis.KeyLeft):
if sel.focus > 0 {
sel.focus--
sel.Invalidate()
@@ -157,9 +156,9 @@ func (sel *Selector) Event(event vaxis.Event) bool {
if sel.onSelect != nil {
sel.onSelect(sel.Selected())
}
case tcell.KeyCtrlL:
case key.Matches('l', vaxis.ModCtrl):
fallthrough
case tcell.KeyRight:
case key.Matches(vaxis.KeyRight):
if sel.focus < len(sel.options)-1 {
sel.focus++
sel.Invalidate()
@@ -167,7 +166,7 @@ func (sel *Selector) Event(event vaxis.Event) bool {
if sel.onSelect != nil {
sel.onSelect(sel.Selected())
}
case tcell.KeyEnter:
case key.Matches(vaxis.KeyEnter):
if sel.onChoose != nil {
sel.onChoose(sel.Selected())
}
@@ -242,12 +241,12 @@ func (gp *SelectorDialog) Invalidate() {
func (gp *SelectorDialog) Event(event vaxis.Event) bool {
switch event := event.(type) {
case *tcell.EventKey:
switch event.Key() {
case tcell.KeyEnter:
case vaxis.Key:
switch {
case event.Matches(vaxis.KeyEnter):
gp.selector.Focus(false)
gp.callback(gp.selector.Selected(), nil)
case tcell.KeyEsc:
case event.Matches(vaxis.KeyEsc):
gp.selector.Focus(false)
gp.callback("", ErrNoOptionSelected)
default:

View File

@@ -176,6 +176,7 @@ func (term *Terminal) HandleEvent(ev tcell.Event) {
}
func (term *Terminal) Event(event vaxis.Event) bool {
event = tcell.TcellEvent(event)
if term.OnEvent != nil {
if term.OnEvent(event) {
return true

View File

@@ -3,7 +3,7 @@ package commands
import (
"git.sr.ht/~rjarry/aerc/app"
"git.sr.ht/~rjarry/aerc/config"
"github.com/gdamore/tcell/v2"
"git.sr.ht/~rockorager/vaxis"
"github.com/pkg/errors"
)
@@ -40,7 +40,10 @@ func (s SendKeys) Execute(args []string) error {
}
for _, key := range keys2send {
ev := tcell.NewEventKey(key.Key, key.Rune, key.Modifiers)
ev := vaxis.Key{
Keycode: key.Key,
Modifiers: key.Modifiers,
}
term.Event(ev)
}

View File

@@ -9,9 +9,10 @@ import (
"path"
"regexp"
"strings"
"unicode"
"git.sr.ht/~rjarry/aerc/log"
"github.com/gdamore/tcell/v2"
"git.sr.ht/~rockorager/vaxis"
"github.com/go-ini/ini"
)
@@ -41,9 +42,8 @@ type BindingConfigContext struct {
}
type KeyStroke struct {
Modifiers tcell.ModMask
Key tcell.Key
Rune rune
Modifiers vaxis.ModifierMask
Key rune
}
type Binding struct {
@@ -84,7 +84,7 @@ type BindingSearchResult int
func defaultBindsConfig() *BindingConfig {
// These bindings are not configurable
wizard := NewKeyBindings()
wizard.ExKey = KeyStroke{Key: tcell.KeyCtrlE}
wizard.ExKey = KeyStroke{Key: 'e', Modifiers: vaxis.ModCtrl}
wizard.Globals = false
quit, _ := ParseBinding("<C-q>", ":quit<Enter>", "Quit aerc")
wizard.Add(quit)
@@ -296,8 +296,8 @@ func LoadBinds(binds *ini.File, baseName string, baseGroup **KeyBindings) error
func NewKeyBindings() *KeyBindings {
return &KeyBindings{
ExKey: KeyStroke{tcell.ModNone, tcell.KeyRune, ':'},
CompleteKey: KeyStroke{tcell.ModNone, tcell.KeyTab, 0},
ExKey: KeyStroke{0, ':'},
CompleteKey: KeyStroke{0, vaxis.KeyTab},
Globals: true,
contextualCache: make(map[bindsContextKey]*KeyBindings),
contextualCounts: make(map[bindsContextType]int),
@@ -425,11 +425,6 @@ func (bindings *KeyBindings) GetBinding(
if stroke.Key != binding.Input[i].Key {
goto next
}
if stroke.Key == tcell.KeyRune &&
stroke.Rune != binding.Input[i].Rune {
goto next
}
}
if len(binding.Input) != len(input) {
incomplete = true
@@ -458,9 +453,6 @@ func (bindings *KeyBindings) GetReverseBindings(output []KeyStroke) [][]KeyStrok
if stroke.Key != binding.Output[i].Key {
goto next
}
if stroke.Key == tcell.KeyRune && stroke.Rune != binding.Output[i].Rune {
goto next
}
}
inputs = append(inputs, binding.Input)
next:
@@ -474,7 +466,7 @@ func FormatKeyStrokes(keystrokes []KeyStroke) string {
for _, stroke := range keystrokes {
s := ""
for name, ks := range keyNames {
if ks.Modifiers == stroke.Modifiers && ks.Key == stroke.Key && ks.Rune == stroke.Rune {
if ks.Modifiers == stroke.Modifiers && ks.Key == stroke.Key {
switch name {
case "cr", "c-m":
s = "<enter>"
@@ -490,8 +482,8 @@ func FormatKeyStrokes(keystrokes []KeyStroke) string {
break
}
}
if s == "" && stroke.Key == tcell.KeyRune {
s = string(stroke.Rune)
if s == "" && stroke.Key < unicode.MaxRune {
s = string(stroke.Key)
}
sb.WriteString(s)
}
@@ -511,219 +503,218 @@ func FormatKeyStrokes(keystrokes []KeyStroke) string {
var spaceTrimRe = regexp.MustCompile(`^(\s*)(.*?)(\s*)$`)
var keyNames = map[string]KeyStroke{
"space": {tcell.ModNone, tcell.KeyRune, ' '},
"semicolon": {tcell.ModNone, tcell.KeyRune, ';'},
"enter": {tcell.ModNone, tcell.KeyEnter, 0},
"c-enter": {tcell.ModCtrl, tcell.KeyEnter, 0},
"a-enter": {tcell.ModAlt, tcell.KeyEnter, 0},
"up": {tcell.ModNone, tcell.KeyUp, 0},
"c-up": {tcell.ModCtrl, tcell.KeyUp, 0},
"a-up": {tcell.ModAlt, tcell.KeyUp, 0},
"down": {tcell.ModNone, tcell.KeyDown, 0},
"c-down": {tcell.ModCtrl, tcell.KeyDown, 0},
"a-down": {tcell.ModAlt, tcell.KeyDown, 0},
"right": {tcell.ModNone, tcell.KeyRight, 0},
"c-right": {tcell.ModCtrl, tcell.KeyRight, 0},
"a-right": {tcell.ModAlt, tcell.KeyRight, 0},
"left": {tcell.ModNone, tcell.KeyLeft, 0},
"c-left": {tcell.ModCtrl, tcell.KeyLeft, 0},
"a-left": {tcell.ModAlt, tcell.KeyLeft, 0},
"upleft": {tcell.ModNone, tcell.KeyUpLeft, 0},
"upright": {tcell.ModNone, tcell.KeyUpRight, 0},
"downleft": {tcell.ModNone, tcell.KeyDownLeft, 0},
"downright": {tcell.ModNone, tcell.KeyDownRight, 0},
"center": {tcell.ModNone, tcell.KeyCenter, 0},
"pgup": {tcell.ModNone, tcell.KeyPgUp, 0},
"c-pgup": {tcell.ModCtrl, tcell.KeyPgUp, 0},
"a-pgup": {tcell.ModAlt, tcell.KeyPgUp, 0},
"pgdn": {tcell.ModNone, tcell.KeyPgDn, 0},
"c-pgdn": {tcell.ModCtrl, tcell.KeyPgDn, 0},
"a-pgdn": {tcell.ModAlt, tcell.KeyPgDn, 0},
"home": {tcell.ModNone, tcell.KeyHome, 0},
"end": {tcell.ModNone, tcell.KeyEnd, 0},
"insert": {tcell.ModNone, tcell.KeyInsert, 0},
"delete": {tcell.ModNone, tcell.KeyDelete, 0},
"c-delete": {tcell.ModCtrl, tcell.KeyDelete, 0},
"a-delete": {tcell.ModAlt, tcell.KeyDelete, 0},
"backspace": {tcell.ModNone, tcell.KeyBackspace2, 0},
"help": {tcell.ModNone, tcell.KeyHelp, 0},
"exit": {tcell.ModNone, tcell.KeyExit, 0},
"clear": {tcell.ModNone, tcell.KeyClear, 0},
"cancel": {tcell.ModNone, tcell.KeyCancel, 0},
"print": {tcell.ModNone, tcell.KeyPrint, 0},
"pause": {tcell.ModNone, tcell.KeyPause, 0},
"backtab": {tcell.ModNone, tcell.KeyBacktab, 0},
"f1": {tcell.ModNone, tcell.KeyF1, 0},
"f2": {tcell.ModNone, tcell.KeyF2, 0},
"f3": {tcell.ModNone, tcell.KeyF3, 0},
"f4": {tcell.ModNone, tcell.KeyF4, 0},
"f5": {tcell.ModNone, tcell.KeyF5, 0},
"f6": {tcell.ModNone, tcell.KeyF6, 0},
"f7": {tcell.ModNone, tcell.KeyF7, 0},
"f8": {tcell.ModNone, tcell.KeyF8, 0},
"f9": {tcell.ModNone, tcell.KeyF9, 0},
"f10": {tcell.ModNone, tcell.KeyF10, 0},
"f11": {tcell.ModNone, tcell.KeyF11, 0},
"f12": {tcell.ModNone, tcell.KeyF12, 0},
"f13": {tcell.ModNone, tcell.KeyF13, 0},
"f14": {tcell.ModNone, tcell.KeyF14, 0},
"f15": {tcell.ModNone, tcell.KeyF15, 0},
"f16": {tcell.ModNone, tcell.KeyF16, 0},
"f17": {tcell.ModNone, tcell.KeyF17, 0},
"f18": {tcell.ModNone, tcell.KeyF18, 0},
"f19": {tcell.ModNone, tcell.KeyF19, 0},
"f20": {tcell.ModNone, tcell.KeyF20, 0},
"f21": {tcell.ModNone, tcell.KeyF21, 0},
"f22": {tcell.ModNone, tcell.KeyF22, 0},
"f23": {tcell.ModNone, tcell.KeyF23, 0},
"f24": {tcell.ModNone, tcell.KeyF24, 0},
"f25": {tcell.ModNone, tcell.KeyF25, 0},
"f26": {tcell.ModNone, tcell.KeyF26, 0},
"f27": {tcell.ModNone, tcell.KeyF27, 0},
"f28": {tcell.ModNone, tcell.KeyF28, 0},
"f29": {tcell.ModNone, tcell.KeyF29, 0},
"f30": {tcell.ModNone, tcell.KeyF30, 0},
"f31": {tcell.ModNone, tcell.KeyF31, 0},
"f32": {tcell.ModNone, tcell.KeyF32, 0},
"f33": {tcell.ModNone, tcell.KeyF33, 0},
"f34": {tcell.ModNone, tcell.KeyF34, 0},
"f35": {tcell.ModNone, tcell.KeyF35, 0},
"f36": {tcell.ModNone, tcell.KeyF36, 0},
"f37": {tcell.ModNone, tcell.KeyF37, 0},
"f38": {tcell.ModNone, tcell.KeyF38, 0},
"f39": {tcell.ModNone, tcell.KeyF39, 0},
"f40": {tcell.ModNone, tcell.KeyF40, 0},
"f41": {tcell.ModNone, tcell.KeyF41, 0},
"f42": {tcell.ModNone, tcell.KeyF42, 0},
"f43": {tcell.ModNone, tcell.KeyF43, 0},
"f44": {tcell.ModNone, tcell.KeyF44, 0},
"f45": {tcell.ModNone, tcell.KeyF45, 0},
"f46": {tcell.ModNone, tcell.KeyF46, 0},
"f47": {tcell.ModNone, tcell.KeyF47, 0},
"f48": {tcell.ModNone, tcell.KeyF48, 0},
"f49": {tcell.ModNone, tcell.KeyF49, 0},
"f50": {tcell.ModNone, tcell.KeyF50, 0},
"f51": {tcell.ModNone, tcell.KeyF51, 0},
"f52": {tcell.ModNone, tcell.KeyF52, 0},
"f53": {tcell.ModNone, tcell.KeyF53, 0},
"f54": {tcell.ModNone, tcell.KeyF54, 0},
"f55": {tcell.ModNone, tcell.KeyF55, 0},
"f56": {tcell.ModNone, tcell.KeyF56, 0},
"f57": {tcell.ModNone, tcell.KeyF57, 0},
"f58": {tcell.ModNone, tcell.KeyF58, 0},
"f59": {tcell.ModNone, tcell.KeyF59, 0},
"f60": {tcell.ModNone, tcell.KeyF60, 0},
"f61": {tcell.ModNone, tcell.KeyF61, 0},
"f62": {tcell.ModNone, tcell.KeyF62, 0},
"f63": {tcell.ModNone, tcell.KeyF63, 0},
"f64": {tcell.ModNone, tcell.KeyF64, 0},
"c-space": {tcell.ModCtrl, tcell.KeyCtrlSpace, 0},
"c-a": {tcell.ModCtrl, tcell.KeyCtrlA, 0},
"c-b": {tcell.ModCtrl, tcell.KeyCtrlB, 0},
"c-c": {tcell.ModCtrl, tcell.KeyCtrlC, 0},
"c-d": {tcell.ModCtrl, tcell.KeyCtrlD, 0},
"c-e": {tcell.ModCtrl, tcell.KeyCtrlE, 0},
"c-f": {tcell.ModCtrl, tcell.KeyCtrlF, 0},
"c-g": {tcell.ModCtrl, tcell.KeyCtrlG, 0},
"c-h": {tcell.ModNone, tcell.KeyCtrlH, 0},
"c-i": {tcell.ModNone, tcell.KeyCtrlI, 0},
"c-j": {tcell.ModCtrl, tcell.KeyCtrlJ, 0},
"c-k": {tcell.ModCtrl, tcell.KeyCtrlK, 0},
"c-l": {tcell.ModCtrl, tcell.KeyCtrlL, 0},
"c-m": {tcell.ModNone, tcell.KeyCtrlM, 0},
"c-n": {tcell.ModCtrl, tcell.KeyCtrlN, 0},
"c-o": {tcell.ModCtrl, tcell.KeyCtrlO, 0},
"c-p": {tcell.ModCtrl, tcell.KeyCtrlP, 0},
"c-q": {tcell.ModCtrl, tcell.KeyCtrlQ, 0},
"c-r": {tcell.ModCtrl, tcell.KeyCtrlR, 0},
"c-s": {tcell.ModCtrl, tcell.KeyCtrlS, 0},
"c-t": {tcell.ModCtrl, tcell.KeyCtrlT, 0},
"c-u": {tcell.ModCtrl, tcell.KeyCtrlU, 0},
"c-v": {tcell.ModCtrl, tcell.KeyCtrlV, 0},
"c-w": {tcell.ModCtrl, tcell.KeyCtrlW, 0},
"c-x": {tcell.ModCtrl, tcell.KeyCtrlX, rune(tcell.KeyCAN)},
"c-y": {tcell.ModCtrl, tcell.KeyCtrlY, 0}, // TODO: runes for the rest
"c-z": {tcell.ModCtrl, tcell.KeyCtrlZ, 0},
"c-]": {tcell.ModCtrl, tcell.KeyCtrlRightSq, 0},
"c-\\": {tcell.ModCtrl, tcell.KeyCtrlBackslash, 0},
"c-[": {tcell.ModCtrl, tcell.KeyCtrlLeftSq, 0},
"c-^": {tcell.ModCtrl, tcell.KeyCtrlCarat, 0},
"c-_": {tcell.ModCtrl, tcell.KeyCtrlUnderscore, 0},
"a-space": {tcell.ModAlt, tcell.KeyRune, ' '},
"a-0": {tcell.ModAlt, tcell.KeyRune, '0'},
"a-1": {tcell.ModAlt, tcell.KeyRune, '1'},
"a-2": {tcell.ModAlt, tcell.KeyRune, '2'},
"a-3": {tcell.ModAlt, tcell.KeyRune, '3'},
"a-4": {tcell.ModAlt, tcell.KeyRune, '4'},
"a-5": {tcell.ModAlt, tcell.KeyRune, '5'},
"a-6": {tcell.ModAlt, tcell.KeyRune, '6'},
"a-7": {tcell.ModAlt, tcell.KeyRune, '7'},
"a-8": {tcell.ModAlt, tcell.KeyRune, '8'},
"a-9": {tcell.ModAlt, tcell.KeyRune, '9'},
"a-a": {tcell.ModAlt, tcell.KeyRune, 'a'},
"a-b": {tcell.ModAlt, tcell.KeyRune, 'b'},
"a-c": {tcell.ModAlt, tcell.KeyRune, 'c'},
"a-d": {tcell.ModAlt, tcell.KeyRune, 'd'},
"a-e": {tcell.ModAlt, tcell.KeyRune, 'e'},
"a-f": {tcell.ModAlt, tcell.KeyRune, 'f'},
"a-g": {tcell.ModAlt, tcell.KeyRune, 'g'},
"a-h": {tcell.ModAlt, tcell.KeyRune, 'h'},
"a-i": {tcell.ModAlt, tcell.KeyRune, 'i'},
"a-j": {tcell.ModAlt, tcell.KeyRune, 'j'},
"a-k": {tcell.ModAlt, tcell.KeyRune, 'k'},
"a-l": {tcell.ModAlt, tcell.KeyRune, 'l'},
"a-m": {tcell.ModAlt, tcell.KeyRune, 'm'},
"a-n": {tcell.ModAlt, tcell.KeyRune, 'n'},
"a-o": {tcell.ModAlt, tcell.KeyRune, 'o'},
"a-p": {tcell.ModAlt, tcell.KeyRune, 'p'},
"a-q": {tcell.ModAlt, tcell.KeyRune, 'q'},
"a-r": {tcell.ModAlt, tcell.KeyRune, 'r'},
"a-s": {tcell.ModAlt, tcell.KeyRune, 's'},
"a-t": {tcell.ModAlt, tcell.KeyRune, 't'},
"a-u": {tcell.ModAlt, tcell.KeyRune, 'u'},
"a-v": {tcell.ModAlt, tcell.KeyRune, 'v'},
"a-w": {tcell.ModAlt, tcell.KeyRune, 'w'},
"a-x": {tcell.ModAlt, tcell.KeyRune, 'x'},
"a-y": {tcell.ModAlt, tcell.KeyRune, 'y'},
"a-z": {tcell.ModAlt, tcell.KeyRune, 'z'},
"a-]": {tcell.ModAlt, tcell.KeyRune, ']'},
"a-\\": {tcell.ModAlt, tcell.KeyRune, '\\'},
"a-[": {tcell.ModAlt, tcell.KeyRune, '['},
"a-^": {tcell.ModAlt, tcell.KeyRune, '^'},
"a-_": {tcell.ModAlt, tcell.KeyRune, '_'},
"nul": {tcell.ModNone, tcell.KeyNUL, 0},
"soh": {tcell.ModNone, tcell.KeySOH, 0},
"stx": {tcell.ModNone, tcell.KeySTX, 0},
"etx": {tcell.ModNone, tcell.KeyETX, 0},
"eot": {tcell.ModNone, tcell.KeyEOT, 0},
"enq": {tcell.ModNone, tcell.KeyENQ, 0},
"ack": {tcell.ModNone, tcell.KeyACK, 0},
"bel": {tcell.ModNone, tcell.KeyBEL, 0},
"bs": {tcell.ModNone, tcell.KeyBS, 0},
"tab": {tcell.ModNone, tcell.KeyTAB, 0},
"lf": {tcell.ModNone, tcell.KeyLF, 0},
"vt": {tcell.ModNone, tcell.KeyVT, 0},
"ff": {tcell.ModNone, tcell.KeyFF, 0},
"cr": {tcell.ModNone, tcell.KeyCR, 0},
"so": {tcell.ModNone, tcell.KeySO, 0},
"si": {tcell.ModNone, tcell.KeySI, 0},
"dle": {tcell.ModNone, tcell.KeyDLE, 0},
"dc1": {tcell.ModNone, tcell.KeyDC1, 0},
"dc2": {tcell.ModNone, tcell.KeyDC2, 0},
"dc3": {tcell.ModNone, tcell.KeyDC3, 0},
"dc4": {tcell.ModNone, tcell.KeyDC4, 0},
"nak": {tcell.ModNone, tcell.KeyNAK, 0},
"syn": {tcell.ModNone, tcell.KeySYN, 0},
"etb": {tcell.ModNone, tcell.KeyETB, 0},
"can": {tcell.ModNone, tcell.KeyCAN, 0},
"em": {tcell.ModNone, tcell.KeyEM, 0},
"sub": {tcell.ModNone, tcell.KeySUB, 0},
"esc": {tcell.ModNone, tcell.KeyESC, 0},
"fs": {tcell.ModNone, tcell.KeyFS, 0},
"gs": {tcell.ModNone, tcell.KeyGS, 0},
"rs": {tcell.ModNone, tcell.KeyRS, 0},
"us": {tcell.ModNone, tcell.KeyUS, 0},
"del": {tcell.ModNone, tcell.KeyDEL, 0},
"space": {vaxis.ModifierMask(0), ' '},
"semicolon": {vaxis.ModifierMask(0), ';'},
"enter": {vaxis.ModifierMask(0), vaxis.KeyEnter},
"c-enter": {vaxis.ModCtrl, vaxis.KeyEnter},
"a-enter": {vaxis.ModAlt, vaxis.KeyEnter},
"up": {vaxis.ModifierMask(0), vaxis.KeyUp},
"c-up": {vaxis.ModCtrl, vaxis.KeyUp},
"a-up": {vaxis.ModAlt, vaxis.KeyUp},
"down": {vaxis.ModifierMask(0), vaxis.KeyDown},
"c-down": {vaxis.ModCtrl, vaxis.KeyDown},
"a-down": {vaxis.ModAlt, vaxis.KeyDown},
"right": {vaxis.ModifierMask(0), vaxis.KeyRight},
"c-right": {vaxis.ModCtrl, vaxis.KeyRight},
"a-right": {vaxis.ModAlt, vaxis.KeyRight},
"left": {vaxis.ModifierMask(0), vaxis.KeyLeft},
"c-left": {vaxis.ModCtrl, vaxis.KeyLeft},
"a-left": {vaxis.ModAlt, vaxis.KeyLeft},
"upleft": {vaxis.ModifierMask(0), vaxis.KeyUpLeft},
"upright": {vaxis.ModifierMask(0), vaxis.KeyUpRight},
"downleft": {vaxis.ModifierMask(0), vaxis.KeyDownLeft},
"downright": {vaxis.ModifierMask(0), vaxis.KeyDownRight},
"center": {vaxis.ModifierMask(0), vaxis.KeyCenter},
"pgup": {vaxis.ModifierMask(0), vaxis.KeyPgUp},
"c-pgup": {vaxis.ModCtrl, vaxis.KeyPgUp},
"a-pgup": {vaxis.ModAlt, vaxis.KeyPgUp},
"pgdn": {vaxis.ModifierMask(0), vaxis.KeyPgDown},
"c-pgdn": {vaxis.ModCtrl, vaxis.KeyPgDown},
"a-pgdn": {vaxis.ModAlt, vaxis.KeyPgDown},
"home": {vaxis.ModifierMask(0), vaxis.KeyHome},
"end": {vaxis.ModifierMask(0), vaxis.KeyEnd},
"insert": {vaxis.ModifierMask(0), vaxis.KeyInsert},
"delete": {vaxis.ModifierMask(0), vaxis.KeyDelete},
"c-delete": {vaxis.ModCtrl, vaxis.KeyDelete},
"a-delete": {vaxis.ModAlt, vaxis.KeyDelete},
"backspace": {vaxis.ModifierMask(0), vaxis.KeyBackspace},
// "help": {vaxis.ModifierMask(0), vaxis.KeyHelp},
"exit": {vaxis.ModifierMask(0), vaxis.KeyExit},
"clear": {vaxis.ModifierMask(0), vaxis.KeyClear},
"cancel": {vaxis.ModifierMask(0), vaxis.KeyCancel},
"print": {vaxis.ModifierMask(0), vaxis.KeyPrint},
"pause": {vaxis.ModifierMask(0), vaxis.KeyPause},
"backtab": {vaxis.ModShift, vaxis.KeyTab},
"f1": {vaxis.ModifierMask(0), vaxis.KeyF01},
"f2": {vaxis.ModifierMask(0), vaxis.KeyF02},
"f3": {vaxis.ModifierMask(0), vaxis.KeyF03},
"f4": {vaxis.ModifierMask(0), vaxis.KeyF04},
"f5": {vaxis.ModifierMask(0), vaxis.KeyF05},
"f6": {vaxis.ModifierMask(0), vaxis.KeyF06},
"f7": {vaxis.ModifierMask(0), vaxis.KeyF07},
"f8": {vaxis.ModifierMask(0), vaxis.KeyF08},
"f9": {vaxis.ModifierMask(0), vaxis.KeyF09},
"f10": {vaxis.ModifierMask(0), vaxis.KeyF10},
"f11": {vaxis.ModifierMask(0), vaxis.KeyF11},
"f12": {vaxis.ModifierMask(0), vaxis.KeyF12},
"f13": {vaxis.ModifierMask(0), vaxis.KeyF13},
"f14": {vaxis.ModifierMask(0), vaxis.KeyF14},
"f15": {vaxis.ModifierMask(0), vaxis.KeyF15},
"f16": {vaxis.ModifierMask(0), vaxis.KeyF16},
"f17": {vaxis.ModifierMask(0), vaxis.KeyF17},
"f18": {vaxis.ModifierMask(0), vaxis.KeyF18},
"f19": {vaxis.ModifierMask(0), vaxis.KeyF19},
"f20": {vaxis.ModifierMask(0), vaxis.KeyF20},
"f21": {vaxis.ModifierMask(0), vaxis.KeyF21},
"f22": {vaxis.ModifierMask(0), vaxis.KeyF22},
"f23": {vaxis.ModifierMask(0), vaxis.KeyF23},
"f24": {vaxis.ModifierMask(0), vaxis.KeyF24},
"f25": {vaxis.ModifierMask(0), vaxis.KeyF25},
"f26": {vaxis.ModifierMask(0), vaxis.KeyF26},
"f27": {vaxis.ModifierMask(0), vaxis.KeyF27},
"f28": {vaxis.ModifierMask(0), vaxis.KeyF28},
"f29": {vaxis.ModifierMask(0), vaxis.KeyF29},
"f30": {vaxis.ModifierMask(0), vaxis.KeyF30},
"f31": {vaxis.ModifierMask(0), vaxis.KeyF31},
"f32": {vaxis.ModifierMask(0), vaxis.KeyF32},
"f33": {vaxis.ModifierMask(0), vaxis.KeyF33},
"f34": {vaxis.ModifierMask(0), vaxis.KeyF34},
"f35": {vaxis.ModifierMask(0), vaxis.KeyF35},
"f36": {vaxis.ModifierMask(0), vaxis.KeyF36},
"f37": {vaxis.ModifierMask(0), vaxis.KeyF37},
"f38": {vaxis.ModifierMask(0), vaxis.KeyF38},
"f39": {vaxis.ModifierMask(0), vaxis.KeyF39},
"f40": {vaxis.ModifierMask(0), vaxis.KeyF40},
"f41": {vaxis.ModifierMask(0), vaxis.KeyF41},
"f42": {vaxis.ModifierMask(0), vaxis.KeyF42},
"f43": {vaxis.ModifierMask(0), vaxis.KeyF43},
"f44": {vaxis.ModifierMask(0), vaxis.KeyF44},
"f45": {vaxis.ModifierMask(0), vaxis.KeyF45},
"f46": {vaxis.ModifierMask(0), vaxis.KeyF46},
"f47": {vaxis.ModifierMask(0), vaxis.KeyF47},
"f48": {vaxis.ModifierMask(0), vaxis.KeyF48},
"f49": {vaxis.ModifierMask(0), vaxis.KeyF49},
"f50": {vaxis.ModifierMask(0), vaxis.KeyF50},
"f51": {vaxis.ModifierMask(0), vaxis.KeyF51},
"f52": {vaxis.ModifierMask(0), vaxis.KeyF52},
"f53": {vaxis.ModifierMask(0), vaxis.KeyF53},
"f54": {vaxis.ModifierMask(0), vaxis.KeyF54},
"f55": {vaxis.ModifierMask(0), vaxis.KeyF55},
"f56": {vaxis.ModifierMask(0), vaxis.KeyF56},
"f57": {vaxis.ModifierMask(0), vaxis.KeyF57},
"f58": {vaxis.ModifierMask(0), vaxis.KeyF58},
"f59": {vaxis.ModifierMask(0), vaxis.KeyF59},
"f60": {vaxis.ModifierMask(0), vaxis.KeyF60},
"f61": {vaxis.ModifierMask(0), vaxis.KeyF61},
"f62": {vaxis.ModifierMask(0), vaxis.KeyF62},
"f63": {vaxis.ModifierMask(0), vaxis.KeyF63},
"c-space": {vaxis.ModCtrl, ' '},
"c-a": {vaxis.ModCtrl, 'a'},
"c-b": {vaxis.ModCtrl, 'b'},
"c-c": {vaxis.ModCtrl, 'c'},
"c-d": {vaxis.ModCtrl, 'd'},
"c-e": {vaxis.ModCtrl, 'e'},
"c-f": {vaxis.ModCtrl, 'f'},
"c-g": {vaxis.ModCtrl, 'g'},
"c-h": {vaxis.ModCtrl, 'h'},
"c-i": {vaxis.ModCtrl, 'i'},
"c-j": {vaxis.ModCtrl, 'j'},
"c-k": {vaxis.ModCtrl, 'k'},
"c-l": {vaxis.ModCtrl, 'l'},
"c-m": {vaxis.ModCtrl, 'm'},
"c-n": {vaxis.ModCtrl, 'n'},
"c-o": {vaxis.ModCtrl, 'o'},
"c-p": {vaxis.ModCtrl, 'p'},
"c-q": {vaxis.ModCtrl, 'q'},
"c-r": {vaxis.ModCtrl, 'r'},
"c-s": {vaxis.ModCtrl, 's'},
"c-t": {vaxis.ModCtrl, 't'},
"c-u": {vaxis.ModCtrl, 'u'},
"c-v": {vaxis.ModCtrl, 'v'},
"c-w": {vaxis.ModCtrl, 'w'},
"c-x": {vaxis.ModCtrl, 'x'},
"c-y": {vaxis.ModCtrl, 'y'},
"c-z": {vaxis.ModCtrl, 'z'},
"c-]": {vaxis.ModCtrl, ']'},
"c-\\": {vaxis.ModCtrl, '\\'},
"c-[": {vaxis.ModCtrl, '['},
"c-^": {vaxis.ModCtrl, '^'},
"c-_": {vaxis.ModCtrl, '_'},
"a-space": {vaxis.ModAlt, ' '},
"a-0": {vaxis.ModAlt, '0'},
"a-1": {vaxis.ModAlt, '1'},
"a-2": {vaxis.ModAlt, '2'},
"a-3": {vaxis.ModAlt, '3'},
"a-4": {vaxis.ModAlt, '4'},
"a-5": {vaxis.ModAlt, '5'},
"a-6": {vaxis.ModAlt, '6'},
"a-7": {vaxis.ModAlt, '7'},
"a-8": {vaxis.ModAlt, '8'},
"a-9": {vaxis.ModAlt, '9'},
"a-a": {vaxis.ModAlt, 'a'},
"a-b": {vaxis.ModAlt, 'b'},
"a-c": {vaxis.ModAlt, 'c'},
"a-d": {vaxis.ModAlt, 'd'},
"a-e": {vaxis.ModAlt, 'e'},
"a-f": {vaxis.ModAlt, 'f'},
"a-g": {vaxis.ModAlt, 'g'},
"a-h": {vaxis.ModAlt, 'h'},
"a-i": {vaxis.ModAlt, 'i'},
"a-j": {vaxis.ModAlt, 'j'},
"a-k": {vaxis.ModAlt, 'k'},
"a-l": {vaxis.ModAlt, 'l'},
"a-m": {vaxis.ModAlt, 'm'},
"a-n": {vaxis.ModAlt, 'n'},
"a-o": {vaxis.ModAlt, 'o'},
"a-p": {vaxis.ModAlt, 'p'},
"a-q": {vaxis.ModAlt, 'q'},
"a-r": {vaxis.ModAlt, 'r'},
"a-s": {vaxis.ModAlt, 's'},
"a-t": {vaxis.ModAlt, 't'},
"a-u": {vaxis.ModAlt, 'u'},
"a-v": {vaxis.ModAlt, 'v'},
"a-w": {vaxis.ModAlt, 'w'},
"a-x": {vaxis.ModAlt, 'x'},
"a-y": {vaxis.ModAlt, 'y'},
"a-z": {vaxis.ModAlt, 'z'},
"a-]": {vaxis.ModAlt, ']'},
"a-\\": {vaxis.ModAlt, '\\'},
"a-[": {vaxis.ModAlt, '['},
"a-^": {vaxis.ModAlt, '^'},
"a-_": {vaxis.ModAlt, '_'},
"nul": {vaxis.ModCtrl, ' '},
"soh": {vaxis.ModCtrl, 'a'},
"stx": {vaxis.ModCtrl, 'b'},
"etx": {vaxis.ModCtrl, 'c'},
"eot": {vaxis.ModCtrl, 'd'},
"enq": {vaxis.ModCtrl, 'e'},
"ack": {vaxis.ModCtrl, 'f'},
"bel": {vaxis.ModCtrl, 'g'},
"bs": {vaxis.ModCtrl, 'h'},
"tab": {vaxis.ModifierMask(0), vaxis.KeyTab},
"lf": {vaxis.ModCtrl, 'j'},
"vt": {vaxis.ModCtrl, 'k'},
"ff": {vaxis.ModCtrl, 'l'},
"cr": {vaxis.ModifierMask(0), vaxis.KeyEnter},
"so": {vaxis.ModCtrl, 'n'},
"si": {vaxis.ModCtrl, 'o'},
"dle": {vaxis.ModCtrl, 'p'},
"dc1": {vaxis.ModCtrl, 'q'},
"dc2": {vaxis.ModCtrl, 'r'},
"dc3": {vaxis.ModCtrl, 's'},
"dc4": {vaxis.ModCtrl, 't'},
"nak": {vaxis.ModCtrl, 'u'},
"syn": {vaxis.ModCtrl, 'v'},
"etb": {vaxis.ModCtrl, 'w'},
"can": {vaxis.ModCtrl, 'x'},
"em": {vaxis.ModCtrl, 'y'},
"sub": {vaxis.ModCtrl, 'z'},
"esc": {vaxis.ModifierMask(0), vaxis.KeyEsc},
"fs": {vaxis.ModCtrl, '\\'},
"gs": {vaxis.ModCtrl, ']'},
"rs": {vaxis.ModCtrl, '^'},
"us": {vaxis.ModCtrl, '_'},
"del": {vaxis.ModifierMask(0), vaxis.KeyDelete},
}
func ParseKeyStrokes(keystrokes string) ([]KeyStroke, error) {
@@ -767,9 +758,8 @@ func ParseKeyStrokes(keystrokes string) ([]KeyStroke, error) {
fallthrough
default:
strokes = append(strokes, KeyStroke{
Modifiers: tcell.ModNone,
Key: tcell.KeyRune,
Rune: tok,
Modifiers: vaxis.ModifierMask(0),
Key: tok,
})
}
}

View File

@@ -4,7 +4,7 @@ import (
"fmt"
"testing"
"github.com/gdamore/tcell/v2"
"git.sr.ht/~rockorager/vaxis"
"github.com/stretchr/testify/assert"
)
@@ -32,26 +32,26 @@ func TestGetBinding(t *testing.T) {
}
test([]KeyStroke{
{tcell.ModNone, tcell.KeyRune, 'a'},
{vaxis.ModifierMask(0), 'a'},
}, BINDING_INCOMPLETE, "")
test([]KeyStroke{
{tcell.ModNone, tcell.KeyRune, 'a'},
{tcell.ModNone, tcell.KeyRune, 'b'},
{tcell.ModNone, tcell.KeyRune, 'c'},
{vaxis.ModifierMask(0), 'a'},
{vaxis.ModifierMask(0), 'b'},
{vaxis.ModifierMask(0), 'c'},
}, BINDING_FOUND, ":abc")
test([]KeyStroke{
{tcell.ModNone, tcell.KeyRune, 'c'},
{tcell.ModNone, tcell.KeyRune, 'b'},
{tcell.ModNone, tcell.KeyRune, 'a'},
{vaxis.ModifierMask(0), 'c'},
{vaxis.ModifierMask(0), 'b'},
{vaxis.ModifierMask(0), 'a'},
}, BINDING_FOUND, ":cba")
test([]KeyStroke{
{tcell.ModNone, tcell.KeyRune, 'f'},
{tcell.ModNone, tcell.KeyRune, 'o'},
{vaxis.ModifierMask(0), 'f'},
{vaxis.ModifierMask(0), 'o'},
}, BINDING_INCOMPLETE, "")
test([]KeyStroke{
{tcell.ModNone, tcell.KeyRune, '4'},
{tcell.ModNone, tcell.KeyRune, '0'},
{tcell.ModNone, tcell.KeyRune, '4'},
{vaxis.ModifierMask(0), '4'},
{vaxis.ModifierMask(0), '0'},
{vaxis.ModifierMask(0), '4'},
}, BINDING_NOT_FOUND, "")
add("<C-a>", "c-a")
@@ -59,18 +59,18 @@ func TestGetBinding(t *testing.T) {
add("<C-PgUp>", ":prev")
add("<C-Enter>", ":open")
test([]KeyStroke{
{tcell.ModCtrl, tcell.KeyCtrlA, 0},
{vaxis.ModCtrl, 'a'},
}, BINDING_FOUND, "c-a")
test([]KeyStroke{
{tcell.ModCtrl, tcell.KeyDown, 0},
{vaxis.ModCtrl, vaxis.KeyDown},
}, BINDING_FOUND, ":next")
test([]KeyStroke{
{tcell.ModCtrl, tcell.KeyPgUp, 0},
{vaxis.ModCtrl, vaxis.KeyPgUp},
}, BINDING_FOUND, ":prev")
test([]KeyStroke{
{tcell.ModCtrl, tcell.KeyPgDn, 0},
{vaxis.ModCtrl, vaxis.KeyPgDown},
}, BINDING_NOT_FOUND, "")
test([]KeyStroke{
{tcell.ModCtrl, tcell.KeyEnter, 0},
{vaxis.ModCtrl, vaxis.KeyEnter},
}, BINDING_FOUND, ":open")
}

View File

@@ -336,50 +336,52 @@ func (ti *TextInput) OnFocusLost(onFocusLost func(ti *TextInput)) {
func (ti *TextInput) Event(event vaxis.Event) bool {
ti.Lock()
defer ti.Unlock()
if event, ok := event.(*tcell.EventKey); ok {
if key, ok := event.(vaxis.Key); ok {
c := ti.completeKey
if c != nil && c.Key == event.Key() && c.Modifiers == event.Modifiers() {
if c != nil && key.Matches(c.Key, c.Modifiers) {
ti.showCompletions(true)
return true
}
ti.invalidateCompletions()
switch event.Key() {
case tcell.KeyBackspace, tcell.KeyBackspace2:
switch {
case key.Matches(vaxis.KeyBackspace):
ti.backspace()
case tcell.KeyCtrlD, tcell.KeyDelete:
case key.Matches('d', vaxis.ModCtrl), key.Matches(vaxis.KeyDelete):
ti.deleteChar()
case tcell.KeyCtrlB, tcell.KeyLeft:
case key.Matches('b', vaxis.ModCtrl), key.Matches(vaxis.KeyLeft):
if ti.index > 0 {
ti.index--
ti.ensureScroll()
ti.Invalidate()
}
case tcell.KeyCtrlF, tcell.KeyRight:
case key.Matches('f', vaxis.ModCtrl), key.Matches(vaxis.KeyRight):
if ti.index < len(ti.text) {
ti.index++
ti.ensureScroll()
ti.Invalidate()
}
case tcell.KeyCtrlA, tcell.KeyHome:
case key.Matches('a', vaxis.ModCtrl), key.Matches(vaxis.KeyHome):
ti.index = 0
ti.ensureScroll()
ti.Invalidate()
case tcell.KeyCtrlE, tcell.KeyEnd:
case key.Matches('e', vaxis.ModCtrl), key.Matches(vaxis.KeyEnd):
ti.index = len(ti.text)
ti.ensureScroll()
ti.Invalidate()
case tcell.KeyCtrlK:
case key.Matches('k', vaxis.ModCtrl):
ti.deleteLineForward()
case tcell.KeyCtrlW:
case key.Matches('w', vaxis.ModCtrl):
ti.deleteWord()
case tcell.KeyCtrlU:
case key.Matches('u', vaxis.ModCtrl):
ti.deleteLineBackward()
case tcell.KeyESC:
case key.Matches(vaxis.KeyEsc):
ti.Invalidate()
case tcell.KeyRune:
ti.insert(event.Rune())
case key.Text != "":
for _, ch := range key.Text {
ti.insert(ch)
}
}
}
return true
@@ -482,9 +484,9 @@ func (c *completions) exec() {
}
func (c *completions) Event(e vaxis.Event) bool {
if e, ok := e.(*tcell.EventKey); ok {
if e, ok := e.(vaxis.Key); ok {
k := c.ti.completeKey
if k != nil && k.Key == e.Key() && k.Modifiers == e.Modifiers() {
if k != nil && e.Matches(k.Key, k.Modifiers) {
if len(c.ti.completions) == 1 {
c.ti.completeIndex = 0
c.exec()
@@ -498,14 +500,16 @@ func (c *completions) Event(e vaxis.Event) bool {
return true
}
switch e.Key() {
case tcell.KeyCtrlN, tcell.KeyDown:
switch {
case e.Matches('n', vaxis.ModCtrl), e.Matches(vaxis.KeyDown):
c.next()
return true
case tcell.KeyBacktab, tcell.KeyCtrlP, tcell.KeyUp:
case e.Matches(vaxis.KeyTab, vaxis.ModShift),
e.Matches('p', vaxis.ModCtrl),
e.Matches(vaxis.KeyUp):
c.prev()
return true
case tcell.KeyEnter:
case e.Matches(vaxis.KeyEnter):
if c.index() >= 0 {
c.exec()
return true

View File

@@ -9,7 +9,6 @@ import (
"git.sr.ht/~rjarry/aerc/config"
"git.sr.ht/~rjarry/aerc/log"
"git.sr.ht/~rockorager/vaxis"
"github.com/gdamore/tcell/v2"
)
// Use unbuffered channels (always blocking unless somebody can read
@@ -143,7 +142,6 @@ func HandleEvent(event vaxis.Event) {
case vaxis.Redraw:
Invalidate()
default:
event = tcell.TcellEvent(event)
// if we have a popover, and it can handle the event, it does so
if state.popover == nil || !state.popover.Event(event) {
// otherwise, we send the event to the main content