# HG changeset patch # User Steve Losh # Date 1318047099 14400 # Node ID fd0f7560abf1261dee1c293120110b68373bb8cb # Parent 6837a9468ab71d28164169d46efdf4ad23516e26 Maplocal diff -r 6837a9468ab7 -r fd0f7560abf1 chapters/11.markdown --- a/chapters/11.markdown Fri Oct 07 23:36:49 2011 -0400 +++ b/chapters/11.markdown Sat Oct 08 00:11:39 2011 -0400 @@ -1,133 +1,107 @@ -Autocommands -============ - -Now we're going to look at a topic almost as important as mappings: -autocommands. +Buffer-Local Options and Mappings +================================= -Autocommands are a way to tell Vim to run certain commands whenever certain -events happen. Let's dive right into an example. +Now we're going to take a few minutes to revisit three things we've already +talked about: mappings, abbreviations and options, but with a twist: we're going +to set each of them in a single buffer at a time. -First, open a new file with `:edit foo` and close it right away with `:quit`. -Look on your hard drive and you'll notice that the file is not there. This is -because Vim doesn't actually *create* the file until you save it for the first -time. +The true power of this idea will become apparent in the next chapter, but we +need to lay the groundwork for it now. -Let's change it so that Vim creates files as soon as you edit them. Run the -following command: - - :autocmd BufNewFile * :write +For this chapter you'll need to open two files in Vim, each in its own split. +We'll call them `foo` and `bar`, but you can name them whatever you like. Put +some text into each of them. -This is a lot to take it, but try it out and see that it works. Run `:edit foo` -again, close it with `:quit`, and look at your hard drive. This time the file -will be there (and empty, of course). +Mappings +-------- -You'll have to close Vim to remove the autocommand. We'll talk about how to -avoid this in a later chapter. +Switch to file `foo` and run the following commands: -Autocommand Structure ---------------------- + :nnoremap d dd + :nnoremap x dd -Let's take a closer look at the autocommand we just created: +Now stay in file `foo`, make sure you're in normal mode, and type `d`. +Vim will delete a line. This is nothing new to us. + +Still in file `foo`, type `x`. Vim will delete a line again. This +makes sense because we mapped `x` to `dd` as well. - :autocmd BufNewFile * :write - ^ ^ ^ - | | | - | | The command to run. - | | - | A "pattern" to filter the event. - | - The "event" to watch for. +Now move over to file `bar`. While in normal mode, type `d`. Again, +Vim deletes the current line. Nothing surprising here either. -The first piece of the command is the type of event we want to watch for. Vim -offers *many* events to watch. Some of them include: +Now for the twist: while still in file `bar` type `x`. + +Nothing happened! -* Starting to edit a file that doesn't already exist. -* Reading a file, whether it exists or not. -* Switching a buffer's `filetype`. -* Not pressing a key on your keyboard for a certain amount of time. -* Entering insert mode. -* Exiting insert mode. +The `` in the second `nnoremap` command told Vim to only consider that +mapping when we're in the same buffer as where we defined it. + +Local Leader +------------ -This is just a tiny sample of the available events -- there are many more you -can use to do lots of interesting things. +In our example we used `x` for our buffer-local mapping, but this is bad +form. In general, when you create a mapping that only applies to specific +buffers you should use `` instead of ``. -The next part of the command is a "pattern" that lets you be more specific about -when you want the command to fire. Start up a new Vim instance and run the -following command: - - :autocmd BufNewFile *.txt :write +Using two separate "leader" keys provides a sort of "namespacing" that will help +you keep all your various mappings straight in your head. -This is almost the same as the last command, but this time it will only apply to -files whose names end in `.txt`. Try it out by running `:edit bar`, then -`:quit`, then `:edit bar.txt`, then `:quit`. You'll see that Vim writes the -`bar.txt` automatically, but *doesn't* write `bar` because it doesn't match the -pattern. +It's even more important when you're writing a plugin for other people to use. +The convention of using `` for local mappings will prevent your +plugin from overwriting someone else's `` mapping that they've +painstakingly burned into their fingers over time. -The final part of the command is the command we want to run when the event -fires. This is pretty self-explanatory, except for one catch: you can't use -special characters like `` in the command. We'll talk about how to get -around this limitation later in the book, but for now you'll just have to live -with it. +Settings +-------- -Another Example ---------------- +In one of the earliest chapters of the book we talked about settings options +with `set`. Some options always apply to all of Vim, but others can be set on +a per-buffer basis. -Let's define another autocommand, this time using a different event. Run the -following command: +Switch to file `foo` and run the following command: - :autocmd BufWrite *.html :normal gg=G + :setlocal wrap -We're getting a bit ahead of ourselves here because we're going to talk about -`normal` later in the book, but for now you'll need to bear with me because it's -tough to come up with useful examples at this point. +Now switch to file `bar` and run this command: -Now create a new file called `foo.html`. Edit it with Vim and enter the -following text *exactly*, including the whitespace: + :setlocal nowrap - - -

Hello!

- - +Make your Vim window smaller and you'll see that the lines in `foo` wrap, but +the lines in `bar` don't. + +Let's try another option. Switch to `foo` and run this command: -Now save this file with `:w`. What happened? Vim seems to have reindented the -file for us before saving it! + :setlocal number -For now I want you to trust me that running `:normal gg=G` will tell Vim to -reindent the current file. Don't worry about how that works just yet. +Now switch over to `bar` and run this command: + + :setlocal nonumber -What we *do* want to pay attention to is the autocommand. The event type is -`BufWrite`, which means the event will be checked whenever you write *any* file. +You now have line numbers in `foo` but not in `bar`. -We used a pattern of `*.html` to ensure that this command will only fire when -we're working on files that end in `.html`. This lets us target our -autocommands at specific files, which is a very powerful idea that we'll -continue to explore later on. +Not all options can be used with `setlocal`. To see if you can set a particular +option locally, read its `:help`. -Multiple Events ---------------- +Shadowing +--------- -You can create a single autocommand bound to *multiple* events by separating the -events with a comma. Run this command: +Before we move on, let's look at a particularly interesting property of local +mappings. Switch over to `foo` and run the following commands: - :autocmd BufWrite,BufRead *.html :normal gg=G - -This is almost like our last command, except it will also reindent the code -whenever we *read* an HTML file as well as when we write it. This could be -useful if you have coworkers that don't indent their HTML well. + :nnoremap Q x + :nnoremap Q dd -A common idiom in Vim scripting is to pair the `BufRead` and `BufNewFile` events -to run a command whenever you open a certain kind of file, regardless of whether -it happened to exist already or not. Run the following command: +Now switch to file `foo` and type `Q`. What happens? - au BufNewFile,BufRead *.html setlocal nowrap +When you press `Q`, Vim will run the first mapping, not the second, because the +first mapping is *more specific* than the second. -This will turn line wrapping off whenever you're working on an HTML file. -Don't worry about `setlocal` right now, we'll get to that later. +Switch to file `bar` and type `Q` to see that Vim uses the second mapping, +because it's not shadowed by the first in this buffer. Exercises --------- -Skim `:help autocmd-events` to see a list of all the events you can bind -autocommands to. You don't need to memorize each one right now, but just try -to get a feel for the kinds of things you can do. +Read `:help setlocal`. + +Read `:help map-local`. diff -r 6837a9468ab7 -r fd0f7560abf1 chapters/12.markdown --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/chapters/12.markdown Sat Oct 08 00:11:39 2011 -0400 @@ -0,0 +1,133 @@ +Autocommands +============ + +Now we're going to look at a topic almost as important as mappings: +autocommands. + +Autocommands are a way to tell Vim to run certain commands whenever certain +events happen. Let's dive right into an example. + +First, open a new file with `:edit foo` and close it right away with `:quit`. +Look on your hard drive and you'll notice that the file is not there. This is +because Vim doesn't actually *create* the file until you save it for the first +time. + +Let's change it so that Vim creates files as soon as you edit them. Run the +following command: + + :autocmd BufNewFile * :write + +This is a lot to take in, but try it out and see that it works. Run `:edit foo` +again, close it with `:quit`, and look at your hard drive. This time the file +will be there (and empty, of course). + +You'll have to close Vim to remove the autocommand. We'll talk about how to +avoid this in a later chapter. + +Autocommand Structure +--------------------- + +Let's take a closer look at the autocommand we just created: + + :autocmd BufNewFile * :write + ^ ^ ^ + | | | + | | The command to run. + | | + | A "pattern" to filter the event. + | + The "event" to watch for. + +The first piece of the command is the type of event we want to watch for. Vim +offers *many* events to watch. Some of them include: + +* Starting to edit a file that doesn't already exist. +* Reading a file, whether it exists or not. +* Switching a buffer's `filetype`. +* Not pressing a key on your keyboard for a certain amount of time. +* Entering insert mode. +* Exiting insert mode. + +This is just a tiny sample of the available events -- there are many more you +can use to do lots of interesting things. + +The next part of the command is a "pattern" that lets you be more specific about +when you want the command to fire. Start up a new Vim instance and run the +following command: + + :autocmd BufNewFile *.txt :write + +This is almost the same as the last command, but this time it will only apply to +files whose names end in `.txt`. Try it out by running `:edit bar`, then +`:quit`, then `:edit bar.txt`, then `:quit`. You'll see that Vim writes the +`bar.txt` automatically, but *doesn't* write `bar` because it doesn't match the +pattern. + +The final part of the command is the command we want to run when the event +fires. This is pretty self-explanatory, except for one catch: you can't use +special characters like `` in the command. We'll talk about how to get +around this limitation later in the book, but for now you'll just have to live +with it. + +Another Example +--------------- + +Let's define another autocommand, this time using a different event. Run the +following command: + + :autocmd BufWrite *.html :normal gg=G + +We're getting a bit ahead of ourselves here because we're going to talk about +`normal` later in the book, but for now you'll need to bear with me because it's +tough to come up with useful examples at this point. + +Now create a new file called `foo.html`. Edit it with Vim and enter the +following text *exactly*, including the whitespace: + + + +

Hello!

+ + + +Now save this file with `:w`. What happened? Vim seems to have reindented the +file for us before saving it! + +For now I want you to trust me that running `:normal gg=G` will tell Vim to +reindent the current file. Don't worry about how that works just yet. + +What we *do* want to pay attention to is the autocommand. The event type is +`BufWrite`, which means the event will be checked whenever you write *any* file. + +We used a pattern of `*.html` to ensure that this command will only fire when +we're working on files that end in `.html`. This lets us target our +autocommands at specific files, which is a very powerful idea that we'll +continue to explore later on. + +Multiple Events +--------------- + +You can create a single autocommand bound to *multiple* events by separating the +events with a comma. Run this command: + + :autocmd BufWrite,BufRead *.html :normal gg=G + +This is almost like our last command, except it will also reindent the code +whenever we *read* an HTML file as well as when we write it. This could be +useful if you have coworkers that don't indent their HTML well. + +A common idiom in Vim scripting is to pair the `BufRead` and `BufNewFile` events +to run a command whenever you open a certain kind of file, regardless of whether +it happened to exist already or not. Run the following command: + + au BufNewFile,BufRead *.html setlocal nowrap + +This will turn line wrapping off whenever you're working on an HTML file. +Don't worry about `setlocal` right now, we'll get to that later. + +Exercises +--------- + +Skim `:help autocmd-events` to see a list of all the events you can bind +autocommands to. You don't need to memorize each one right now, but just try +to get a feel for the kinds of things you can do.