Open osyo-manga opened 9 years ago
incsearch.vim では実装してるので必要だったらprします
お、お願いします!
ただvisualモードで起動されてるかvital-over側で検知するのめんどいかも...?
まぁ mode(1)
直接叩けばいいか
どうなんですかね。 そこら辺はなんかいい感じに(適当。
あーこれよく思い返してみれば実は2段階問題があります.
普通にヴィジュアルモードの選択を維持する場合は
<expr>
マッピングなどを用いてコマンド(:
)を経由しないようにするnormal! gv
するのいづれかの方法を取れば可能です. これが問題の1段階目で,これはあんまりモジュールでやる問題でもなさそう(ヴィジュアルモードから起動したかどうかは引数とったりヴィジュアル用の関数を作らないとわからないため.<expr>
じゃない場合は呼び出し先でmode(1)
つかっても無理)
しかしこれだけでは2段階目の問題が浮上し,これはヴィジュアル選択範囲のハイライトがmatchadd()
よりも必ず優先度が高いようなので,incsearch.vimやおそらくvim-overのハイライトがビジュアル選択ハイライトに負けます.
これをincsearch.vimではビジュアル選択ハイライトを一旦消して自前でハイライトすることで対応しており,モジュール化するとしたらおそらくこちらの方だと思いますがそういう認識でいいでしょうか? Retain highlight in visual mode
という要望を応えるだけならnormal! gv
でできる(vim-overがそれでエンバグする可能性はわからないですが).
あとかなり気軽にPRしましょうかと言ってしまいましたが,mode
を引数として取らないと対応できない(かも)なので,vital-overのenter
/leave
イベントあたりで対応するの意外とダルそうだということに気づいた...
ふーむ、なるほど。
Retain highlight in visual mode という要望を応えるだけならnormal! gvでできる(vim-overがそれでエンバグする可能性はわからないですが).
確かにそれが一番手っ取り早そうな気がするんですが、set showmode=1
の時に normal! gv
すると vital-over の出力が崩れてしまいますね。
あとカーソルのハイライトもおかしくなります。
これは incsearch.vim でも同様に再現します。 vital-over 側で対応するのがよいかなぁ…。
うーん、ここら辺も含めてモジュール化してしまってもよさそうな気はします。
確かにそれが一番手っ取り早そうな気がするんですが、set showmode=1 の時に normal! gv すると vital-over の出力が崩れてしまいますね。 あとカーソルのハイライトもおかしくなります。
これ再現しない...と思ったらgvimで起動したら再現しました.
あと正確には set showmode
ですかね?
関係ないけどgvimかつヴィジュアルモードから起動したらめっちゃ遅いな...ターミナルだと普通の速度なのに
カーソルのハイライトがおかしくなる問題は :set noshowmode
でも再現しそう
カーソルのハイライトがおかしくなる問題は :set noshowmode でも再現しそう
ですね。
showmode
とカーソルハイライトが残ったままになる2つの問題があるみたいです。
とりあえず、normal! gv
だと問題あるみたいなんで、matchadd()
を使った版を実装してみました。
call vital#of("vital").unload()
let s:V = vital#of("vital")
let s:Highlight = s:V.import("Coaster.Highlight")
let s:cmdline = s:V.import("Over.Commandline").make_standard("> ")
let s:module = {
\ "name" : "HighlightVisualMode"
\}
function! s:module.__valid__()
return 0
endfunction
function! s:module.on_enter(cmdline)
if !self.__valid__(a:cmdline)
return
endif
if &selection == "exclusive"
let pat = '\%''<\|\%>''<.*\%<''>'
else
let pat = '\%''<\|\%>''<.*\%<''>\|\%''>'
endif
call s:Highlight.highlight("visualmode", "Visual", pat)
endfunction
function! s:module.on_leave(...)
call s:Highlight.clear("visualmode")
endfunction
let s:hl_vmode = deepcopy(s:module)
" ユーザ側でハイライトする条件を定義
function! s:hl_vmode.__valid__(cmdline)
return a:cmdline._visualmode
endfunction
call s:cmdline.connect(s:hl_vmode)
function! Test() range
" 複数行選択されていた場合、visual mode にする
" NOTE: 1行のみ選択されていた場合は有効にならない
let s:cmdline._visualmode = (a:firstline != a:lastline)
call s:cmdline.start()
endfunction
vnoremap <A-c> :call Test()<CR>
nnoremap <A-c> :call Test()<CR>
visual mode かどうかを判定するのはユーザ側で決定できるように実装しました。
いまは range の値で判定していますが、<expr>
時に mode()
の値を渡してごにょごにょというような判定もできます。
暫定的な問題点として矩形選択した場合にちゃんとハイライトされないというのがあります。
余計なコード混ざってたので修正
関連 : https://github.com/osyo-manga/vim-over/issues/41
Modules で実装したほうがよいかと思いこっちに立てました。