Is it possible to object-select a heredoc or “here document” with vim?
-
23-09-2019 - |
Question
One of Vim's great strengths is object-select, offering quick manipulation of content inside words, paragraphs and assorted delimiters.
For example,
vi{
will select everything inside a pair of {} braces.
Is there any equivalent functionality for selecting a here document or heredoc:
<<<HTML
....
....
HTML;
Based on ErichBSchulz's answer I came up with the following for an heredoc inner select:
nmap <F6> ?<<<<CR>w*kV?<<<<CR>j
?<<<<CR>w " find beginning tag (after <<<)
*k " find matching end tag and go up 1 line
V " enter visual mode
?<<<<CR>j " find beginning tag and go down 1 line
Solution
Thinking about the earlier posts and trying to take them a step closer. This wont be 100% reliable (ie will break if the starting tag occurs within the heredoc but something like:
?<<< "find begining
w " go to starting tag
* " find starting tag
v " enter visual mode (could use Upper V to do an 'ambientish' object select
n " find end tag
e " optional include end tag
Edit: Ken has improved the sequence as above, so I suggest you use his better key mapping for an 'inner' heredoc select:
nmap <F6> ?<<<<CR>w*kV?<<<<CR>j
(this is based on php style heredocs)
OTHER TIPS
For selecting heredoc's I usually place the cursor at the first line, over the heredoc identifier and press V*
V will start a line selection, and * will start a search, going to the next match of the identifier, the end of the heredoc...
A <<''
heredoc terminated by an empty line is easy, if you're already at the start (?<<^M^M
): v}
selects from here until the empty line.
Otherwise, in your example the best I can think of is v/^HTML
.
There's this plugin that let's you define your own text objects.
http://www.vim.org/scripts/script.php?script_id=2100
I imagine it would be nice to define one so you could say 'yih' (yank in heredoc) so you don't have to explicitly go to the start.
Note I haven't fooled around with this myself.
If you just want a visual select you could.
nnoremap <leader>ih ?HTML<cr>V/HTML<cr>