Hacker Newsnew | past | comments | ask | show | jobs | submitlogin
Vim Text Objects : The Definitive Guide (carbonfive.com)
198 points by rudyjahchan on Oct 17, 2011 | hide | past | favorite | 41 comments


Vim's text objects are one of the fundamental things that make using it so awesome.

I've had a bit of code in my vimrc that creates "next/previous" text objects for a while. Someone came along and helped me make it more compact a while ago, but I can't remember who.

It lets you use "din(" for "delete in next parens (on the current line)", which saves a bit of typing.

https://bitbucket.org/sjl/dotfiles/src/1b6ffba66e9f/vim/.vim...

Maybe I should turn it into a pathogen-installable plugin one of these days.


Ah, I've loved this for ever! I didn't know other people did that too. :)

    noremap H ^
    noremap L $
Stealing your K-kill idea too!


You don't find the default H/M/L that useful?

To be honest I never really got around using them but it might a nice addition to my vim usage.


Wow. That's a huge vimrc config (1350 lines!) filled with gems, I am going to go through it and steal them for my vimrc! :)


Not clear what this does:

    " Stop it, hash key.
    inoremap # X<BS>#
I tried it too. It's in insert mode, so it types an X, backspaces and then types a '#'.


I've got something similar in mine; The use-case is to allow indented comments (in languages where '#' is the comment delimiter)

Normally, when using auto-indent/smart-indent, pressing '#' on a blank line will change the column to zero, deleting any existing whitespace. By typing a character and deleting it, you override this behavior, allowing you to have comments at the same indentation level as the rest of the code.


Steve You have a line regarding setting "fuoptions". That only works in mac_vim, so you need to put that in a condition.


Could it be modified to just use di( or dib etc, and still not break anything essential?


A couple of text object related plugins also worth checking out:

Easymotion - https://github.com/Lokaltog/vim-easymotion

Surround - https://github.com/tpope/vim-surround


For those of us hacking in languages with significant whitespace, I made a simple plugin for treating indent levels as text objects.

It's not nearly as cool as Easymotion or Surround, but here it is if you're interested:

https://github.com/esk/aye-aye


Thanks for this :) It's going to be really useful


Thanks for that - this is the first time I've come across easymotion and I can already tell it's going to be used heavily. Great plugin. Highly recommended to anyone not familiar with it.


Don't forget Vim's built-in help and user manual:

    :h text-objects
    :h usr_04


Related, and more generally:

    :help object<CTRL-D>
    objects                 text-objects            vimwiki-text-objects
    object-select           sql-object-motions      sql-predefined-objects
    object-motions          text-objects-changed    +textobjects
    :help object
shows all help subjects with "object" in their name.

Then change the help query to whichever subject looks interesting.


question about text objects:

given the following string and with the cursor over f:

     function(1,2,"3")
why does di" yield:

     function(1,2,"")
