클립 보드에서 vi-enabled zsh 또는 bash 쉘로 붙여 넣기


15

키보드를 사용하여 시스템 클립 보드 (또는 텍스트 선택)에서 "vi-like"셸 프롬프트에 붙여넣고 싶습니다. 나는 보통 zsh를 사용하고 때로는 bash를 사용합니다. 두 경우 모두 vi와 비슷한 동작 ( bindkey -v/ set -o vi)으로 쉘을 설정했습니다 .

vim에서 내가 찾고있는 동작은 키 시퀀스로 사용할 수 있습니다 "+p. 그러나이 특정 키 시퀀스는 vi 활성화 쉘 프롬프트에서 예상대로 작동하지 않습니다. zsh 또는 bash 쉘 프롬프트에서 vi와 같은 키 바인딩을 유지하면서 키보드 만 사용 하여이 또는 유사한 동작을 가능하게하는 방법이 있습니까?

-- 편집하다 --

사용 사례 : 터미널 에뮬레이터 인 Pentadactyl addon을 사용하여 Firefox간에 이동하는 경우가 많습니다 . 사용자 정의 키가 있는 Xmonad 창 관리자를 사용하여 이동합니다. 세 프로그램 모두 vi와 유사한 키 바인딩을 가지고 있는데, 이는 "finger memory"에 대해 매우 효율적이므로 vim 구문 (또는 매우 유사한 구문) 만 사용하여 텍스트 사이에 텍스트를 전달하는 것이 이상적입니다.

답변:


9

Zsh는 내부 레지스터 이외의 것을 지원하지 않으며 bash는 내가 아는 한 레지스터를 전혀 지원하지 않습니다. 전반적으로 쉘은 vim 명령이 아닌 vi 명령을 지원합니다.

zsh에는 명령 모드에서 X 선택 항목에 액세스하기위한 개념 증명이 있습니다. 실제로 사용하려면 이러한 기술을 자세히 설명하고 싶을 것입니다. 나는 xsel프로그램을 사용하지만 xclip대신 사용할 수 있습니다 . 레지스터를 사용하여 한 vim 인스턴스에서 다른 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

이 함수는 vi-append-x-selection(유사 커서 후 현재 X 선택을 삽입 p하거나 P). 이 함수 vi-yank-x-selection는 마지막으로 강제 종료 된 텍스트를 X 선택 영역에 복사합니다. zle -N함수를 zle 위젯 (예 : 에디션 명령)으로 선언합니다. bindkey -avi 명령 모드에 대한 바인딩을 설정합니다.


이것은 xsel.zshrc를 약간 수정하여 제안 코드를 설치 하고 복사 한 후에 완벽하게 작동했습니다 ( '^ P'의 원래 동작을 덮어 쓰는 '^ X'대신 '^ P'를 선택했습니다)
Dalker

4

다음은 원래 위젯을 래핑하여 클립 보드가 항상 동기화되는 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

의 매력처럼 작동합니다 xterm-termite.
Rotareti

3

X Window에서는 선택과 클립 보드가 서로 다르며 IMHO "데스크톱 환경"으로 인해 문제가 훨씬 더 어둡습니다.

시프트 인서트가 효과가 있습니까? 베어 X 애플리케이션에서는 이러한 바인딩이 수행 될 때 선택 사항을 붙여 넣어야합니다.


선택과 클립 보드가 다르면 여기서는 실제로 관련이 없습니다. 하나와 호환되는 솔루션은 다른 것과 쉽게 적응할 수 있습니다. 데스크탑 환경은 변경되지 않습니다. 그들의 확산은 선택에서 클립 보드로 향하는 힘의 균형을 변화시켰다.
Gilles 'SO- 악의를 멈춰라'

shift-insert 는 내 환경에서 작동하며 다른 시스템에있을 때 사용하는 것이 좋습니다. 그러나 터미널, vim 자체 및 다른 프로그램 사이의 yank 및 / 또는 붙여 넣기를위한 실제 vim 키 바인딩에 더 가까운 것을 찾고 있습니다.
Dalker

1

이 솔루션은 플러그인을 설치 oh-my-zsh하고 활성화 한 경우 작동합니다 vi-mode.

Gilles ' xselzle기반 솔루션이 작동하지 않았습니다. 그러나 기본적으로 시스템 클립 보드를 사용하도록 vim을 구성했기 때문에 ( set clipboard=unnamedplusin ~/.vimrc), v터미널 일반 모드로 입력 하여 현재 명령을 연 vim다음 vimyank 명령 을 사용하여 X 클립 보드에 복사 할 수 있습니다 .


이것은 ZSH와 어떤 관련이 있습니까? :termNeovim 및 Vim의 새 버전에 포함 된 임베디드에 대해 이야기 하고 있습니까?
Doron Behar

@DoronBehar zsh에서 vi 모드를 활성화 v한 경우 터미널 모드 대신 vim 내부에서 현재 입력 된 명령을 편집하려면 일반 모드로 입력 할 수 있습니다 .
joelostblom

Neovim과 Vim의 :term기능에 대한 답변을 말하고 있다는 사실을 언급해야 합니다. 그렇지 않으면 명확하지 않습니다.
Doron Behar

@DoronBehar 나는 말하고 있지 않다 :term. 그러나, 내가 언급 하는 기능 이 실제로 제공 된다는 것을 발견 했습니다 oh-my-zsh. 이에 따라 답변을 업데이트했습니다.
joelostblom
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.