Vim Tips Wiki
No edit summary
(Reword and fix errors in text and script)
Line 1: Line 1:
{{review}}
 
 
{{TipImported
 
{{TipImported
 
|id=331
 
|id=331
Line 6: Line 5:
 
|created=September 22, 2002
 
|created=September 22, 2002
 
|complexity=basic
 
|complexity=basic
|author=Alex A. Naanou
+
|author=
|version=5.7
+
|version=6.0
 
|rating=154/50
 
|rating=154/50
 
|category1=
 
|category1=
 
|category2=
 
|category2=
 
}}
 
}}
  +
Options set in your [[vimrc]] will apply to all files that you edit. You can also set:
One of the things about Vim that are both quite simple yet very useful is that you can store by-file settings... That is each file can contain settings specific to it. This thing is called a modeline {{help|modeline}}. Though this is limited only to the 'set' command arguments, you can store quite a lot local file settings like the indent type, folding method and so on.
 
  +
*Different options for all files of a certain type (for example, all <tt>*.py</tt> files). See [[VimTip1510|filetypes]] and an [[VimTip1565|example]].
  +
*Different options for a particular file using modelines (this tip).
   
  +
==Examples==
The syntax is as follows:
 
  +
For example, in a particular file you may want each tab character that you type to be expanded to spaces. To achieve this, put the following modeline near the top or the bottom of that file:
 
<pre>
 
<pre>
// vim:set ts=4 sw=4 nowrap:
+
# vim: set expandtab:
 
</pre>
 
</pre>
  +
or
 
  +
In a Python file, the '<tt>#</tt>' starts a comment so the modeline is not interpreted by Python.
  +
  +
The following examples show some alternatives that could be in a C file:
 
<pre>
 
<pre>
/* vim:noai:ts=2:sw=4: */
+
// vim: noai:ts=4:sw=4
  +
-or-
  +
/* vim: noai:ts=4:sw=4
  +
*/
  +
-or-
  +
/* vim: set noai ts=4 sw=4: */
 
</pre>
 
</pre>
FIXME The above modeline does not actually work: "E518: Unknown option: */"
 
   
  +
With "<tt>set</tt>", the modeline ends at the first colon. Without "<tt>set</tt>", no text can follow the options, so for example, the following is invalid:
The modelines can be contained in comments so as to not interfere with the file syntax (shown here for C/C++). These lines are read by Vim when it loads the file, and they can either be in the first or last 5 lines (by default).
 
 
<pre>
  +
Error E518: Unknown option: */
  +
/* vim: noai:ts=4:sw=4 */
 
</pre>
   
  +
==Adding a modeline==
Please note that the second modeline syntax (the one using "se[t]") _must_ be colon terminated, while the first (plain) one _may_.
 
  +
With the following in your [[vimrc]] and the default leader key, you could type <tt>\ml</tt> to add a modeline based on your current settings:
 
<pre>
 
" Append modeline after last line in buffer.
 
function! AppendModeline()
  +
let save_cursor = getpos('.')
 
$put =printf(&commentstring, ' vim: set ts='.&tabstop.' sw='.&shiftwidth.' tw='.&textwidth.': ')
  +
call setpos('.', save_cursor)
 
endfunction
 
nnoremap <silent> <Leader>ml :call AppendModeline()<CR>
 
</pre>
   
  +
In a C file, you would get a modeline like this:
==Comments==
 
Speaking of modelines I find it handy to have a very primitive menu entry to insert my normal modeline for me:
 
 
<pre>
 
<pre>
  +
/* vim: set ts=8 sw=4 tw=0: */
amenu Fe&amp;ral's.Insert\ a\ Vim\ modeline &lt;Esc&gt;&lt;Esc&gt;ggOvim:ff=unix ts=4 ss=4&lt;CR&gt;vim60:fdm=marker&lt;esc&gt;gg
 
 
</pre>
 
</pre>
   
  +
Alternatively, you could use a simple menu entry like this:
This will net you a (I think proper) modeline at the start of the file like so:
 
  +
