usr_43.txt For Vim version 7.4. Last change: 2008 Dec 28LINK

VIM USER MANUAL - by Bram Moolenaar

Using filetypes

When you are editing a file of a certain type, for example a C program or a

shell script, you often use the same option settings and mappings. You

quickly get tired of manually setting these each time. This chapter explains

how to do it automatically.

43.1 Plugins for a filetype

43.2 Adding a filetype

Next chapter: usr_44.txt Your own syntax highlighted

Previous chapter: usr_42.txt Add new menus

Table of contents: usr_toc.txt

==============================================================================

43.1 Plugins for a filetype filetype-pluginLINK

How to start using filetype plugins has already been discussed here:

add-filetype-plugin. But you probably are not satisfied with the default

settings, because they have been kept minimal. Suppose that for C files you

want to set the 'softtabstop' option to 4 and define a mapping to insert a

three-line comment. You do this with only two steps:

your-runtime-dirLINK

1. Create your own runtime directory. On Unix this usually is "~/.vim". In

this directory create the "ftplugin" directory:

mkdir ~/.vim

mkdir ~/.vim/ftplugin

When you are not on Unix, check the value of the 'runtimepath' option to

see where Vim will look for the "ftplugin" directory:

set runtimepath

You would normally use the first directory name (before the first comma).

You might want to prepend a directory name to the 'runtimepath' option in

your vimrc file if you don't like the default value.

2. Create the file "~/.vim/ftplugin/c.vim", with the contents:

setlocal softtabstop=4

noremap <buffer> <LocalLeader>c o/**************<CR><CR>/<Esc>

Try editing a C file. You should notice that the 'softtabstop' option is set

to 4. But when you edit another file it's reset to the default zero. That is

because the ":setlocal" command was used. This sets the 'softtabstop' option

only locally to the buffer. As soon as you edit another buffer, it will be

set to the value set for that buffer. For a new buffer it will get the

default value or the value from the last ":set" command.

Likewise, the mapping for "\c" will disappear when editing another buffer.

The ":map <buffer>" command creates a mapping that is local to the current

buffer. This works with any mapping command: ":map!", ":vmap", etc. The

<LocalLeader> in the mapping is replaced with the value of the

"maplocalleader" variable.

You can find examples for filetype plugins in this directory:

$VIMRUNTIME/ftplugin/

More details about writing a filetype plugin can be found here:

write-plugin.

==============================================================================

43.2 Adding a filetypeLINK

If you are using a type of file that is not recognized by Vim, this is how to

get it recognized. You need a runtime directory of your own. See

your-runtime-dir above.

Create a file "filetype.vim" which contains an autocommand for your filetype.

(Autocommands were explained in section 40.3.) Example:

augroup filetypedetect

au BufNewFile,BufRead *.xyz setf xyz

augroup END

This will recognize all files that end in ".xyz" as the "xyz" filetype. The

":augroup" commands put this autocommand in the "filetypedetect" group. This

allows removing all autocommands for filetype detection when doing ":filetype

off". The "setf" command will set the 'filetype' option to its argument,

unless it was set already. This will make sure that 'filetype' isn't set

twice.

You can use many different patterns to match the name of your file. Directory

names can also be included. See autocmd-patterns. For example, the files

under "/usr/share/scripts/" are all "ruby" files, but don't have the expected

file name extension. Adding this to the example above:

augroup filetypedetect

au BufNewFile,BufRead *.xyz setf xyz

au BufNewFile,BufRead /usr/share/scripts/* setf ruby

augroup END

However, if you now edit a file /usr/share/scripts/README.txt, this is not a

ruby file. The danger of a pattern ending in "*" is that it quickly matches

too many files. To avoid trouble with this, put the filetype.vim file in

another directory, one that is at the end of 'runtimepath'. For Unix for

example, you could use "~/.vim/after/filetype.vim".

You now put the detection of text files in ~/.vim/filetype.vim:

augroup filetypedetect

au BufNewFile,BufRead *.txt setf text

augroup END

That file is found in 'runtimepath' first. Then use this in

~/.vim/after/filetype.vim, which is found last:

augroup filetypedetect

au BufNewFile,BufRead /usr/share/scripts/* setf ruby

augroup END

What will happen now is that Vim searches for "filetype.vim" files in each

directory in 'runtimepath'. First ~/.vim/filetype.vim is found. The

autocommand to catch *.txt files is defined there. Then Vim finds the

filetype.vim file in $VIMRUNTIME, which is halfway 'runtimepath'. Finally

~/.vim/after/filetype.vim is found and the autocommand for detecting ruby

files in /usr/share/scripts is added.

When you now edit /usr/share/scripts/README.txt, the autocommands are

checked in the order in which they were defined. The *.txt pattern matches,

thus "setf text" is executed to set the filetype to "text". The pattern for

ruby matches too, and the "setf ruby" is executed. But since 'filetype' was

already set to "text", nothing happens here.

When you edit the file /usr/share/scripts/foobar the same autocommands are

checked. Only the one for ruby matches and "setf ruby" sets 'filetype' to

ruby.

RECOGNIZING BY CONTENTS

If your file cannot be recognized by its file name, you might be able to

recognize it by its contents. For example, many script files start with a

line like:

#!/bin/xyz

To recognize this script create a file "scripts.vim" in your runtime directory

(same place where filetype.vim goes). It might look like this:

if did_filetype()

finish

endif

if getline(1) =~ '^#!.*[/\\]xyz\>'

setf xyz

endif

The first check with did_filetype() is to avoid that you will check the

contents of files for which the filetype was already detected by the file

name. That avoids wasting time on checking the file when the "setf" command

won't do anything.

The scripts.vim file is sourced by an autocommand in the default

filetype.vim file. Therefore, the order of checks is:

1. filetype.vim files before $VIMRUNTIME in 'runtimepath'

2. first part of $VIMRUNTIME/filetype.vim

3. all scripts.vim files in 'runtimepath'

4. remainder of $VIMRUNTIME/filetype.vim

5. filetype.vim files after $VIMRUNTIME in 'runtimepath'

If this is not sufficient for you, add an autocommand that matches all files

and sources a script or executes a function to check the contents of the file.

==============================================================================

Next chapter: usr_44.txt Your own syntax highlighted

Copyright: see manual-copyright vim:tw=78:ts=8:ft=help:norl: