rcmdnk's blog

クリップボード オールドスクール(ペンコ)A4 DP110

NeoVimではOSのクリップボードとNeoVimのクリップボード(レジスタ)を共有する機能があります。

それをちょっといじって違う感じでも使えるという話。

NeoVimのclipboardオプション

NeoVimで.config/nvim/init.vim

set clipboard+=unnamedplus

とオプション設定しておくと、 yyとかでコピーするとOSのクリップボードにも追加され、 他のメモ帳とかでCtrl-VとするとNeoVimでコピーしたものがペーストできます。

逆に、メモ帳とかでCtrl-Cとして NeoVim上でpとすればメモ帳でコピーしたものがNeoVimでペーストできます。

これはコピーとかする際にxselpbcopyと言ったクリップボードを操作するコマンドを使って います。

NeoVimをインストールしたディレクトリ内のclipboard.vimを見ると何が使われてるかわかります。 MacでHomebrewでインストールしているなら

/usr/local/share/nvim/runtime/autoload/provider/clipboard.vim

これを見ると

  • g:clipboardが設定されていたらそれに従う
  • Macでpbpasteがあればpbcopy/pbpasteを使う
  • 環境変数WAYLAND_DISPLAYが設定されていてwl-copy/wl-pasteがあればそれを使う
  • 環境変数DISPLAYが設定されていてxclipがあればそれを使う
  • 環境変数DISPLAYが設定されていてxselがあればそれを使う
  • lemonadeコマンドが使えればそれを使う
  • doitclientコマンドが使えればそれを使う
  • win32yank.exeコマンドが使えればそれを使う
  • 環境変数TMUXが設定されていればtmuxを使う

と言った感じ。

lemonade/doitclientはsshでリモートサーバーでNeoVimを開いているとき、 手元のマシンのクリップボードとつなげるためのツールです。 dotclientはWindows用。 lemonadeはバーチャルマシン内で動かしているLinuxなどと共有するのを想定して作られているようです。

この辺の用意されてるものを見るのも興味深いですが、 最初にあるようにg:clipboardという変数を自分で設定することが出来ます。

NeoVimで:help clipboardとかしてみるとヘルプを見れますが、その中にtmuxを使う例として

let g:clipboard = {
      \   'name': 'myClipboard',
      \   'copy': {
      \      '+': 'tmux load-buffer -',
      \      '*': 'tmux load-buffer -',
      \    },
      \   'paste': {
      \      '+': 'tmux save-buffer -',
      \      '*': 'tmux save-buffer -',
      \ }

とあります。これでコピー時とペースト時に実行するコマンドを指定出来ます。 +とか*とかはレジスタ名でclipboard+=unnamedplusとしてるのでこの場合は+の方を使ってますが

これらのコマンドは標準入力を受け取ってそれを何らかのものへ入力するもの(copy)と 何かを標準出力するもの(paste)です。

pasteの方に

      \      '+': 'echo foo',

とか指定すると何をコピーしてもfooしか貼り付けられなくなります。

copyの方は

      \      '+': 'touch /tmp/copied',

とかするとコピーと同時に/tmp/copiedというファイルが出来ます。 この際はコピー自体は行われるのでファイルが作られる以外はそのままです。

というわけで、もしNeoVimとtmuxのクリップボードを共有したい場合、 LinuxなどMac/Windows以外でかつDISPLAY/WAYLAND_DISPLAYが設定されてない状態でかつ llemonadedotclientといったツールをインストールしてない場合には clipboardオプションを設定するだけで使えうようになります。

MacなどでOSのクリップボードではなくtmuxの方を使いたい場合には g:clipboardを指定します。

GNU screenのクリップボードとの共有

GNU screenのクリップボードはtmuxのように直接コマンドから操作できませんが、 bufferfileを通してクリイプボードの内容を操作することは出来ます。 bufferfileは何も指定してなければ/tmp/screen-exchangeになります。 もしくは

bufferfile "$HOME/screen-exchange"

とかして設定します。

コマンドラインから

$ screen -X writebuf

とするとbufferfileにクリップボードの内容が書き込まれ、 逆に

$ screen -X readbuf

とするとbufferfileに書かれた内容がクリップボードに読み込まれます。

これを使ってファイルの内容をxselとかpbcopyとか使ってOSのクリップボードに入れてやればOK。

一つのコマンドでやるのは大変ですがmulti_clipboard を使えば一発で出来ます。

これを使って

1
2
3
4
5
6
7
8
9
10
11
12
13
set clipboard+=unnamedplus
let g:clipboard = {
      \   'name': 'myClipboard',
      \   'copy': {
      \      '+': 'multi_clipboard -s',
      \      '*': 'multi_clipboard -s',
      \    },
      \   'paste': {
      \      '+': 'multi_clipboard -g',
      \      '*': 'multi_clipboard -g',
      \   },
      \   'cache_enabled': 1,
      \ }

のようにすればGNU screenとNeoVimのクリップボードが共有できます。

ただし、screenの仕様上(かmulti_clipboardのせい)最後の改行を削除するようになってるので NeoVimでライン単位でコピー(yyなど)したあと、ペースとしても ラインペーストにならずにその場所から挿入されてしまう状態になります。

というわけで、このままだとちょっと実用性にかけますが、 GNU screeに限らず、NeoVimでコピー、ペーストするときに何かしらのコマンドを実行できる、というのは 面白いな、と思ったのでメモしておきました。

Vimの場合

Vimの方でもclipboardオプションはありますが、 まず、

$ vim --version|grep clipboard
+clipboard         +jumplist          +persistent_undo   +vartabs
+eval              -mouse_gpm         +syntax            -xterm_clipboard

として+clipboardが含まれてる必要があります。

もし-clipboardとなっているとするとclipboardが有効になっていないので コンパイル時に 以下のいずれかのオプションを使ってconfigureしてコンパイルする必要があります。

  • --with-features=normal
  • --enable-gui
  • --with-x

xorg - Compiling vim with xterm_clipboard support - Super User

ただ、g:clipboardという変数はなくてこれを設定しても何も変わらないので 上に書いたような事はできません。

また、Yankroundなど、コピペの動作をいじるようなプラグインを入れている場合 コピー/ペースト自体がまともに動かなくなる可能性があります。

NeoVimではYankroundを有効にしたままclipboard設定が出来ましたが Vim(8.1, Mac)ではコピーが出来なくなりました。

まとめ

現状、ターミナルでの操作時に(Neo)VimのクリップボードとGNU screenのクリップボードとさらに OSのクリップボードそれぞれで分けて使うことでマルチクリップボード的な役割もしているので 逆に共有する必要はないかな、という使い方をしていますが、 ちょっと気になっているものだったので調べてみました。

NeoVimではコマンド以外にもlambda式も設定できるようです。 (何に使ってる人がいるのだろう…?)

なんでも設定できる感じなので何か面白いことも出来るかもしれません。

Sponsored Links
Sponsored Links

« GitHubで公開されてるipynbファイルをGoogle Colaboratoryで開くブックマークレット Chromeで多数のタブを開くときに本当によろしいですか?と聞かれなくする方法 »

}