Zmień kształt kursora w trybie oczekiwania operatora

9

Mój kursor w Gvim:

Mój kursor w Gvim

Mój kursor w Gvimie po naciśnięciu d:

Mój kursor w Gvimie po naciśnięciu <code> d </code>

Czy jest jakiś sposób na zmianę kursora w terminalu Vim w trybie oczekiwania operatora? Nie musi wyglądać dokładnie jak zrzuty ekranu.

Odbywa się to o:hor50-Cursorw guicursorGvim. Jedyne trzy opcje, które widzę dla Vima to:

t_SI    start insert mode (bar cursor shape)        *t_SI* *'t_SI'*
t_SR    start replace mode (underline cursor shape) *t_SR* *'t_SR'*
t_EI    end insert or replace mode (block cursor shape) *t_EI* *'t_EI'*
    |termcap-cursor-shape|

Ale nic o trybie oczekiwania operatora ...

Martin Tournoij
źródło
2
Nie sądzę, że jest to możliwe (może użyć poprawki kodu źródłowego ..). To, co robię, to spojrzeć na prawą dolną stronę okna Vima, aby sprawdzić częściowo wprowadzone litery poleceń, które się tam pojawiają (z showcmdwłączonym ustawieniem). Wyłączam też wszystkie limity czasu i esckeysopcję (to sprawia, że ​​Vim jest niezadowolony, ale pozwala mi na przykład zastanowić się, co chcę zrobić w trybie oczekiwania).
VanLaser
1
@VLLaser Tak, ale lubię kursor ;-)
Martin Tournoij
Hehe, rozumiem to :)
VanLaser
Znam C / C ++, oferuję $ bounty i mogę spróbować zaimplementować go w kodzie źródłowym Vima, jeśli to możliwe: D
VanLaser
Możesz użyć vi.stackexchange.com/a/11437/10337, aby wykryć tryb oczekiwania operatora i wysłać echo, aby zmienić kursor.
laktak

Odpowiedzi:

3

To aktualizuje kursor podczas wchodzenia / wychodzenia z trybu oczekiwania operatora.

Chociaż jest to trochę hacky rozwiązanie, nie sądzę, aby miał problemy z wydajnością.

" This is esentially:
"   exec 'silent !printf "\e[" . a:t . ' q'
"   redraw!
" but without the screen flash
function! s:setCursor(t)
    " Save existing values.
    let [l:title, l:t_ts, l:t_fs, l:titlestring] = [&title, &t_ts, &t_fs, &titlestring]

    try
        let &titleold = ''
        let &t_ts = "\e[0;0"
        let &t_fs = "\e[" . a:t . ' q'
        set title
        set titlestring=H
        redraw!
    finally
        let [&title, &t_ts, &t_fs, &titlestring] = [l:title, l:t_ts, l:t_fs, l:titlestring]
    endtry
endfunction

let s:prevmode = ''
function! DetectPendingMode(timer)
    let l:mode = mode(1)
    if l:mode is# s:prevmode
        return
    endif

    if l:mode is# 'no'
        call <SID>setCursor(4)
    elseif s:prevmode is# 'no'
        call <SID>setCursor(2)
    endif
    let s:prevmode = l:mode
endfunction

call timer_start(250, 'DetectPendingMode', {'repeat': -1})

Być może trzeba zmienić styl kursora SetCursor()na preferowany:

0: blinking block.
1: blinking block.
2: steady block.
3: blinking underline.
4: steady underline.
5: blinking bar (xterm).
6: steady bar (xterm).
laktak
źródło