貼り付けオプションを設定しますが、1つの挿入のみ


16

Vim 'paste'オプションを設定し、テキストを挿入して、前の値に戻す簡単な方法が必要です'paste'

典型的なユースケースでは、自動インデントなどのアクティブな挿入モードの書き換えに関係なく、Vimの状態を変更せずに、OSクリップボードのコンテンツを文字通り挿入します。別のユースケースは、OSマクロ機能がキーストロークをVimに挿入し、リテラルテキストとして解釈できるようにすることです。

これは明らかに他のオプションに一般化されます-一般的な考え方は、いくつかのオプションを設定することですが、挿入モードを1回実行する間のみです。

基本的に_i、これを行うマクロにキーシーケンス(たとえば)をバインドしたい

:set paste
i…<Esc>
:set nopaste

ここi…<Esc>で、iコマンドと同様に挿入モードに切り替えて、コマンドモードに戻ったときにマクロを再開しますが、'paste'事前にアクティブだった場合はまだアクティブになります。これどうやってするの?

注:OSクリップボードのコンテンツは"*registerにマップさます。それが機能する場合、この'paste'オプションはあまり役に立ちません。この質問の動機付けのシナリオは、"*レジスタサポートの条件が満たされていない場合です。Vimは+xterm_clipboard機能でコンパイルされていないか、Screenなどの端末で実行されているか、SSHを介してアンビエントXサーバーから隔離されています。


1
私はあなたの質問が好きです(私は何度もそこに行きました)。ただし、+またはから*登録する方が簡単ではありませんか?
よ」

@yo ' 彼らが働くときだけ。私がVimを使用する場合、これはよくありません。
ジル「SO-悪であるのをやめる」

回答:


15

これを試してみてください:

function! Paste_Func()
    let s:inPaste = &paste
    if !s:inPaste
        set paste
    endif

    echom s:inPaste
    augroup paste_callback
        autocmd!
        autocmd InsertLeave <buffer> call Paste_End()
    augroup END

    startinsert
endfunction

function! Paste_End()
    augroup paste_callback
        autocmd!
    augroup END
    augroup! paste_callback

    if !s:inPaste
        set nopaste
    endif
endfunction

map _i :call Paste_Func()<cr>

現在の貼り付けステータスがinPaste変数に保存され、まだ設定されていない場合は貼り付けが設定されます。次に、挿入モードを終了するときにautocmdを設定し、挿入モードにします。

挿入モードを終了すると、autocmdが実行され、最初にautocmdが削除され(したがって、他の方法で挿入モードを終了すると実行されません)、最後に貼り付けモードではなかった場合は最終的にnopasteが設定されます。

また、ターミナルでvimを使用している場合は、vim-bracketed-pasteご覧ください。これは、いくつかのターミナルエミュレーターが提供するブラケットペーストモード機能を使用して、モードを自動的に貼り付けて設定するかどうかを検出します。

編集:スクリプトを修正しました


これは正しい軌道に乗っているように見えます(特に、通常のワールドコマンドによって一連の挿入を「ブラケット」する方法がわかりませんでした)。ありがとう。しかし、それはまったく正しくなく、問題がどこにあるのかわかりません:after _ipaste前にオンになっていたとしても、オプションはオフです。
ジル「SO-悪であるのをやめる」

あなたが正しいです!私はそれをテストしたと確信していますが、何かを変更したに違いありません。投稿のスクリプトを更新しました。今すぐ動作するか確認してください。
チャド

4

ただし、'paste'事前にアクティブになっていた場合は、まだアクティブになります。

'paste'できるだけ短時間アクティブにする必要があります。貼り付けられているテキストの誤解を避けることを唯一の目的とするため、多くの機能(マップを含む)を無効にします。そのため、引用された要件は実際には必要ではないと思います。

そうは言っても、実際に設定する必要なしに貼り付けるのは非常に簡単'paste'です。gvimを実行している場合、または+xterm_clipboardコンソールvimを使用"+pしている場合は、単に使用してOSクリップボードから貼り付けることができます。

貼り付け中の自動インデントの問題は、実際には2つのシナリオでのみ発生します。挿入モード(<C-r>+)でレジスターの内容を挿入するか、マウスで中クリックして貼り付けます。

挿入モードでレジスタの内容を挿入する代わりに、通常モードでレジスタから貼り付けることで、再フォーマットの問題を回避できます。

マウスで貼り付けを中央クリックする場合'mouse'は、ターミナルの代わりにVimに中央クリックを処理させるオプションを使用します。Vimは、入力されたテキストを入力されたと解釈する代わりに、内容をそのまま挿入します。


2
これのどれも私の質問に答えません。明確な要件を理由に入れました!通常'paste'、事前に実際にはアクティブではありませんが、これについて考える必要はありません。私は、Vimビルドに機能がないxterm_clipboardため、またはたとえば現在接続されているScreenセッションで作業しているため、XクリップボードまたはマウスにアクセスできないVimで作業することがよくあります。Xターミナル。
ジル「SO-悪であるのをやめる」2015

@Gillesそれでは、どのように貼り付けているのか説明していただけますか?それはあなたがやりたいことでそのアクションをラップできる答えを提供できるようにするための関連情報です。
ジェームスサン

1
私の基本的な使用例は、マウスの中ボタンまたはShift + Insertで貼り付けることです。しかし、それは実際には関係ありません:質問の核心は、オプションの設定方法、挿入モードへの切り替え(iこれをパラメータ化する方法を尋ねていません)、および挿入モードからの戻り時にオプションの値を復元する方法です。
ジル「SO-悪であるのをやめる」

1
@Gillesこのコメントで述べられているあなたの質問の核心は、あなたの元の質問よりもずっと明確です。ありがとう。
ジェームスサン

1
@Gillesこれはあなたには関係ありません、将来の訪問者に関係する可能性があります。したがって、質問自体に入力するか(「クリップボードを使用する"*p"+p、クリップボードから貼り付けることができますが、システムの貼り付け機能を使用したくない」)、この回答は不要です。または、あなたはしません、そして、私はこの答えがここに場所を持っていると思います。
yo

4

個人的には、まさにこの理由のためにyo、Tim Popeの優れたvim損なわれていないプラグインのキーバインドを使用しています。彼のドキュメントから:

単独挿入のラッピングの典型的なユースケースは非常に無駄であるため、「貼り付け」のトグルは提供されていません。2回切り替えますが、一度だけ貼り付けます(YOPO)。代わりに、yoまたはyOを押して起動する|o||O|、「貼り付け」がすでに設定されています。挿入モードを終了すると、「nopaste」が自動的に設定されます。

単にあなたの質問のためにプラグインをインストールするのはやり過ぎかもしれませんが、私はそれが他の便利なキーバインディングも豊富に提供していることを発見しました(詳細はREADMEをご覧ください)。


1

LinuxまたはMacのVim 8+では、ターミナルがブラケットペーストをサポートしている場合、ターミナルのネイティブペースト(Macのctrl+shift+VGnomeではマウスの中央ボタンなどcmd+V)を使用できます。i挿入モードでは押さないでください。

OSクリップボードの内容を貼り付け、自動インデントを追加せずにスペースとタブを保持します。それは古いと同等だ:set pasteictrl+shift+Vesc:set nopaste方法。

もうvim機能+clipboard+xterm_clipboardvim機能をインストールする必要はありません。この機能は「ブラケットペースト」と呼ばれます。詳細については、https://stackoverflow.com/questions/2514445/turning-off-auto-indent-when-pasting-text-into-vim/56781763#56781763を参照してください

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.