从剪贴板粘贴到启用 vi 的 zsh 或 bash shell

Dal*_*ker 18 shell bash zsh vi clipboard

我希望能够使用键盘从系统剪贴板(或文本选择)粘贴到我的“类似 vi”的 shell 提示中。我通常使用 zsh,有时使用 bash。在这两种情况下,我都使用类似 vi 的行为 ( bindkey -v/ set -o vi)设置了 shell 。

在 vim 中,我正在寻找的行为可通过 key sequence 获得"+p。但是,此特定键序列在启用 vi 的 shell 提示中无法按预期工作。有什么方法可以启用这个或类似的行为,只使用键盘,同时在 zsh 或 bash shell 提示中保留类似 vi 的键绑定?

- 编辑 -

用例:我经常在带有Pentadactyl 插件、终端模拟器和 vim 本身的Firefox 之间导航- 使用带有自定义键的Xmonad窗口管理器来移动。所有三个程序都有类似 vi 的键绑定,这非常有效(对于“手指记忆”),因此最好仅使用 vim 语法(或非常相似的语法)在它们之间进行文本通信。

Gil*_*il' 10

Zsh 除了内部寄存器之外不支持任何东西,据我所知 bash 根本不支持 register。总的来说,shell 支持 vi 命令,而不是 vim 命令。

在 zsh 中,这是从命令模式访问 X 选择的概念验证。对于实际使用,您需要详细说明这些技术。我用的xsel程序,你可以用xclip;请参阅如何使用寄存器从一个 vim 实例复制到另一个。您会在zle 手册中找到我使用的功能。

vi-append-x-selection () { RBUFFER=$(xsel -o -p </dev/null)$RBUFFER; }
zle -N vi-append-x-selection
bindkey -a '^X' vi-append-x-selection
vi-yank-x-selection () { print -rn -- $CUTBUFFER | xsel -i -p; }
zle -N vi-yank-x-selection
bindkey -a '^Y' vi-yank-x-selection
Run Code Online (Sandbox Code Playgroud)

该函数vi-append-x-selection在光标后插入当前的 X 选择(类似于pP)。该函数vi-yank-x-selection将最后杀死或拉出的文本复制到 X 选择。zle -N将函数声明为 zle 小部件(即编辑命令)。bindkey -a为 vi 命令模式设置绑定。


ole*_*enb 5

这是 zsh(vi 模式)的解决方案,它包装原始小部件,以便剪贴板始终同步

替换xclip为您首选的剪贴板工具。

function x11-clip-wrap-widgets() {
    # NB: Assume we are the first wrapper and that we only wrap native widgets
    # See zsh-autosuggestions.zsh for a more generic and more robust wrapper
    local copy_or_paste=$1
    shift

    for widget in $@; do
        # Ugh, zsh doesn't have closures
        if [[ $copy_or_paste == "copy" ]]; then
            eval "
            function _x11-clip-wrapped-$widget() {
                zle .$widget
                xclip -in -selection clipboard <<<\$CUTBUFFER
            }
            "
        else
            eval "
            function _x11-clip-wrapped-$widget() {
                CUTBUFFER=\$(xclip -out -selection clipboard)
                zle .$widget
            }
            "
        fi

        zle -N $widget _x11-clip-wrapped-$widget
    done
}


local copy_widgets=(
    vi-yank vi-yank-eol vi-delete vi-backward-kill-word vi-change-whole-line
)
local paste_widgets=(
    vi-put-{before,after}
)

# NB: can atm. only wrap native widgets
x11-clip-wrap-widgets copy $copy_widgets
x11-clip-wrap-widgets paste  $paste_widgets
Run Code Online (Sandbox Code Playgroud)


Dor*_*har 5

我推荐一个 ZSH 插件:https ://github.com/kutsan/zsh-system-clipboard 。要安装它,请运行:

git clone https://github.com/kutsan/zsh-system-clipboard ~/.zsh/plugins/zsh-system-clipboard
Run Code Online (Sandbox Code Playgroud)

然后将文件来源到您的.zshrc

source "$HOME/.zsh/plugins/zsh-system-clipboard/zsh-system-clipboard.zsh"
Run Code Online (Sandbox Code Playgroud)

该插件支持使用 Tmux 缓冲区来定位剪贴板的保存位置,您甚至可以为剪切/粘贴/复制功能配置替代键绑定。

该插件已经处理了一个小细节,其他答案建议没有处理,那就是区分带换行符和不带换行符的系统剪贴板内容(请参阅PR)。对剪贴板输入的这种小检查应确保粘贴任何类型内容的体验与 Vim/Neovim 相同。