Установите параметр вставки, но только для одной вставки


16

Я хочу иметь быстрый способ установки 'paste'опции Vim , вставки некоторого текста и возврата к предыдущему значению 'paste'.

Типичный вариант использования вставляет содержимое буфера обмена ОС буквально, независимо от любого перезаписи режима вставки, которая может быть активной, такой как автоматическое отступление, и без изменения состояния Vim. Другой вариант использования - позволить макросу ОС вводить нажатия клавиш в Vim и интерпретировать их как текст.

Это очевидно обобщает другие параметры - общая идея состоит в том, чтобы установить некоторые параметры, но только на время одной поездки в режиме вставки.

В основном я хочу связать последовательность клавиш (скажем _i) с макросом, который делает это

:set paste
i…<Esc>
:set nopaste

где i…<Esc>я имею в виду переключение в режим вставки (как с iкомандой) и возобновление макроса при возврате в командный режим, за исключением того, что я хочу закончить все 'paste'еще активным, если он был активен заранее. Как я могу это сделать?

Примечание. Содержимое буфера обмена ОС сопоставляется с "*регистром . Когда это работает, 'paste'опция не очень полезна. Сценарий мотивации для этого вопроса относится к тем случаям, когда условия "*поддержки регистра не выполняются - Vim не скомпилирован с этой +xterm_clipboardфункцией или работает в терминале, таком как Screen, или поверх SSH, который изолирует его от окружающего X-сервера.


1
Мне нравится твой вопрос (я сам был там много раз). Однако не проще ли вставить +или *зарегистрировать?
лет»

@yo ' Только когда они работают . Что, для моего использования Vim, часто не так.
Жиль "ТАК ... перестать быть злым"

Ответы:


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 , который использует функцию режима вставки в скобках, предоставляемую несколькими эмуляторами терминала, чтобы определить, вставляете ли вы и устанавливаете режим автоматически.

Редактировать: исправил скрипт


Это кажется правильным путем (в частности, я понятия не имел, как «заключить» в скобки вставку с помощью обычных команд мира). Благодарю. Однако, это не совсем правильно, и я не вижу, в чем проблема: после _i, pasteопция отключена, даже если она была включена раньше.
Жиль "ТАК ... перестать быть злым"

Вы правы! Я почти уверен, что проверял это, но я, должно быть, кое-что изменил. Я обновил скрипт в посте, посмотрите, работает ли он сейчас у вас.
Чад

4

за исключением того, что я хочу закончить все 'paste'еще активным, если он был активен заранее.

'paste'должен быть активным в течение максимально короткого времени. Он отключает множество функций (включая карты), потому что его единственная цель - избежать неверного толкования вставляемого текста. Поэтому я считаю, что приведенное требование не должно быть обязательным.

Это, как говорится, на самом деле довольно легко вставить без необходимости установки 'paste'. Если вы используете gvim или используете +xterm_clipboardконсоль vim, вы можете просто использовать ее "+pдля вставки из буфера обмена ОС.

Проблема автоматического отступа при вставке действительно существует только в двух сценариях. Вставка содержимого регистра в режиме вставки ( <C-r>+) или вставка с помощью среднего щелчка мышью.

Вместо вставки содержимого регистра в режиме вставки вставка из регистра в обычном режиме позволит избежать проблемы переформатирования.

Если вы хотите вставить щелчок средней кнопкой мыши, затем используйте 'mouse'опцию, чтобы Vim вместо терминала обрабатывал среднюю кнопку. Затем Vim вставит содержимое буквально вместо того, чтобы интерпретировать входящий текст как набранный.


2
Ничто из этого не отвечает на мой вопрос. Я поставил в явные требования по причине! Обычно 'paste'он действительно не активен заранее, но я не хочу думать об этом. Я часто работаю в Vim, который не имеет доступа к буферу обмена X или мыши, либо потому, что моя сборка Vim не имеет этой xterm_clipboardфункции, либо потому, что я работаю, например, в сеансе Screen, который в данный момент подключен к Х терминал.
Жиль "ТАК - перестань быть злым"

@Gilles Тогда не могли бы вы объяснить, как вы вставляете? Это важная информация, чтобы иметь возможность дать ответ, который может связать это действие с тем, что вы хотите сделать.
Jamessan

1
Мой основной вариант использования - вставить с помощью средней кнопки мыши или Shift + Insert. Это не совсем актуально: суть вопроса в том, как установить параметр, переключиться в режим вставки (с помощью i, я не спрашиваю, как его параметризовать), и восстановить значение параметра по возвращении из режима вставки.
Жиль "ТАК - перестань быть злым"

1
@ Жиль Суть вашего вопроса, изложенная в этом комментарии, для меня гораздо понятнее, чем ваш первоначальный вопрос. Благодарю.
Jamessan

1
@Gilles Это не относится к вам , но может иметь отношение к будущим посетителям. Поэтому либо вы можете поставить его в самом вопросе («Я знаю, что могу использовать "*pили "+pвставить из буфера обмена, но я не хочу использовать возможности вставки системы»), и тогда этот ответ не нужен. Или нет, и тогда я думаю, что этот ответ имеет место здесь.
лет»

4

Лично я использую сочетание yoклавиш из превосходного Тима папы ВИМ-незатронутым плагин именно по этой причине. Из его документации:

Переключение не было предоставлено для «вставки», потому что типичный вариант использования обертывания одиночной вставки является настолько расточительным: вы переключаетесь дважды, но вставляете только один раз (YOPO). Вместо этого нажмите yoили yOдля вызова |o|или |O|с уже установленной «вставкой». Выход из режима вставки устанавливает 'nopaste' автоматически.

Возможно, было бы излишне устанавливать плагин просто по вашему вопросу, но я считаю, что он также предоставляет множество других полезных сочетаний клавиш (более подробную информацию см. В README ).


1

С Vim 8+ в Linux или Mac вы теперь можете просто использовать встроенную вставку терминала (например, среднюю кнопку мыши ctrl+shift+Vв Gnome cmd+Vна Mac), если терминал поддерживает вставку в скобках. Не нажимайте iдля режима вставки.

Он вставит содержимое буфера обмена вашей ОС, сохраняя пробелы и вкладки без добавления автоматического отступа. Это эквивалентно старому :set paste, i, ctrl+shift+V, esc, :set nopasteметод.

Вам даже не нужны функции +clipboardили +xterm_clipboardvim, установленные больше. Эта функция называется «вставка в скобках». Для получения дополнительной информации см. Https://stackoverflow.com/questions/2514445/turning-off-auto-indent-when-pasting-text-into-vim/56781763#56781763

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.