but di( has no effect unless you are within the parenthesis already?

Why doesn't di( when issued over the f in function yield the following?

     function()


It looks like the 'i(' motion has special meaning in Vim - it corresponds to the previous unmatched '(' to the next matched ')'. Type 'help motion.txt' and look for i(.

Edit: Actually, the description for i" implies that its behaviour should be the same. Which one works correctly, I wonder?


Since brackets come in matchable pairs and double quotes do not, and because brackets can be nested while double quotes cannot, it wouldn't surprise me if this were a deliberate difference. If the user hits "di(" on a line and there's no "(" before the cursor, you can search backwards over previous lines looking for an unmatched "(" without too much worry you'll get confused by a stray "(" and delete something the user didn't expect. If the user hits 'di"' on a line and there's no '"' before the cursor, searching any further is quite likely to hit a false positive and do something ridiculous (like deleting all the code between two string literals).


That's a fair interpretation. I'd be more comfortable if this difference were reflected in the documentation - it could at least state that if no previous quote is found, the next quote on the line will be used.


Something related but not mentioned in the article is that lines are the standard object in vim (and vi). The syntax is not the same, but the concept is fully supported. For example, change the whole line = cc. Delete the whole line = dd.


I've been using vim for just a few months and this article is a revelation to me.


The revelations never stop. :)


inner words were the turning point for me with vim. The first time I did ci" I knew I had found a lifelong partner :)


Text objects along with movement by search were the two things that propelled my editing capabilities with Vim the most so far.


This stuff is nuts. I really need to get deeper in to vim.


Eclipse lets you expand your selection to ever increasing expressions in Java and back again (Shift-Alt-Up/Down). Press up often enough, and you end up selecting the entire outer class, and after that the entire file. Press down and you get back right where you started.

It's super useful, particularly for understanding and refactoring old code. In fact it makes refactoring very enjoyable, almost game like. It seems as if that Eclipse feature is a pale shadow of vim text objects.


I really wish there was "ac"/"ic" (or something) for comments. Especially for a gq motion it would be really helpful.


Are there such equivalents for emacs? What's the best one out there?


I've been learning emacs and hunting for the same thing. Aside from Viper mode, these two manual pages are the best I've found:

http://www.gnu.org/s/libtool/manual/emacs/Expressions.html

http://www.gnu.org/software/libtool/manual/emacs/Moving-by-P...

It has helped, but I'm still wishing there were more equivalents. This just seems to scratch the surface of what Vim can do in this area. If you find anything else that is helpful for this sort of editing task, please post it here...


Do not use viper mode. Use evil, a much better emulation layer from the authors of vim-mode and vimpulse. I also recommend evil-surround.


Oh, that looks really interesting. It looks like it didn't exist last time I was looking.


I don't understand. Emacs blows vim away here. Of course, obviously both emacs and vim users are unaware of these symbolic modes. But Emacs modes are designed to have this idea of customizing the word, sentence, paragraph, and symbolic expression per language/syntax. And using the mark and region and operating on them with commands is exactly what's described in this vim article. That said, I didn't know that vim could do these things, either, because the default vim objects are lines, which are hideously crude and turned me off.


I'm not an emacs guru, but it feels especially sad to see that emacs grammar/syntax aware (emacs does a lot in this department) structures aren't used to provide this kind of operations by default (of course with some elisp-fu it's doable). The combinator orientation of vim commands is just plain cute.


Putting the article's content aside, how many "beginner's guides" to Vim do we really need? It seems like every other week I find a new author writing about basic vim commands. Now, considering the article's content-- I'm not sure it contained anything that couldn't be learned from `vimtutor`, but it's been quite a while since I've run it.


Pretty much nothing from this article is in vimtutor, as I learned using that and don't recognize any of these commands. It teaches cw, dw, things like that, but it doesn't go into depth like this article.


You're right. I mistook vimtutor for the first chapter of a Vim book I have, although I did make a point to indicate that I wasn't 100% sure in the OP.


I've been using vi for 15+ years and full-time for development for about a year. There were at least 3 of these that I wasn't aware of which I will now commit to memory.

Certainly a beginner could learn this stuff right away, but I wouldn't consider it inherently beginner-oriented. Personally I don't think one canonical tutorial or reference is as effective as a large number of articles focused on things that different individuals find useful. Vim is just too big to absorb through one gargantuan tutorial.


I'm not the author.

My guess is that it's a combination of a) a lot of people are learning Vim right now and b) a lot of these people have blogs.

Coming to Vim from some other editor is an awesome experience for them and they want to share.

I know: I've been using Vim daily since one year now (coming from TextMate) and I've posted 20+ random tricks as I learned them. I'm currently drafting my "one year with Vim" post.


If one person (even the author) learns one thing from any of those beginners guides, then it was worth it.


So if I rewrite an existing program from scratch and it takes 10x longer than just using the existing one, but one person uses the program, it's still worth the time?

I think that one person could have found the information from an existing source, such as _:help text-objects_. That isn't to say that the article is useless; it's just redundant.


The post covers material outside of Vim's help system (e.g. some Vim scripts that create new text objects), and provides a different presentation that might be helpful to someone learning the concept. I think that's valuable.


What's wrong with different ways of explaining the same lessons? What if you don't know what text-objects are in the first place?




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: