Отключение автоматического отступа при вставке текста в vim


1186

Я прилагаю усилия, чтобы изучить Vim.

Когда я вставляю код в свой документ из буфера обмена, я получаю дополнительные пробелы в начале каждой новой строки:

line
  line
    line

Я знаю, что вы можете отключить автоматический отступ, но я не могу заставить его работать, потому что у меня есть другие параметры, конфликтующие или что-то в этом роде (что выглядит довольно очевидно в моем .vimrc, но, кажется, не имеет значения, когда я их вынимаю).

Как отключить автоматический отступ, когда я вставляю код, но при написании кода все еще есть vim auto Indent? Вот мой .vimrcфайл:

set expandtab  
set tabstop=2  
set shiftwidth=2  
set autoindent  
set smartindent  
set bg=dark  
set nowrap  

4
В FWIW, vim 8.0.210 добавлена ​​встроенная поддержка вставки в скобках, чтобы избежать вставки вставленного текста.
— sh1

Для новых файлов, чтобы избежать путаницы с vim's paste / nopaste, вы можете cat > mynewfile.txtнажать Enter , вставить свой текст, снова нажать Enter , а затем Ctr + D, чтобы сохранить. Файл теперь создан, и вы можете редактировать его vim mynewfile.txt.
— ccpizza

Ответы:


2068

Обновление: лучше ответ здесь: https://stackoverflow.com/a/38258720/62202

Чтобы отключить автоиндентирование при вставке кода, есть специальный режим «вставки».

Тип

:set paste

Затем вставьте свой код. Обратите внимание, что текст во всплывающей подсказке теперь говорит -- INSERT (paste) --.

После того, как вы вставили свой код, выключите режим вставки, чтобы автоматический ввод отступа при вводе снова работал правильно.

:set nopaste

Тем не менее, я всегда находил это громоздким. Вот почему я отображаю так <F3>, что он может переключаться между режимами вставки и nopaste при редактировании текста! Я добавляю это к.vimrc

set pastetoggle=<F3>

38
Это не легче, чем :set noaiследуют :set ai. Предложение :r! catкороче.
— Леопд

69
Я думаю, что set pasteпроще, определенно. Это гораздо более семантически, чем noaiили даже noautoindent, что более важно, когда ввод «noai» и «paste» занимает примерно одинаковое количество времени, когда вы достаточно опытны в качестве машинистки на ощупь.
— Виктор Заманян

52
:set noaiне всегда работает, в зависимости от того, как настроены другие параметры, связанные с отступом, согласно OP. :set pasteкажется сокращением для нескольких настроек одновременно.
— MarkHu

13
Поздно на вечеринку, но set copyindentпозаботимся об этом для вас без проблем.
— Мэтт Райан

33
:set pasteтакже отключает другие функции, такие как завершение фигурных скобок, что также не требуется при вставке кода.
— Мануэль Фо

263

Чтобы избежать нежелательных эффектов при вставке, есть параметр, который необходимо установить:

set paste

Полезная команда, которая должна быть в вашем .vimrc - это set pastetoggle=<F10>или другая кнопка, чтобы легко переключаться между вставкой и nopaste.


13
В заключение! Я продолжал печатать: set paste /: set nopaste, как глупо! Спасибо.
— imwilsonxu

4
с практической точки зрения ваш ответ более полезен, чем принятый ответ
— Lynob

8
Другой вариант - добавить макрос в ваш vimrc:nmap <silent> <leader>p :set paste<CR>"*p:set nopaste<CR>
— Крис

Хорошее предложение @Chris - единственная последовательность клавиш для вставки без проблем с отступами!
— RichVel

Что делать, если я никогда не хочу быть в режиме вставки? Есть ли способ навсегда отключить?
— Максвелл

132

Я обычно использую, :r! catа затем вставляю ( shift + insert )содержимое, и CTRL+D.

Нет необходимости включать и отключать, прямое использование.


Мне нравится этот вариант прямого использования. Я все еще учусь читать синтаксис vim на веб-страницах. Что означают ваши шаги? В частности, если у меня есть что-то в системном буфере обмена, что я нажимаю, чтобы вставить это в документ в vim?
— jvriesem

9
Этот ответ будет более полезен с информацией о том, почему и как :r! catработает.
— К Эрландссон

11
@KErlandsson, :rвставляет содержимое файла в текущий документ. !catговорит, что запустить cat, которая по существу открывает stdin (* nix shells) (shift + insert)или для некоторых терминалов, щелчок правой кнопкой мыши вставит содержимое буфера обмена в CTRL+Dконец файла, поэтому он закроет :r !catсеанс.
— Даниил

Это «прямое», правда? Чем настройка pasteсделана исключительно для этой цели? @jvriesem Это не «прямой» вариант, если я правильно понимаю, что вы понимаете это слово.
— 0xc0de

Вы также можете использовать :r! catзатем, CTRL+SHIFT+Vчтобы вставить в терминал (затем CTRL+D).
— Поль Ружье

86

Если вы работаете локально, вы можете вставить из системного буфера обмена последовательность клавиш:

"+p

Это правильная команда vim, поэтому не нужно беспокоиться о входе в режим вставки или об отключении автоматического отступа.

Конечно, если вы работаете удаленно (например, через консоль через SSH), это не сработает, и вы должны перейти в :set noaiрежим вставки, вставить в консоль, оставить режим вставки, выполнить :set aiмаршрутизацию, как описано в другом месте.


10
Я пишу этот ответ давным-давно. В настоящее время я использую :set pasteи :set nopasteвместо этого, потому что, несмотря на то, что он длиннее, его легче запомнить, и мне не нужно искать его каждый раз!
— Томасруттер

6
В некоторых встроенных системах (в основном на основе busybox) :set pasteэто не реализовано, поэтому :set noaiследует использовать вместо этого.
— jcarballo

Если у вас есть большой текст для копирования, не быстрее ли использовать вместо него регистр +?
— pedromanoel

1
@pedromanoel, который работает только при локальной работе. Например, доступ к vim через SSH не будет работать, если вы скопировали что-то локально и хотите вставить его в vim, который находится в вашем сеансе SSH.
— Томасруттер

1
@thomasrutter, но я сопоставил это с <leader>p... очень полезно!
— датчанин

51

Хотя установка режима вставки с помощью paste/nopaste/pastetoggleотлично подходит, вам все равно придется вручную включить режим вставки перед вставкой и отключить режим вставки после вставки. Будучи ленивым человеком, я - лучшее решение, которое я нашел на данный момент, которое автоматически включает режим вставки при вставке.

Вот небольшой трюк, который использует режим вставки в скобках терминала для автоматической установки / отмены режима вставки Vim при вставке. Поместите следующее в ваш .vimrc:

let &t_SI .= "\<Esc>[?2004h"
let &t_EI .= "\<Esc>[?2004l"

inoremap <special> <expr> <Esc>[200~ XTermPasteBegin()

function! XTermPasteBegin()
  set pastetoggle=<Esc>[201~
  set paste
  return ""
endfunction

Теперь вы можете вставлять без явного включения / выключения режима вставки - он обрабатывается автоматически для вас.

Источник: Coderwall

Замечания: Это решение не работает в WSL (подсистема Windows 10 для Linux). Если у кого-то есть решение для WSL, пожалуйста, обновите этот ответ или добавьте его в комментариях.

Tmux При использовании tmux, объявления должны быть дважды экранированы. Код для этого также в Coderwall


Это великолепно. Хотя одна вещь ... С каждой пастой я получаю нулевой (нулевой) символ в начале каждой пасты. Любой совет для этого?
— Юлиус Ш.

Также обратите внимание на то, что если вы используете tmux, вам нужно выполнить двойной escape. Код для этого находится в ссылке Coderwall в ответе
— Daithí

1
Если вы еще ленивее и копируете вставленный выше код в свой .vimrc, позаботьтесь о отступе функции XTermPasteBegin ().
— k1133

Мне было интересно , как это работает, и поэтому я искал Paste Брекетинга и нашел gitlab.com/gnachman/iterm2/-/wikis/Paste-Bracketing , который объясняет , что t_SIи t_EIпеременные позволяет вставить в скобках и отключить его. Когда брекетинг вставки включен, перед вставляемым текстом ставится префикс esc[200~и после него esc[201~.
— PatS

37

Пользователи Mac могут избежать автоматического форматирования, читая непосредственно с монтажной панели с помощью:

:r !pbpaste

3
Это потрясающий ответ. Однако, когда я делаю это, он скрывает документ (похоже, я вернулся в командную строку), но в моем буфере обмена есть текст. Он побуждает меня нажать Enter, поэтому я возвращаюсь к моему документу без каких-либо изменений. Что случилось, и как мне сделать то, что вы говорите?
— jvriesem

Если вы просто печатаете :.!pbpaste, это должно работать, заменяя текущую строку выводом буфера вставки. В общем случае vim позволяет передавать данные из вашего текущего файла в другую программу и заменять текст выводом команды. Таким образом, :1,3!pbpasteпервые три строки вашего файла заменяются буфером вставки. Я использую :.!ppjsonочень длинную (неформатированную строку JSON), форматирую ее и заменяю длинную строку форматированным эквивалентом. ppjson - это просто скрипт bash, который запускается python -m json.tool.
— PatS

19

Вот сообщение того, кто выяснил, как переназначить событие вставки, чтобы автоматически включить режим вставки и затем снова выключить. У меня работает в tmux / iTerm на MacOSX.


1
Спасибо за совет. Я также выследил плагин, в котором человек связал похожую функциональность - stackoverflow.com/a/36512548/255961 .
— Studgeek

Кажется, это вызывает строку 'eeeeeee', когда я вставляю фрагмент текста из буфера обмена.
— Джон Цзян

16

Добавьте это к вашему, ~/.vimrcи вам нужно будет только нажать F2 до и после вставки:

set pastetoggle=<F2>

12

Я просто вставил set clipboard=unnamedсвой .vimrc. Это делает карту буфера вставки по умолчанию в буфер обмена X.

Поэтому, если я отмечу немного текста в терминале, я могу просто нажать, pчтобы вставить его в vim. Точно так же я могу дергать вещи в Vim (например,YY чтобы вставить текущую строку в буфер) и щелкнуть средней кнопкой мыши в любом окне, чтобы вставить его.

Не знаю. Я нахожу это супер удобным.


ИМХО, это лучший ответ, нет необходимости переключаться с F11 (который предварительно настроен в vim по умолчанию). Это работает в системе Mac OSX, я не знаю, о других.
— LightMan

9

При работе внутри терминала vim-bracketed-paste плагин vim будет автоматически обрабатывать без необходимости нажатия клавиш до или после вставки.

Он работает путем обнаружения режима вставки в скобках, который представляет собой escape-последовательность, отправляемую «современными» терминалами, совместимыми с x-term, такими как iTerm2, gnome-терминал и другие терминалы, использующие libvte. В качестве дополнительного бонуса он работает также для сеансов tmux. Я успешно использую его с iTerm2 на Mac, подключаясь к серверу Linux и используя tmux.


Остерегайтесь того, что он также отмечает далее: к сожалению, это означает, что они также будут запускать содержимое буфера ввода, если во всем, что вы вставляете в терминал, есть новая строка.
— 0xc0de

1
@ 0xc0de, эта цитата здесь не актуальна. Это говорит о том, что будет делать оболочка , когда она не поддерживает режим вставки в скобках. В этом и заключается смысл вставки в скобках - чтобы это не происходило.
— sh1

Это работало намного лучше для меня, чем другие решения. Спасибо.
— JJJ

8

Вставьте это в ваш ~ / .vimrc и будьте счастливы:

" enables :Paste to just do what you want
command Paste execute 'set noai | insert | set ai'

Изменить: при отражении, :r !catэто гораздо лучший подход, так как он короткий, семантический и не требует никакого пользовательского vimrc. Используйте это вместо этого!


5

Хотя :pastetoggleили :pasteи :nopasteдолжно работать нормально (если реализовано - они не всегда, как мы видим из обсуждения), я настоятельно рекомендую вставлять с использованием прямого подхода "+pили "*pи читать с "+rили"*r :

Vim имеет доступ к десяти типам регистров ( :help registers), а спрашивающий интересуется quotestarи quoteplusиз раздела

  1. Выбор и удаление регистров "*, "+и "~

Используйте эти регистры для хранения и извлечения выбранного текста для графического интерфейса. Увидеть quotestarиquoteplus . Когда буфер обмена недоступен или не работает, вместо него используется безымянный регистр. Для систем Unix буфер обмена доступен только при наличии функции + xterm_clipboard. {не в Vi}

Обратите внимание, что существует только различие между "* и" + для систем X11.

:help x11-selectionдалее разъясняет разницу *и +:

                                                  quoteplus quote+

Существует три документированных выбора X: PRIMARY (который, как ожидается, будет представлять текущий визуальный выбор - как в визуальном режиме Vim), SECONDARY (который не определен) и CLIPBOARD (который, как ожидается, будет использоваться для операций вырезания, копирования и вставки ).

Из этих трех Vim использует PRIMARY при чтении и записи в регистр "* (следовательно, когда выбор X11 доступен, Vim устанавливает значение по умолчанию для буфера обмена" autoselect ") и CLIPBOARD при чтении и записи в регистр" + ". Vim не имеет доступа к ВТОРИЧНОМУ выбору.

Примеры: (при условии значения параметра по умолчанию)

  • Выберите URL в визуальном режиме в Vim. Перейдите в браузер и нажмите среднюю кнопку мыши в текстовом поле URL. Выбранный текст будет вставлен (надеюсь!). Примечание: в Firefox вы можете установить для параметра middlemouse.contentLoadURL значение true в about: config, тогда выбранный URL-адрес будет использоваться при нажатии средней кнопки мыши в большинстве мест окна.

  • Выделите текст в браузере, перетаскивая его мышью. Перейти к Vim и нажмите среднюю кнопку мыши: выделенный текст вставлен.

  • Выделите некоторый текст в Vim и выполните «+ y. Перейдите в браузер, выделите текст в текстовом поле, перетаскивая его мышью. Теперь используйте правую кнопку мыши и выберите« Вставить »во всплывающем меню. Выбранный текст перезаписывается текст из Vim. Обратите внимание, что текст в регистре "+" остается доступным при создании визуального выделения, что делает доступным другой текст в регистре "*. Это позволяет перезаписывать выделенный текст.

я заметил, что использование среднего клика в vim не
— портит

4

Это работает для меня (случай + регистр, что я использую как буфер обмена между aps):

imap <silent> <S-Insert> <C-O>:set noai<CR><C-R>+<C-O>:set ai<CR>

2

Если вы работаете на Mac, Macvim, кажется, справится с этим без необходимости переключения пасты.

brew install macvim --override-system-vim


Это тот случай, если вы включите директивы ОП в свой .vimrcфайл?
— Дрю Ноакс


1

Самый быстрый способ, которым я знаю, чтобы быстро перейти в режим вставки-вставки для вставки одним выстрелом, - это незатронутая tpope , которая имеет yoи yO, по-видимому, мнемонику для «вы открываете». Они только зарегистрированы в его vimdoc, как:

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


1

Другой способ вставки - через <CR>и сброс содержимого регистра (здесь глобальный регистр). Смотрите: :h i_ctrl-rиh i_CTRL-R_CTRL-O .

Из справочной документации vim:
Insert the contents of a register literally and don't auto-indent. Does the same as pasting with the mouse<MiddleMouse>. Does not replace characters! The '.' register (last inserted text) is still inserted as typed.{not in Vi}

Чтобы вставить содержимое в vim без автоматического отступа, используйте <CR><CO>* в большинстве систем Unix.

Примечание: это работает, только если vim скомпилирован clipboard.



1

Другого ответа я не видел до сих пор:

:se paste noai

1

Нативная паста / паста в скобках - лучший и самый простой способ с тех пор vim 8(выпущен в 2016 году). Это даже работает над SSH! (Вставка в скобках работает на Linux и Mac, но не на Windows Git Bash)

  1. Убедитесь, что у вас vim 8+ (вам не нужны опции +clipboardили +xterm_clipboard).

    vim --version | head -1

  2. Просто используйте собственную команду вставки ОС (например, ctrl+shift+Vили cmd+V) в обычном режиме. Не нажимайте iдля режима вставки.


Тестовое задание

  1. Скопируйте ( ctrl+shift+Cили cmd+C) вывод этого (2 строки с отступом табуляции) в системный буфер обмена:

    echo -e '\ta\n\tb'

  2. Запустите чистый vim 8+ с autoindent:

    vim -u NONE --noplugin -c 'set autoindent'

  3. Вставить из системного буфера обмена ( ctrl+shift+Vили cmd+V) в обычном режиме. Не нажимайте iдля режима вставки. Символ aи bдолжен быть выровнен с отступом одной вкладки. Вы даже можете сделать это при подключении по ssh к удаленному компьютеру (удаленному компьютеру потребуется vim 8+).

  4. Теперь попробуйте старый способ, при котором вторая строка будет автоматически вставлена ​​с дополнительной вкладкой: нажмите iдля режима вставки. Затем вставьте с помощью ctrl+shift+Vили cmd+V. aИ bразрегулированы в настоящее время.


Установка Vim 8


1
лучший и самый простой способ! Кроме того, Google предложил это Featured snippetдля моего поиска «вставить контент без вкладок vim», может быть потому, что я использовал ключевое слово «вкладка», только в этом ответе упоминалось :)
— Дэвид

0

К сожалению, я обнаружил, что упомянутый плагин vim не работает с iTerm2 3.0.15 (честно говоря, я не знаю, сломался ли он на старых версиях) - но вместо этого я нашел этот хак.

Сопоставьте команду p для вставки и использования ключей ver iTerm2. Очевидно, это работает только для iTerm2.

Как это работает. Я использую "JK", чтобы войти в режим побега, поэтому вам также понадобится:

: inoremap jk

в вашем .vimrc.

Затем он просто вызывает P, чтобы войти в режим вставки, "+ p, чтобы вставить из буфера обмена, а затем P, чтобы отключить режим вставки. Hth.

введите описание изображения здесь


1
Подождите, что, вы используете 'JK' для этого?
— 0xc0de

О да, я забыл упомянуть об этом. Просто добавьте ": inoremap jk <esc>" в ваш .vimrc. Что касается того, почему я использую jk, спросите Apple, и почему они почувствовали необходимость переместиться и избавиться от физического управляющего ключа. 8 (
— Нил Макгилл,

Кстати, это требует некоторой тренировки, но через некоторое время jk чувствует себя быстрее, и я думаю, что я предпочитаю это сейчас вместо побега ... В любом случае было бы интересно узнать, принимает ли iTerm2 и здесь <ESC>.
— Нил МакГилл

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