Reload dari tmux config bukan unbinding keys (bind-key adalah kumulatif)

33

Saya telah bereksperimen dengan pengaturan tmux keybinding yang berbeda dan saya perhatikan hal berikut:

Jika saya memuat ulang konfigurasi tmux saya (dari dalam tmux) keybindings yang pernah saya muat akan tetap dimuat. Satu-satunya cara (saya tahu) untuk membersihkan ini adalah untuk keluar dari semua sesi tmux dan restart. Jadi sepertinya tmux mengingat semua keybindings yang dimuat sebelumnya dan hanya akan menghapusnya pada awal yang baru atau dengan secara eksplisit melepas ikatannya.

Untuk membuat ulang ini:

  • buka terminal (A)
  • mulai tmux
  • periksa apakah ikatan tombol menunjukkan jam (tekan PREFIX C-t)
  • tekan PREFIX ?untuk melihat pengikat tombol dalam daftar
  • sunting ~/.tmux.conf
  • tambahkan pengikat kunci ( bind C-t display "Keybinding C-t")
  • reload tmux config ( PREFIX : source-file ~/.tmux.conf)
  • periksa apakah pengikatan tombol berfungsi (tekan PREFIX C-t)
  • tekan PREFIX ?untuk melihat pengikat kunci baru dalam daftar
  • edit ~/.tmux.conflagi
  • menghapus keybinding (jadi hapus bind C-t display "Keybinding C-t")
  • reload tmux config ( PREFIX : source-file ~/.tmux.conf)
  • periksa apakah keybinding berfungsi (tekan PREFIX C-t), masih menampilkan "Keybinding Ct"
  • tekan PREFIX ?untuk melihat bahwa pengikat kunci baru masih ada dalam daftar
  • keluar dari tmux
  • masukkan tmux
  • periksa apakah pengikatan kunci yang asli berfungsi lagi (tekan PREFIX C-t), sekarang ia akan menampilkan jam lagi
  • tekan PREFIX ?untuk melihat bahwa penjilidan kunci baru telah dihapus dari daftar

Pertanyaan saya: apakah ada cara untuk memerintahkan tmux untuk "melupakan" semua konfigurasi yang dimuat lalu memuat .tmux.conf?

Niels Bom
sumber

Jawaban:

19

Menurut tmux(1)halaman manual, unbind-key -aadalah apa yang Anda cari.

Perhatikan bahwa tmuxmenjalankan server yang hanya akan keluar setelah semua sesi ditutup, dan ikatan kunci adalah per-server. Karenanya begitu Anda membuat ikatan, itu akan tetap ada di atas semua pelepasan klien.

Yang mengatakan, letakkan unbind-key -adi bagian paling atas file konfigurasi Anda, dan pada konfigurasi ulang itu harus melakukan apa yang Anda inginkan - batalkan segalanya dan mulai mengikat dari awal. Atau - jika modifikasi Anda lebih kecil - batasi hanya apa yang ingin Anda ubah.

peterph
sumber
Ya dan saya sudah menyatakan itu dalam pertanyaan saya. Tetapi alih-alih "mengatur ulang" semua kunci yang mungkin diikat secara manual, saya ingin tmux memulai kembali dengan "clean slate" dan kemudian memuat ulang file konfigurasi.
Niels Bom
@NielsBom periksa jawaban yang diperbarui, tolong
peterph
Anda benar, unbind-key -amenghapus semua keybindings. Saya akan menandai jawaban Anda sebagai benar, tetapi demi pemirsa lain, saya juga akan menambahkan "retasan" yang telah saya terapkan untuk memperbaiki masalah unbind-key -a.
Niels Bom
Lihat jawaban saya untuk solusi saya.
Niels Bom
16

