From 715ed5aaeb2a566dab6258cc121c04d1f65a9769 Mon Sep 17 00:00:00 2001 From: ayn2op Date: Thu, 8 Oct 2026 15:03:48 -0400 Subject: [PATCH] feat(config): add keybinds to scroll the trees --- docs/config.md | 58 +++++++++++++++++++++++++- go.mod | 10 ++--- go.sum | 20 ++++----- internal/config/keybinds.go | 29 +++++++++---- internal/ui/chat/guildstree/keymap.go | 1 + internal/ui/chat/memberstree/keymap.go | 1 + internal/ui/tree/tree.go | 12 ++++++ 7 files changed, 107 insertions(+), 24 deletions(-) diff --git a/docs/config.md b/docs/config.md index 630df51..cf1d757 100644 --- a/docs/config.md +++ b/docs/config.md @@ -540,6 +540,34 @@ Default: `"esc"` Only while focusing on the guilds tree. +### keybinds.guilds_tree.scroll_up + +Scroll without changing the selection. + +Default: `"pgup"` + +### keybinds.guilds_tree.scroll_down + +Default: `"pgdn"` + +### keybinds.guilds_tree.scroll_top + +Default: `"home"` + +### keybinds.guilds_tree.scroll_bottom + +Default: `"end"` + +### keybinds.guilds_tree.scroll_left + +Scroll sideways to read names that are cut off. + +Default: `"h"` + +### keybinds.guilds_tree.scroll_right + +Default: `"l"` + ### keybinds.guilds_tree.select_up Default: `"k"` @@ -592,6 +620,34 @@ Default: `"J"` Only while focusing on the members tree. +### keybinds.members_tree.scroll_up + +Scroll without changing the selection. + +Default: `"pgup"` + +### keybinds.members_tree.scroll_down + +Default: `"pgdn"` + +### keybinds.members_tree.scroll_top + +Default: `"home"` + +### keybinds.members_tree.scroll_bottom + +Default: `"end"` + +### keybinds.members_tree.scroll_left + +Scroll sideways to read names that are cut off. + +Default: `"h"` + +### keybinds.members_tree.scroll_right + +Default: `"l"` + ### keybinds.members_tree.select_up Default: `"k"` @@ -652,7 +708,7 @@ Default: `"G"` ### keybinds.messages_list.scroll_up -Scroll the messages list without changing the selection. +Scroll without changing the selection. Default: `"K"` diff --git a/go.mod b/go.mod index 11e2bc1..22f7054 100644 --- a/go.mod +++ b/go.mod @@ -15,7 +15,7 @@ require ( github.com/andybalholm/brotli v1.2.6 github.com/ayn2op/arikawa/v3 v3.0.0-20260929021956-7d0802bf4d7c github.com/ayn2op/ningen/v3 v3.0.1-0.20260929010920-29794d5fa70e - github.com/ayn2op/tview v0.0.0-20261004231500-f79adb05b560 + github.com/ayn2op/tview v0.0.0-20261008190544-5da45c25c67d github.com/bogdanfinn/fhttp v0.6.9 github.com/bogdanfinn/tls-client v1.16.0 github.com/gdamore/tcell/v3 v3.5.0 @@ -45,7 +45,7 @@ require ( github.com/cloudflare/circl v1.6.5 // indirect github.com/danieljoos/wincred v1.2.3 // indirect github.com/dchest/jsmin v1.0.0 // indirect - github.com/dlclark/regexp2/v2 v2.8.3 // indirect + github.com/dlclark/regexp2/v2 v2.8.4 // indirect github.com/ebitengine/purego v0.11.1 // indirect github.com/gdamore/encoding v1.0.1 // indirect github.com/godbus/dbus/v5 v5.2.2 // indirect @@ -55,13 +55,13 @@ require ( github.com/quic-go/qpack v0.6.0 // indirect github.com/randall77/makefat v0.0.0-20260406194835-1b91746796b7 // indirect github.com/tam7t/hpkp v0.0.0-20160821193359-2b70b4024ed5 // indirect - github.com/twmb/murmur3 v1.2.0 // indirect + github.com/twmb/murmur3 v1.2.1 // indirect go4.org v0.0.0-20260112195520-a5071408f32f // indirect golang.design/x/x11 v0.2.0 // indirect golang.org/x/crypto v0.57.0 // indirect - golang.org/x/exp/shiny v0.0.0-20260908205506-85c1c2202aba // indirect + golang.org/x/exp/shiny v0.0.0-20261007192929-f45ad48fbe92 // indirect golang.org/x/mobile v0.0.0-20260908204917-8b95e45f8d3e // indirect - golang.org/x/net v0.59.0 // indirect + golang.org/x/net v0.60.0 // indirect golang.org/x/sys v0.48.0 // indirect golang.org/x/term v0.46.0 // indirect golang.org/x/text v0.42.0 // indirect diff --git a/go.sum b/go.sum index 45146dc..d4d4c49 100644 --- a/go.sum +++ b/go.sum @@ -14,8 +14,8 @@ github.com/ayn2op/arikawa/v3 v3.0.0-20260929021956-7d0802bf4d7c h1:Qkl3W5RXzUQUR github.com/ayn2op/arikawa/v3 v3.0.0-20260929021956-7d0802bf4d7c/go.mod h1:SHqcr+EmZKeNtVKZybHJn4HNz+ufA1XbeKNSTigBCEE= github.com/ayn2op/ningen/v3 v3.0.1-0.20260929010920-29794d5fa70e h1:QAei/IVEyZV7GcpkpcFUh37+QRqwrt57z7OT3ciHrhI= github.com/ayn2op/ningen/v3 v3.0.1-0.20260929010920-29794d5fa70e/go.mod h1:RsvYiMzi4Si1F7vmml5NCL2DaKIZXkNUQC7QlGTMtCw= -github.com/ayn2op/tview v0.0.0-20261004231500-f79adb05b560 h1:joRW9LhEPGkbhKgs8tUMgmoXPzH8v+5GQSe6geS0crg= -github.com/ayn2op/tview v0.0.0-20261004231500-f79adb05b560/go.mod h1:sMf5NqBlGJjsaGCUycTqTyNG5vewJU6jq/3BdJIzbCU= +github.com/ayn2op/tview v0.0.0-20261008190544-5da45c25c67d h1:nueCN+u4FjTTU2ZdyDfRG68eCwa9Oq4dQY3CMgRUZQc= +github.com/ayn2op/tview v0.0.0-20261008190544-5da45c25c67d/go.mod h1:sMf5NqBlGJjsaGCUycTqTyNG5vewJU6jq/3BdJIzbCU= github.com/bdandy/go-errors v1.2.2 h1:WdFv/oukjTJCLa79UfkGmwX7ZxONAihKu4V0mLIs11Q= github.com/bdandy/go-errors v1.2.2/go.mod h1:NkYHl4Fey9oRRdbB1CoC6e84tuqQHiqrOcZpqFEkBxM= github.com/bdandy/go-socks4 v1.2.3 h1:Q6Y2heY1GRjCtHbmlKfnwrKVU/k81LS8mRGLRlmDlic= @@ -42,8 +42,8 @@ github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/dchest/jsmin v1.0.0 h1:Y2hWXmGZiRxtl+VcTksyucgTlYxnhPzTozCwx9gy9zI= github.com/dchest/jsmin v1.0.0/go.mod h1:AVBIund7Mr7lKXT70hKT2YgL3XEXUaUk5iw9DZ8b0Uc= -github.com/dlclark/regexp2/v2 v2.8.3 h1:4iBHVtmyAsQOOthVo+0v0RxktjLPDOTKx9Nuhf+PpD0= -github.com/dlclark/regexp2/v2 v2.8.3/go.mod h1:avUrQvPaLz2DrFNHJF0taWAFFX2C1GMSSoeiqFjcBmU= +github.com/dlclark/regexp2/v2 v2.8.4 h1:yfDDXTn4oxyLDC10/ieOBNDCCdIVWS9WbT6ddVXsPKI= +github.com/dlclark/regexp2/v2 v2.8.4/go.mod h1:avUrQvPaLz2DrFNHJF0taWAFFX2C1GMSSoeiqFjcBmU= github.com/ebitengine/purego v0.11.1 h1:2zpWRSQNVKN4eKsKO9eM1ILDgWfYMY9GwqRmK6XeQ/0= github.com/ebitengine/purego v0.11.1/go.mod h1:DCHPP08djqhNSoTfImcnHYQRZmd0qhakvrozqaEYhGQ= github.com/gdamore/encoding v1.0.1 h1:YzKZckdBL6jVt2Gc+5p82qhrGiqMdG/eNs6Wy0u3Uhw= @@ -90,8 +90,8 @@ github.com/stretchr/testify v1.11.1 h1:7s2iGBzp5EwR7/aIZr8ao5+dra3wiQyKjjFuvgVKu github.com/stretchr/testify v1.11.1/go.mod h1:wZwfW3scLgRK+23gO65QZefKpKQRnfz6sD981Nm4B6U= github.com/tam7t/hpkp v0.0.0-20160821193359-2b70b4024ed5 h1:YqAladjX7xpA6BM04leXMWAEjS0mTZ5kUU9KRBriQJc= github.com/tam7t/hpkp v0.0.0-20160821193359-2b70b4024ed5/go.mod h1:2JjD2zLQYH5HO74y5+aE3remJQvl6q4Sn6aWA2wD1Ng= -github.com/twmb/murmur3 v1.2.0 h1:S6p/KHqoqsLveELUoKh6zSm/Kwwgl1pStVBgrrLa5UA= -github.com/twmb/murmur3 v1.2.0/go.mod h1:LVqs/avIy0flspVtmBd4VSbogDepFl6Wkj0i0ToccHE= +github.com/twmb/murmur3 v1.2.1 h1:TJzZGygOc1VJ7jiBpy8m7KAAzm67zy1jvkUxxEjJp+g= +github.com/twmb/murmur3 v1.2.1/go.mod h1:LVqs/avIy0flspVtmBd4VSbogDepFl6Wkj0i0ToccHE= github.com/xyproto/randomstring v1.0.5 h1:YtlWPoRdgMu3NZtP45drfy1GKoojuR7hmRcnhZqKjWU= github.com/xyproto/randomstring v1.0.5/go.mod h1:rgmS5DeNXLivK7YprL0pY+lTuhNQW3iGxZ18UQApw/E= github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY= @@ -113,8 +113,8 @@ golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACk golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= golang.org/x/crypto v0.57.0 h1:3ZVCjf8Ggz7zneR/EHRVx68Ctf+2pmIMP2UFhh9cC6M= golang.org/x/crypto v0.57.0/go.mod h1:Fdz0i5U6CoizGwLda9DttjSk6qlZo25zYNtR+ycvuZA= -golang.org/x/exp/shiny v0.0.0-20260908205506-85c1c2202aba h1:BnfR/oT2pP5DHXCNHqgkxE4XT7gaR1n5gdQKycDMH1Y= -golang.org/x/exp/shiny v0.0.0-20260908205506-85c1c2202aba/go.mod h1:LjwWUAy73DRPU6z93L7ykfRhO3biQRlb+dRIYvdwhs8= +golang.org/x/exp/shiny v0.0.0-20261007192929-f45ad48fbe92 h1:7cE4BGFh6IvCa0ujlMC6IpzhmFe6UIabAn0mltXQGX8= +golang.org/x/exp/shiny v0.0.0-20261007192929-f45ad48fbe92/go.mod h1:LjwWUAy73DRPU6z93L7ykfRhO3biQRlb+dRIYvdwhs8= golang.org/x/image v0.46.0 h1:b1+oYj0Jbp6K5MDT4i4/eZpYlk3V8SJhhDKh6LBHAyQ= golang.org/x/image v0.46.0/go.mod h1:3B3W05VGVQyuXucLINLjXKrqISASfi4Xj+iCVkLMwew= golang.org/x/mobile v0.0.0-20260908204917-8b95e45f8d3e h1:zYnHsDmxfxKH/x9DjYNAdoIdMsP8enB1Ncb10b3pdHk= @@ -126,8 +126,8 @@ golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v golang.org/x/net v0.0.0-20211104170005-ce137452f963/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c= golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= -golang.org/x/net v0.59.0 h1:5zfYln+w5XCxwrnMMJPufRgNoXEaGxl0wo5GqPXyues= -golang.org/x/net v0.59.0/go.mod h1:2DA/G1UfVbCpQPeWTmMPGY7Cs2PkBkwu743bVX5PIVg= +golang.org/x/net v0.60.0 h1:79p50tfZlm0J9YfoDsSi639qSXNGVwEzOPLCxM2FsYU= +golang.org/x/net v0.60.0/go.mod h1:2DA/G1UfVbCpQPeWTmMPGY7Cs2PkBkwu743bVX5PIVg= golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= diff --git a/internal/config/keybinds.go b/internal/config/keybinds.go index 5bf9d15..59294ae 100644 --- a/internal/config/keybinds.go +++ b/internal/config/keybinds.go @@ -54,7 +54,7 @@ func key(key, desc string) Keybind { } type ScrollKeybinds struct { - // Scroll the messages list without changing the selection. + // Scroll without changing the selection. ScrollUp Keybind `toml:"scroll_up"` ScrollDown Keybind `toml:"scroll_down"` ScrollTop Keybind `toml:"scroll_top"` @@ -75,10 +75,16 @@ type PickerKeybinds struct { } type TreeKeybinds struct { + ScrollKeybinds + // Scroll sideways to read names that are cut off. + ScrollLeft Keybind `toml:"scroll_left"` + ScrollRight Keybind `toml:"scroll_right"` + SelectionKeybinds // Select the highlighted text-based channel, or expand or collapse the highlighted node. SelectCurrent Keybind `toml:"select_current"` - YankID Keybind `toml:"yank_id"` + + YankID Keybind `toml:"yank_id"` CollapseAll Keybind `toml:"collapse_all"` CollapseParentNode Keybind `toml:"collapse_parent_node"` @@ -197,11 +203,23 @@ func selectionKeybinds(up, down, top, bottom string) SelectionKeybinds { } } +func scrollKeybinds(up, down, top, bottom string) ScrollKeybinds { + return ScrollKeybinds{ + ScrollUp: key(up, "scr up"), + ScrollDown: key(down, "scr down"), + ScrollTop: key(top, "scr top"), + ScrollBottom: key(bottom, "scr btm"), + } +} + func defaultKeybinds() Keybinds { vi := selectionKeybinds("k", "j", "g", "G") emacs := selectionKeybinds("ctrl+p", "ctrl+n", "home", "end") tree := TreeKeybinds{ SelectionKeybinds: vi, + ScrollKeybinds: scrollKeybinds("pgup", "pgdn", "home", "end"), + ScrollLeft: key("h", "scr left"), + ScrollRight: key("l", "scr right"), SelectCurrent: key("enter", "select"), YankID: key("i", "copy id"), @@ -238,12 +256,7 @@ func defaultKeybinds() Keybinds { MembersTree: tree, MessagesList: MessagesListKeybinds{ SelectionKeybinds: vi, - ScrollKeybinds: ScrollKeybinds{ - ScrollUp: key("K", "scr up"), - ScrollDown: key("J", "scr down"), - ScrollTop: key("home", "scr top"), - ScrollBottom: key("end", "scr btm"), - }, + ScrollKeybinds: scrollKeybinds("K", "J", "home", "end"), SelectReply: key("s", "sel reply"), Reply: key("R", "reply"), diff --git a/internal/ui/chat/guildstree/keymap.go b/internal/ui/chat/guildstree/keymap.go index eeb64f4..bee7d52 100644 --- a/internal/ui/chat/guildstree/keymap.go +++ b/internal/ui/chat/guildstree/keymap.go @@ -48,6 +48,7 @@ func (m Model) FullHelp() [][]keybind.Keybind { return [][]keybind.Keybind{ {cfg.SelectUp.Keybind, cfg.SelectDown.Keybind, cfg.SelectTop.Keybind, cfg.SelectBottom.Keybind}, + {cfg.ScrollUp.Keybind, cfg.ScrollDown.Keybind, cfg.ScrollTop.Keybind, cfg.ScrollBottom.Keybind, cfg.ScrollLeft.Keybind, cfg.ScrollRight.Keybind}, selectGroup, {cfg.SelectPreviousUnread.Keybind, cfg.SelectNextUnread.Keybind}, {cfg.YankID.Keybind}, diff --git a/internal/ui/chat/memberstree/keymap.go b/internal/ui/chat/memberstree/keymap.go index a8d9e8e..4076973 100644 --- a/internal/ui/chat/memberstree/keymap.go +++ b/internal/ui/chat/memberstree/keymap.go @@ -29,6 +29,7 @@ func (m Model) FullHelp() [][]keybind.Keybind { kbs := m.cfg.Keybinds.MembersTree return [][]keybind.Keybind{ {kbs.SelectUp.Keybind, kbs.SelectDown.Keybind, kbs.SelectTop.Keybind, kbs.SelectBottom.Keybind}, + {kbs.ScrollUp.Keybind, kbs.ScrollDown.Keybind, kbs.ScrollTop.Keybind, kbs.ScrollBottom.Keybind, kbs.ScrollLeft.Keybind, kbs.ScrollRight.Keybind}, {kbs.SelectCurrent.Keybind, kbs.MoveToParentNode.Keybind, kbs.CollapseParentNode.Keybind, kbs.CollapseAll.Keybind}, {kbs.YankID.Keybind}, } diff --git a/internal/ui/tree/tree.go b/internal/ui/tree/tree.go index 8a3ab46..2f8e328 100644 --- a/internal/ui/tree/tree.go +++ b/internal/ui/tree/tree.go @@ -49,6 +49,18 @@ func bindKeys(kbs config.TreeKeybinds) func(tview.KeyMsg) tree.Action { return tree.ActionMoveToParent case keybind.Matches(key, kbs.SelectCurrent.Keybind): return tree.ActionSelect + case keybind.Matches(key, kbs.ScrollUp.Keybind): + return tree.ActionScrollUp + case keybind.Matches(key, kbs.ScrollDown.Keybind): + return tree.ActionScrollDown + case keybind.Matches(key, kbs.ScrollTop.Keybind): + return tree.ActionScrollTop + case keybind.Matches(key, kbs.ScrollBottom.Keybind): + return tree.ActionScrollBottom + case keybind.Matches(key, kbs.ScrollLeft.Keybind): + return tree.ActionScrollLeft + case keybind.Matches(key, kbs.ScrollRight.Keybind): + return tree.ActionScrollRight } return tree.ActionNone }