<pre>
 
amenu Edit.Insert\ &modeline <Esc><Esc>ggOvim:ff=unix ts=4 ss=4<CR>vim60:fdm=marker<Esc>
  +
</pre>
  +
  +
Choosing the menu item would insert two modelines like this:
 
<pre>
 
<pre>
 
vim:ff=unix ts=4 ss=4
 
vim:ff=unix ts=4 ss=4
Line 40: Line 67:
 
</pre>
 
</pre>
   
  +
==Security==
----
 
  +
{{Todo}}
This mechanism can be extended to 'let'. Cf. for instance: {{script|id=83}}.
 
  +
*Need note on security implications of modelines and reference to alternatives.
  +
*Text other than "vim:" can be recognised as a modeline.
  +
*Google "vim modeline vulnerability" (without quotes) for information.
   
  +
==References==
----
 
  +
*{{help|auto-setting}}
  +
*{{help|modeline}}
  +
*{{help|'modeline'}} determines whether to look for modelines
  +
*{{help|'modelines'}} number of lines checked to find each modeline
   
 
==Comments==
It is also possible to append a modeline using the file type's comment string:
 
 
This mechanism can be extended to 'let' &ndash; see {{script|id=83}}.
<pre>
 
  +
function! InsertModeline()
 
 
----
" save the old position
 
let l:pos = line( '.' ).' | normal! '.virtcol( '.' ).'|'
 
" insert the modeline at the end of the buffer
 
execute "normal Go" . printf(&commentstring, "vim: ts=".tabstop." sw=".&shiftwidth." tw=".&textwidth.": " )
 
" restore the old position
 
exe l:pos
 
endif
 
endfunction
 
</pre>
 
Then one may create a mapping such as:
 
<pre>
 
nnoremap <silent> <LocalLeader>ml :call InsertModeline()<CR>
 
</pre>
 

Revision as of 03:29, 22 September 2008

Tip 331 Printable Monobook Previous Next

created September 22, 2002 · complexity basic · version 6.0


Options set in your vimrc will apply to all files that you edit. You can also set:

  • Different options for all files of a certain type (for example, all *.py files). See filetypes and an example.
  • Different options for a particular file using modelines (this tip).

Examples

For example, in a particular file you may want each tab character that you type to be expanded to spaces. To achieve this, put the following modeline near the top or the bottom of that file:

# vim: set expandtab:

In a Python file, the '#' starts a comment so the modeline is not interpreted by Python.

The following examples show some alternatives that could be in a C file:

// vim: noai:ts=4:sw=4
   -or-
/* vim: noai:ts=4:sw=4
*/
   -or-
/* vim: set noai ts=4 sw=4: */

With "set", the modeline ends at the first colon. Without "set", no text can follow the options, so for example, the following is invalid:

Error E518: Unknown option: */
/* vim: noai:ts=4:sw=4 */

Adding a modeline

With the following in your vimrc and the default leader key, you could type \ml to add a modeline based on your current settings:

" Append modeline after last line in buffer.
function! AppendModeline()
  let save_cursor = getpos('.')
  $put =printf(&commentstring, ' vim: set ts='.&tabstop.' sw='.&shiftwidth.' tw='.&textwidth.': ')
  call setpos('.', save_cursor)
endfunction
nnoremap <silent> <Leader>ml :call AppendModeline()<CR>

In a C file, you would get a modeline like this:

/* vim: set ts=8 sw=4 tw=0: */

Alternatively, you could use a simple menu entry like this:

amenu Edit.Insert\ &modeline <Esc><Esc>ggOvim:ff=unix ts=4 ss=4<CR>vim60:fdm=marker<Esc>

Choosing the menu item would insert two modelines like this:

vim:ff=unix ts=4 ss=4
vim60:fdm=marker

Security

 TO DO 

  • Need note on security implications of modelines and reference to alternatives.
  • Text other than "vim:" can be recognised as a modeline.
  • Google "vim modeline vulnerability" (without quotes) for information.

References

Comments

This mechanism can be extended to 'let' – see script#83.