Solusi yang benar (oleh Peter

Jadi @peterph memberikan jawaban yang benar yaitu unbind-key -ayang melakukan hal berikut: (man tmux)

Jika -a ada, semua ikatan kunci dihapus.

Solusi yang bisa diterapkan

Masalahnya (bagi saya) adalah bahwa "semua" sebenarnya berarti semua. Termasuk tmux keybindings hadir . Jika Anda menjalankan unbind-key -aperintah tmux secara instan tidak memiliki ikatan kunci sama sekali lagi sehingga Anda bahkan tidak bisa masuk ke mode perintah atau melakukan apa pun pada dasarnya.

Perbaikan saya (agak jelek) untuk ini adalah sebagai berikut:

  • buat .tmux.reset.confyang menghapus semua keybindings dan kemudian rebind semua yang tmux miliki secara default
  • sumber yang mengatur ulang di bagian atas Anda .tmux.conf

Saya .tmux.conf:

# always load the reset file first
source-file ~/.tmux.reset.conf

Saya .tmux.reset.conf:

# First remove *all* keybindings
unbind-key -a
# Now reinsert all the regular tmux keys
bind-key C-b send-prefix
bind-key C-o rotate-window
bind-key C-z suspend-client
bind-key Space next-layout
bind-key ! break-pane
bind-key " split-window
bind-key # list-buffers
bind-key $ command-prompt -I #S "rename-session '%%'"
bind-key % split-window -h
bind-key & confirm-before -p "kill-window #W? (y/n)" kill-window
bind-key ' command-prompt -p index "select-window -t ':%%'"
bind-key ( switch-client -p
bind-key ) switch-client -n
bind-key , command-prompt -I #W "rename-window '%%'"
bind-key - delete-buffer
bind-key . command-prompt "move-window -t '%%'"
bind-key 0 select-window -t :0
bind-key 1 select-window -t :1
bind-key 2 select-window -t :2
bind-key 3 select-window -t :3
bind-key 4 select-window -t :4
bind-key 5 select-window -t :5
bind-key 6 select-window -t :6
bind-key 7 select-window -t :7
bind-key 8 select-window -t :8
bind-key 9 select-window -t :9
bind-key : command-prompt
bind-key ; last-pane
bind-key = choose-buffer
bind-key ? list-keys
bind-key D choose-client
bind-key L switch-client -l
bind-key [ copy-mode
bind-key ] paste-buffer
bind-key c new-window
bind-key d detach-client
bind-key f command-prompt "find-window '%%'"
bind-key i display-message
bind-key l last-window
bind-key n next-window
bind-key o select-pane -t :.+
bind-key p previous-window
bind-key q display-panes
bind-key r refresh-client
bind-key s choose-session
bind-key t clock-mode
bind-key w choose-window
bind-key x confirm-before -p "kill-pane #P? (y/n)" kill-pane
bind-key { swap-pane -U
bind-key } swap-pane -D
bind-key ~ show-messages
bind-key PPage copy-mode -u
bind-key -r Up select-pane -U
bind-key -r Down select-pane -D
bind-key -r Left select-pane -L
bind-key -r Right select-pane -R
bind-key -r M-1 select-layout even-horizontal
bind-key -r M-2 select-layout even-vertical
bind-key -r M-3 select-layout main-horizontal
bind-key -r M-4 select-layout main-vertical
bind-key -r M-5 select-layout tiled
bind-key -r M-n next-window -a
bind-key -r M-o rotate-window -D
bind-key -r M-p previous-window -a
bind-key -r M-Up resize-pane -U 5
bind-key -r M-Down resize-pane -D 5
bind-key -r M-Left resize-pane -L 5
bind-key -r M-Right resize-pane -R 5
bind-key -r C-Up resize-pane -U
bind-key -r C-Down resize-pane -D
bind-key -r C-Left resize-pane -L
bind-key -r C-Right resize-pane -R

Sepertinya ini bisa bekerja dengan tmux key-tables (sejauh yang saya tahu) tetapi Anda tidak bisa menambahkan key-tables baru.

Niels Bom
sumber
1
Kemungkinan Anda dapat dengan cepat menghasilkan yang setara .tmux.reset.confdengan Anda dengan menjalankan tmux list-keyssesi "bersih".
jw013
2
tmux -f /dev/null -L temp start-server \; list-keysakan secara efektif menghasilkan default (meskipun Anda perlu menambahkan backslash sebelum titik koma dalam pengikatannya).
Chris Johnsen
@ ChrisJohnsen Bisakah Anda menjelaskan pada start-server dalam jawaban yang terpisah?
Niels Bom
7

Saat ini tidak ada cara langsung untuk mengatur ulang ikatan kunci ke standarnya; inisialisasi binding standar (dalam key_bindings_init()) dilakukan sekali ketika server tmux pertama kali dimulai (dalam server_start()), dan tidak ada mekanisme untuk mengatur ulang satu kunci.

Untuk skenario yang Anda inginkan di mana Anda ingin tindakan sumber file konfigurasi Anda untuk membangun kembali default mengikat yang sebelumnya diganti oleh kebiasaan yang mengikat yang sejak itu telah dihapus dari file konfigurasi Anda, metode yang Anda merancang wajar (meskipun sayangnya verbose): unbind-key -a, kemudian bangun kembali semua ikatan "default", lalu buat ikatan kustom Anda (beberapa di antaranya mungkin mengesampingkan ikatan "default").

Binding server saat ini dapat diekstraksi dengan list-keysperintah * ; ini dapat membantu menghasilkan / memelihara .tmux.reset.conffile yang Anda usulkan , tetapi Anda perlu cara untuk mengekstrak binding default , bukan binding saat ini .

* Ada beberapa situasi di mana output list-keyssaat ini tidak secara langsung dapat digunakan: pengikatan untuk titik koma membutuhkan titik koma yang lolos dengan garis miring terbalik agar tidak ditafsirkan sebagai pemisah perintah tmux , dan setiap binding yang memiliki argumen yang menggunakan tanda kutip ganda di dalam single tanda kutip (tidak ada ikatan default seperti ini) akan keluar sebagai tanda kutip ganda di dalam qoutes ganda .

Untuk mendapatkan binding standar, Anda memerlukan server sementara dengan konfigurasi minimal (yaitu tidak ada binding kustom) sehingga Anda dapat menangkap list-keyshasilnya. Tidak ada batasan jumlah server tmux yang dapat Anda jalankan, tetapi masing-masing harus menggunakan socket pathname yang berbeda; opsi -Ldan -S tmux dapat digunakan untuk menentukan nama socket (dalam $TMPDIR/tmux-$UIDatau nama path socket penuh. Jadi, untuk berbicara dengan (atau memulai) server baru pada socket bernama temp, Anda akan menggunakan ini:

tmux -L temp …

Untuk memastikan itu tidak menggunakan Anda .tmux.conf, Anda gunakan -funtuk menyuruhnya membaca /dev/null(file khusus yang selalu kosong):

tmux -f /dev/null -L temp …

Catatan : ini tidak mencegah pemrosesan /etc/tmux.conf, jika file tersebut ada; path ke "file konfigurasi sistem" ini adalah kode-keras dan tidak ada opsi untuk mem-bypass-nya (singkat menambal kode).

Biasanya, Anda memerlukan new-sessionperintah untuk benar-benar memulai server, tetapi kami tidak ingin sesi apa pun, hanya server yang diinisialisasi untuk kueri. The start-serverperintah tidak hanya itu: mulai server tanpa membuat sesi apapun.

tmux -f /dev/null -L temp start-server …

Sekarang, kita hanya perlu menambahkan perintah "query" kami ( list-keysdalam hal ini):

tmux -f /dev/null -L temp start-server \; list-keys

Catatan : titik koma perlu diloloskan atau dikutip untuk mencegah shell memperlakukannya sebagai pemisah perintah shell karena kami ingin itu menjadi pemisah perintah tmux .

Karena tidak ada sesi untuk dipertahankan, server akan keluar secara otomatis setelah selesai menjalankan list-keysperintah.

Jadi, Anda dapat menggunakan perintah seperti ini untuk menghasilkan sebagian besar file Anda .tmux.reset.conftanpa harus khawatir untuk sementara waktu menghapus .tmux.conffile Anda (untuk membiarkan Anda melihat hanya binding standar) dan tanpa harus mematikan server yang ada.


Jika run-shellperintah itu sinkron, Anda bisa menyematkan panggilan seperti ini di file konfigurasi Anda (menangkap ke file sementara yang kemudian Anda proses dengan source-file) daripada memiliki file statis (Anda .tmux.reset.conf). Itu akan membiarkan Anda selalu menggunakan binding default dari versi tmux Anda saat ini (binding default sesekali berubah). Sayangnya, penyelesaian run-shellperintah saat ini tidak sinkron sehubungan dengan perintah berikutnya (perintah yang datang setelah run-shellperintah biasanya akan berjalan sebelum proses melahirkan run-shelltelah memiliki kesempatan untuk menyelesaikan).

Chris Johnsen
sumber
6

Berikut adalah rollup dari semua jawaban lain menjadi skrip bash yang secara otomatis akan menghasilkan .tmux.reset.confdari binding kunci default:

#!/bin/bash
tmux -f /dev/null -L temp start-server \; list-keys | \
  sed -r \
  -e "s/bind-key(\s+)([\"#~\$])(\s+)/bind-key\1\'\2\'\3/g" \
  -e "s/bind-key(\s+)([\'])(\s+)/bind-key\1\"\2\"\3/g" \
  -e "s/bind-key(\s+)([;])(\s+)/bind-key\1\\\\\2\3/g" \
  -e "s/command-prompt -I #([SW])/command-prompt -I \"#\1\"/g" \
  > ~/.tmux.reset.conf

Baris sedperintah tertanam menjaga keluar dari berbagai bagian output list-keys. Ini mungkin memerlukan beberapa penyesuaian untuk spesifikasi sistem Anda.

Dalam .tmux.conffile Anda, cukup lepaskan ikatan semua kunci dan sumber file ini sebelum menentukan ikatan kunci Anda sendiri:

unbind-key -a
source-file ~/.tmux.reset.conf
Richard Cook
sumber
4

Silakan juga merujuk ke jawaban lain di sini, karena mereka melakukan pekerjaan dengan baik untuk menjelaskan situasi. Saya miliki di sini tmux 1.8 saya kompatibel tmux.reset.conf, yang saya harus membuat beberapa modifikasi setelah menyalin tmux -f /dev/null -L temp start-server \; list-keysoutput. Secara khusus, beberapa hal harus dikutip.

# First remove *all* keybindings
unbind-key -a
# Now reinsert all the regular tmux keys
bind-key C-b send-prefix
bind-key C-o rotate-window
bind-key C-z suspend-client
bind-key Space next-layout
bind-key ! break-pane
bind-key '"' split-window
bind-key '#' list-buffers
bind-key '$' command-prompt -I "#S" "rename-session '%%'"
bind-key % split-window -h
bind-key & confirm-before -p "kill-window #W? (y/n)" kill-window
bind-key "'" command-prompt -p index "select-window -t ':%%'"
bind-key ( switch-client -p
bind-key ) switch-client -n
bind-key , command-prompt -I "#W" "rename-window '%%'"
bind-key - delete-buffer
bind-key . command-prompt "move-window -t '%%'"
bind-key 0 select-window -t :0
bind-key 1 select-window -t :1
bind-key 2 select-window -t :2
bind-key 3 select-window -t :3
bind-key 4 select-window -t :4
bind-key 5 select-window -t :5
bind-key 6 select-window -t :6
bind-key 7 select-window -t :7
bind-key 8 select-window -t :8
bind-key 9 select-window -t :9
bind-key : command-prompt
bind-key \; last-pane
bind-key = choose-buffer
bind-key ? list-keys
bind-key D choose-client
bind-key L switch-client -l
bind-key [ copy-mode
bind-key ] paste-buffer
bind-key c new-window
bind-key d detach-client
bind-key f command-prompt "find-window '%%'"
bind-key i display-message
bind-key l last-window
bind-key n next-window
bind-key o select-pane -t :.+
bind-key p previous-window
bind-key q display-panes
bind-key r refresh-client
bind-key s choose-tree
bind-key t clock-mode
bind-key w choose-window
bind-key x confirm-before -p "kill-pane #P? (y/n)" kill-pane
bind-key z resize-pane -Z
bind-key { swap-pane -U
bind-key } swap-pane -D
bind-key '~' show-messages
bind-key PPage copy-mode -u
bind-key -r Up select-pane -U
bind-key -r Down select-pane -D
bind-key -r Left select-pane -L
bind-key -r Right select-pane -R
bind-key M-1 select-layout even-horizontal
bind-key M-2 select-layout even-vertical
bind-key M-3 select-layout main-horizontal
bind-key M-4 select-layout main-vertical
bind-key M-5 select-layout tiled
bind-key M-n next-window -a
bind-key M-o rotate-window -D
bind-key M-p previous-window -a
bind-key -r M-Up resize-pane -U 5
bind-key -r M-Down resize-pane -D 5
bind-key -r M-Left resize-pane -L 5
bind-key -r M-Right resize-pane -R 5
bind-key -r C-Up resize-pane -U
bind-key -r C-Down resize-pane -D
bind-key -r C-Left resize-pane -L
bind-key -r C-Right resize-pane -R
Steven Lu
sumber
4

Saya bertanya ke hulu mereka sepertinya tidak mau memperbaikinya (kecuali seseorang mengajukan PR).

Inilah saya secara manual lolos tmux list-keys, diperoleh melalui contoh server baru dengan

tmux -f /dev/null -L temp start-server \; list-keys

(terima kasih atas jawaban sebelumnya)

## See https://github.com/tmux/tmux/issues/729: How to reset key bindings to default? #729

bind-key    -T prefix C-b              send-prefix
bind-key    -T prefix C-o              rotate-window
bind-key    -T prefix C-z              suspend-client
bind-key    -T prefix Space            next-layout
bind-key    -T prefix !                break-pane
bind-key    -T prefix '"'                split-window
bind-key    -T prefix '#'                list-buffers
bind-key    -T prefix '$'                command-prompt -I '#'S "rename-session '%%'"
bind-key    -T prefix %                split-window -h
bind-key    -T prefix &                confirm-before -p "kill-window #W? (y/n)" kill-window
bind-key    -T prefix "'"                command-prompt -p index "select-window -t ':%%'"
bind-key    -T prefix (                switch-client -p
bind-key    -T prefix )                switch-client -n
bind-key    -T prefix ,                command-prompt -I '#W' "rename-window '%%'"
bind-key    -T prefix -                delete-buffer
bind-key    -T prefix .                command-prompt "move-window -t '%%'"
bind-key    -T prefix 0                select-window -t :=0
bind-key    -T prefix 1                select-window -t :=1
bind-key    -T prefix 2                select-window -t :=2
bind-key    -T prefix 3                select-window -t :=3
bind-key    -T prefix 4                select-window -t :=4
bind-key    -T prefix 5                select-window -t :=5
bind-key    -T prefix 6                select-window -t :=6
bind-key    -T prefix 7                select-window -t :=7
bind-key    -T prefix 8                select-window -t :=8
bind-key    -T prefix 9                select-window -t :=9
bind-key    -T prefix ':'                command-prompt
bind-key    -T prefix \;                last-pane
bind-key    -T prefix =                choose-buffer
bind-key    -T prefix ?                list-keys
bind-key    -T prefix D                choose-client
bind-key    -T prefix L                switch-client -l
bind-key    -T prefix M                select-pane -M
bind-key    -T prefix [                copy-mode
bind-key    -T prefix ]                paste-buffer
bind-key    -T prefix c                new-window
bind-key    -T prefix d                detach-client
bind-key    -T prefix f                command-prompt "find-window '%%'"
bind-key    -T prefix i                display-message
bind-key    -T prefix l                last-window
bind-key    -T prefix m                select-pane -m
bind-key    -T prefix n                next-window
bind-key    -T prefix o                select-pane -t :.+
bind-key    -T prefix p                previous-window
bind-key    -T prefix q                display-panes
bind-key    -T prefix r                refresh-client
bind-key    -T prefix s                choose-tree
bind-key    -T prefix t                clock-mode
bind-key    -T prefix w                choose-window
bind-key    -T prefix x                confirm-before -p "kill-pane #P? (y/n)" kill-pane
bind-key    -T prefix z                resize-pane -Z
bind-key    -T prefix {                swap-pane -U
bind-key    -T prefix }                swap-pane -D
bind-key    -T prefix '~'                show-messages
bind-key    -T prefix PPage            copy-mode -u
bind-key -r -T prefix Up               select-pane -U
bind-key -r -T prefix Down             select-pane -D
bind-key -r -T prefix Left             select-pane -L
bind-key -r -T prefix Right            select-pane -R
bind-key    -T prefix M-1              select-layout even-horizontal
bind-key    -T prefix M-2              select-layout even-vertical
bind-key    -T prefix M-3              select-layout main-horizontal
bind-key    -T prefix M-4              select-layout main-vertical
bind-key    -T prefix M-5              select-layout tiled
bind-key    -T prefix M-n              next-window -a
bind-key    -T prefix M-o              rotate-window -D
bind-key    -T prefix M-p              previous-window -a
bind-key -r -T prefix M-Up             resize-pane -U 5
bind-key -r -T prefix M-Down           resize-pane -D 5
bind-key -r -T prefix M-Left           resize-pane -L 5
bind-key -r -T prefix M-Right          resize-pane -R 5
bind-key -r -T prefix C-Up             resize-pane -U
bind-key -r -T prefix C-Down           resize-pane -D
bind-key -r -T prefix C-Left           resize-pane -L
bind-key -r -T prefix C-Right          resize-pane -R
bind-key    -T root   MouseDown1Pane   select-pane -t = \; send-keys -M
bind-key    -T root   MouseDown1Status select-window -t =
bind-key    -T root   MouseDown3Pane   if-shell -F -t = '#{mouse_any_flag}' "select-pane -t=; send-keys -M" "select-pane -mt="
# Someone also was wondering how to fix here: http://tmux-users.narkive.com/dTFVvLMh/is-it-possible-to-have-a-binding-that-brings-back-mouse-behavior
bind-key    -T root   MouseDrag1Pane   if-shell -F -t = '#{mouse_any_flag}' "if -Ft= '#{pane_in_mode}' 'copy-mode -M' 'send-keys -M' " "copy-mode -M"

bind-key    -T root   MouseDrag1Border resize-pane -M
bind-key    -T root   WheelUpPane      if-shell -F -t = '#{mouse_any_flag}' "send-keys -M" "if -Ft= '#{pane_in_mode}' 'send-keys -M' 'copy-mode -et=' "
bind-key    -T root   WheelUpStatus    previous-window
bind-key    -T root   WheelDownStatus  next-window

Di atas adalah pada github sehingga Anda dapat melakukan:

curl -L https://raw.githubusercontent.com/timotheecour/dinocode/master/tmux_list_keys_escaped.txt > ~/.tmux.reset.conf
unbind-key -a
source-file ~/.tmux.reset.conf

CATATAN: Entah bagaimana jawaban Richard Cook masih menghasilkan masalah untuk melarikan diri.

timotheecour
sumber
Selamat datang di unix.SE! Kami sering waspada terhadap tautan biasa sehingga saya menempelkannya langsung di sini (tetapi menyimpan tautan untuk referensi). Itu cara yang disukai di sini. Tautan memang mati (saya tahu, itu github! Tapi tetap saja bisa mati di beberapa titik). Bagaimanapun itu adalah jawaban yang baik (+1). Mungkin bisa lebih baik jika Anda berhasil memperbaiki masalah dengan kode sed Richard. Itu berumur satu tahun dan tmux memiliki kebiasaan buruk karena tidak 100% kompatibel.
grochmal
2

Berikut ini adalah versi tweak jawaban Richard Cook untuk memperbaiki masalah pelolosan pada tmux 2.1

#!/bin/bash
tmux -f /dev/null -L temp start-server \; list-keys | \
    sed -r \
    -e "s/(bind-key.*\s+)([\"#~\$])(\s+)/\1\'\2\'\3/g" \
    -e "s/(bind-key.*\s+)([\'])(\s+)/\1\"\2\"\3/g" \
    -e "s/(bind-key.*\s+)([;])(\s+)/\1\\\\\2\3/g" \
    -e "s/(command-prompt -I )#([SW])/\1\"#\2\"/g" \
    -e "s/(if-shell -F -t = )#([^ ]+)/\1\"#\2\"/g" \
    > ~/.tmux.reset.conf                              

Tambahkan baris berikut ke awal .tmux.conf

unbind-key -a
source-file ~/.tmux.reset.conf
MILF
sumber