Decompose tcell ReadChar key translation (refactor step 7)
ReadChar's key switch moves into translateKey with namedKey split into motionKey/editingKey halves. term is complexity-clean. Behavior unchanged.
This commit is contained in:
114
term/tcell.go
114
term/tcell.go
@@ -89,48 +89,88 @@ func (t *Tcell) ReadChar() byte {
|
||||
t.Render(t.last)
|
||||
}
|
||||
case *tcell.EventKey:
|
||||
switch ev.Key() {
|
||||
case tcell.KeyUp:
|
||||
return 'k'
|
||||
case tcell.KeyDown:
|
||||
return 'j'
|
||||
case tcell.KeyLeft:
|
||||
return 'h'
|
||||
case tcell.KeyRight:
|
||||
return 'l'
|
||||
case tcell.KeyHome:
|
||||
return 'y'
|
||||
case tcell.KeyPgUp:
|
||||
return 'u'
|
||||
case tcell.KeyEnd:
|
||||
return 'b'
|
||||
case tcell.KeyPgDn:
|
||||
return 'n'
|
||||
case tcell.KeyEnter:
|
||||
return '\n'
|
||||
case tcell.KeyEscape:
|
||||
return game.Escape
|
||||
case tcell.KeyBackspace, tcell.KeyBackspace2:
|
||||
return 8
|
||||
case tcell.KeyDelete:
|
||||
return 0x7f
|
||||
case tcell.KeyTab:
|
||||
return '\t'
|
||||
case tcell.KeyCtrlC:
|
||||
return 3
|
||||
default:
|
||||
if ev.Key() >= tcell.KeyCtrlA && ev.Key() <= tcell.KeyCtrlZ {
|
||||
return byte(ev.Key()) //nolint:gosec // G115: 1..26 fits
|
||||
}
|
||||
|
||||
if r := ev.Rune(); r > 0 && r < 0x80 {
|
||||
return byte(r)
|
||||
}
|
||||
if b, ok := translateKey(ev); ok {
|
||||
return b
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// translateKey converts a key event to a game input byte; ok is false
|
||||
// for keys the C game does not understand.
|
||||
func translateKey(ev *tcell.EventKey) (byte, bool) {
|
||||
if b, ok := namedKey(ev.Key()); ok {
|
||||
return b, true
|
||||
}
|
||||
|
||||
if ev.Key() >= tcell.KeyCtrlA && ev.Key() <= tcell.KeyCtrlZ {
|
||||
return byte(ev.Key()), true //nolint:gosec // G115: 1..26 fits
|
||||
}
|
||||
|
||||
if r := ev.Rune(); r > 0 && r < 0x80 {
|
||||
return byte(r), true
|
||||
}
|
||||
|
||||
return 0, false
|
||||
}
|
||||
|
||||
// namedKey translates tcell's navigation and editing keys to the single
|
||||
// bytes the C game reads (arrows become hjkl, etc.); ok is false for
|
||||
// keys handled elsewhere.
|
||||
func namedKey(k tcell.Key) (byte, bool) {
|
||||
if b, ok := motionKey(k); ok {
|
||||
return b, true
|
||||
}
|
||||
|
||||
return editingKey(k)
|
||||
}
|
||||
|
||||
// motionKey translates the arrow and paging keys to Rogue's movement
|
||||
// letters (tcell.go ReadChar).
|
||||
func motionKey(k tcell.Key) (byte, bool) {
|
||||
switch k {
|
||||
case tcell.KeyUp:
|
||||
return 'k', true
|
||||
case tcell.KeyDown:
|
||||
return 'j', true
|
||||
case tcell.KeyLeft:
|
||||
return 'h', true
|
||||
case tcell.KeyRight:
|
||||
return 'l', true
|
||||
case tcell.KeyHome:
|
||||
return 'y', true
|
||||
case tcell.KeyPgUp:
|
||||
return 'u', true
|
||||
case tcell.KeyEnd:
|
||||
return 'b', true
|
||||
case tcell.KeyPgDn:
|
||||
return 'n', true
|
||||
}
|
||||
|
||||
return 0, false
|
||||
}
|
||||
|
||||
// editingKey translates the editing and control keys to their C0 codes
|
||||
// (tcell.go ReadChar).
|
||||
func editingKey(k tcell.Key) (byte, bool) {
|
||||
switch k {
|
||||
case tcell.KeyEnter:
|
||||
return '\n', true
|
||||
case tcell.KeyEscape:
|
||||
return game.Escape, true
|
||||
case tcell.KeyBackspace, tcell.KeyBackspace2:
|
||||
return 8, true
|
||||
case tcell.KeyDelete:
|
||||
return 0x7f, true
|
||||
case tcell.KeyTab:
|
||||
return '\t', true
|
||||
case tcell.KeyCtrlC:
|
||||
return 3, true
|
||||
}
|
||||
|
||||
return 0, false
|
||||
}
|
||||
|
||||
// ShellEscape suspends the screen and runs the user's shell (main.c
|
||||
// shell + md_shellescape).
|
||||
func (t *Tcell) ShellEscape() {
|
||||
|
||||
Reference in New Issue
Block a user