在 mu Ubuntu 12.04 设置上,我的 tmux 剪贴板复制和粘贴命令设置如下:
set -g prefix M-a
unbind C-b
bind C-c run "tmux save-buffer - | xclip -i -sel clipboard"
bind C-v run "tmux set-buffer \"$(xclip -o -sel clipboard)\"; tmux paste-buffer"
直到大约一个月前,这种方法在很长一段时间内都很有效,当时我怀疑进行了一些配置更改或软件包更改,从而破坏了上述内容。在 GNOME 终端中,使用prefix+ctrl-v和粘贴仍然可以正常工作ctrl-shift-v。
然而,xclip
无论我做什么,复制命令都不再起作用,并且我尝试删除上面的自定义前缀绑定,使用-select
而不是-sel
使用,不使用clipboard
等。对于像我这样的 GVim 用户来说,这几乎是一个表演障碍,因为我不这样做甚至没有ctrl-shift-c使用 tmux 接管 shell 的 GNOME 终端解决方法。我进入复制模式,用space+选择文本movement,当我执行prefix+时ctrl-c,绝对没有任何反应。在此之前,tmux 会在底部的通知部分显示一条确认消息。
有人对如何调试这个有什么建议吗?这对生产力造成了相当大的打击。我也许可以使用目前临时文件解决方法,但很高兴知道 发生了什么事xclip
。
答案1
这xsel
实用程序与 类似xclip
,但实现方式略有不同。通常我希望它们以相同的方式运行,但它们不会进行完全相同的 X 库调用,因此在某些极端情况下可能xsel
会起作用但不起作用xclip
,反之亦然。尝试:
bind C-c run "tmux save-buffer - | xsel -ib"
bind C-v run "tmux set-buffer \"$(xsel -ob)\"; tmux paste-buffer"
答案2
添加-b
to run-shell
(或run
) 命令解决了该问题。跟-b
shell命令是在后台运行的。
bind C-c run-shell -b "tmux save-buffer - | xclip -i -sel clipboard"
答案3
虽然我无法再重现它,但这是您的案例中可能发生的情况的技术答案。
首先,您需要了解 X11 剪贴板的工作原理。你可以阅读 jwz 的文章:http://www.jwz.org/doc/x-cut-and-paste.html
简而言之,保存剪贴板内容的应用程序需要运行,直到其他应用程序声明所有权。因此,当您运行时xclip -i <<< test
,您可以看到 xclip 在后台运行,直到您做出另一个选择:
$ xclip -i <<< test
$ ps
PID TTY TIME CMD
10166 pts/8 00:00:00 xclip
10171 pts/8 00:00:00 ps
19345 pts/8 00:00:00 bash
现在一切都很好,但是当您退出此 shell 时,默认情况下,通过向它们发送 HUP 信号来终止属于此会话的所有进程。这意味着 xclip 将被终止,您将无法再访问剪贴板内容。
因此,建议的解决方法(如果您没有 xsel)是使用以下绑定忽略 HUP 信号:
bind C-c run "tmux save-buffer - | nohup >/dev/null 2>/dev/null xclip -i -sel clipboard"
xsel
不受这个问题的影响,因为在 fork() 之后它做的第一件事就是将自己与控制终端解除关联,这样当它的 shell 退出时它就不会收到 HUP 信号(你甚至不会在上面的 ps 中看到它)输出,但仅当您执行 a ps -e | grep xsel
) 时。
答案4
这是一个老问题,但我怀疑我有解决方案,取自Arch wiki 的 Tmux 页面:
xclip 也可以用于此目的,与 xsel 不同,它在打印不适合当前区域设置的原始比特流时效果更好。尽管如此,使用 xsel 而不是 xclip 更简洁,因为 xclip 在从 tmux 的缓冲区读取数据后不会关闭 STDOUT。因此,tmux 并不知道复制任务已完成,而是继续等待 xclip 的终止,从而导致 tmux 无响应。解决方法是将 xclip 的 STDOUT 重定向到 /dev/null
所以你的命令应该变成:
bind C-c run "tmux save-buffer - | xclip -i -sel clipboard >/dev/null"