1 """"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
2 " Multi-version vimrc compatible with version 4 and above.
3 """"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
5 " Note that "if <condition> | call Something() | endif" syntax is unsupported
6 " in Vim 4 so we write all our functions out the long way. It does work in
7 " autocommand definitions, however.
9 " Vim 4 complains if version isn't set in the configuration file.
12 """"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
13 " Handle options safe to use in version 4. Vim 4 parses but ignores the
14 " "if version" syntax used later in this file so we don't use it. No attempt
15 " is made to make this configuration compatible with Vim 3.
16 """"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
17 " No compatibility mode.
22 " And use spaces not tabs.
24 " And << and >> indent by 2.
27 " Allow backspace to delete before start of line.
32 " Show partial commands in the ruler.
34 " And always show the status line.
39 se cinkeys=0{,0},0),:,!^F,o,O,e
45 " Don't be bugged by messages at the bottom of the screen.
51 " Case-insensitive search.
53 " But override by typing capitals.
56 " Look for ctags in home directory first.
57 se tags=~/.tags,./tags,tags
59 " Don't timeout waiting to interpet, eg, <ESC>OA as an escape code.
62 " Use ^B to search backward when completing.
64 " Use ^L to show matching completions but don't select one.
65 inoremap <C-l> <C-n><C-p>
67 """"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
68 " Handle options only available in Vim 5 and above.
69 """"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
73 " Tell Vim we use dark backgrounds in our terminals.
74 if ! has("gui_running")
78 " Allow mouse use in a terminal.
81 " Update more quickly. For use with sign highlighting as polling for
82 " CursorMove makes redrawing slow.
87 " Enable tab-completion prompting for commands.
89 " Don't list object files when globbing files to load.
90 se wildignore+=*.o,*.obj
91 " So there's no need to assign them low priority.
92 se suffixes-=*.o,*.obj
94 " Save sessions in UNIX format with / as file separator. This is
98 " Nuke any pre-existing autocommands.
111 " Save the current window width so we can restore it when we quit.
112 if ! exists("g:oldcols")
113 let g:oldcols=&columns
116 " More GUI options. Add icon, tearoffs and toolbar.
119 " Allow dynamic window resize even if we aren't in an xterm.
120 se t_WS=
\e[8;%p1%d;%p2%dt
122 " Highlight search results.
125 " Set graphical window title.
126 se titlestring=%{Show_TitleString()}
128 " Syntax highlighting. New versions will use syn enable instead.
138 " Set up our variables.
140 if ! exists("b:iainlist")
143 if ! exists("b:iainhex")
146 if ! exists("b:iainverbose")
147 let b:iainverbose = 0
149 if ! exists("b:iainstatus")
150 " Window Flags: (F)ocused, (I)nsert mode, Cursor (H)old.
151 let b:iainstatus = "Fih"
153 if ! exists("g:iainextracolumns")
154 let g:iainextracolumns = 0
157 if ! exists("g:marksigns")
160 if ! exists("g:firstsign")
161 let g:firstsign = 100
166 " Helper for status line.
167 " Show space, underscore or dollar sign depending on list mode.
173 elseif b:iainlist == 1
182 " Helper for status line.
183 " Show c or C to denote case-sensitivity.
192 " Helper for status line.
193 " Show the size of the tabstop.
198 " Helper for status line.
199 " Show p when paste mode is on.
208 " Show the window title.
209 fun! Show_TitleString()
213 let l:ts1=printf("%2d: %s", bufnr(""), expand('%t'))
215 return printf("%s (%s) %s", l:ts1, getcwd(), v:servername)
218 " Show the status line.
219 fun! Show_StatusLine()
221 let l:sl1='%2n\:\ %<%f\ [%{Show_List()}%{Show_Case()}%{Show_Tabstop()}%{Show_Paste()}%Y%M%R]\ %='
222 let l:sl3='L:%4.6l/%-4.6L\ C:%3.6c\ \|\ %P'
225 let l:hexformat='0\x%02B'
228 let l:sl2=l:hexformat . '\ \|\ P:%4.6o\ '
232 exec "set statusline=" . l:sl1 . l:sl2 . l:sl3
235 " Toggle case-sensitivity.
240 " Grow or shrink the window size.
241 fun! Resize_Columns(op, ...)
243 " Vim 5 hardcodes the size of numbers column to 8.
245 let l:columns = &numberwidth
253 exe "let l:resize=" . &columns . a:op . l:columns
254 let l:resize = "se columns=" . l:resize
256 " HACK: Inside screen there is an extra line for the status bar. Vim
257 " manages the resize by sending an escape sequence to set the number of
258 " lines and number of columns in one action. To do this it will first query
259 " the number of lines and then set <same number of lines> by <new number of
260 " columns>. Because of the extra line for the status bar this results in
261 " the real terminal being shrunk by a line. We ask for the terminal to grow
262 " by a line so it ends up actually being the same.
263 if &term =~ '^screen'
264 let l:resize = l:resize . " lines=" . (&lines + 1)
270 " Toggle number display.
273 let &number = ! &number
277 let l:num_numbers = 0
278 while l:i <= winnr("$")
279 if getwinvar(l:i, "&number") == 1
280 let l:num_numbers = l:num_numbers + 1
285 if l:num_numbers == 0
286 let g:iainextracolumns = 0
288 call Resize_Columns("-")
290 elseif g:iainextracolumns == 0
291 let g:iainextracolumns = 1
293 call Resize_Columns("+")
299 " Restore window size.
300 au Display VimLeave * if exists("g:oldcols") | call Resize_Columns("-", (&columns - g:oldcols)) | endif
303 au Mode BufEnter * if &ft == "make" | call MakeMode_map() | endif
304 au Mode BufLeave * if &ft == "make" | call MakeMode_unmap() | endif
306 " Entering Make mode.
316 fun! MakeMode_unmap()
322 " Show the status line for the first time.
323 call Show_StatusLine()
325 " Function to create mappings with either a hardcoded \ or <Leader>.
326 fun! Mapping(keysequence,mapping)
328 exec "map \\" . a:keysequence . " " . a:mapping
330 exec "map <Leader>" . a:keysequence . " " . a:mapping
334 " Use - and = to create underlines.
335 call Mapping("-", "yyp:s/./-/g<RETURN>:let @/=''<RETURN>:<RETURN>")
336 call Mapping("=", "yyp:s/./=/g<RETURN>:let @/=''<RETURN>:<RETURN>")
338 " Change to ts=2 with \2.
339 call Mapping("2", ":se ts=2<CR>:<CR>")
340 " Change to ts=4 with \4.
341 call Mapping("4", ":se ts=4<CR>:<CR>")
342 " Change to ts=8 with \8.
343 call Mapping("8", ":se ts=8<CR>:<CR>")
344 " Change to ts=16 with \6.
345 call Mapping("6", ":se ts=16<CR>:<CR>")
346 " Change to ts=32 with \3.
347 call Mapping("3", ":se ts=32<CR>:<CR>")
348 " Toggle paste mode with \p.
349 call Mapping("p", ":se paste!<CR>:<CR>")
350 " Swap case-sensitivity with \c.
351 call Mapping("c", ":call Invert_Case()<CR>:<CR>")
352 " Change number mode with \n.
353 call Mapping("n", ":call Number(1)<CR>:<CR>")
354 " Expand or shrink window size with \> and \<.
355 call Mapping(">", ":call Resize_Columns('+')<CR>:<CR>")
356 call Mapping("<", ":call Resize_Columns('-')<CR>:<CR>")
357 " Clear search pattern with \/.
358 call Mapping("/", ":let @/=\"\"<CR>:<CR>")
360 " Forget the Ex mode mapping.
363 " Vim tip 99: What's the highlighting group under the cursor?
364 call Mapping("h", ":echo \"hi<\" . synIDattr(synID(line(\".\"),col(\".\"),1),\"name\") . '> trans<' . synIDattr(synID(line(\".\"),col(\".\"),0),\"name\") . \"> lo<\" . synIDattr(synIDtrans(synID(line(\".\"),col(\".\"),1)),\"name\") . \">\"<CR>")
366 fun! Startup_Resize()
369 " Resize for numbers.
372 let l:columns = &numberwidth
382 let l:columns = l:columns + 2
387 if g:oldcols < (80 + l:columns)
388 call Resize_Columns("+", l:columns)
392 " Show numbers by default.
393 au Display VimEnter * call Number(0)
395 " Resize after startup.
396 au Display VimEnter * call Startup_Resize()
399 """"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
400 " Handle options only available in Vim 6 and above.
401 """"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
405 " Remember quickfix state.
408 " Set indenting by filetype.
411 " Less intrusive syntax highlighting.
415 if has("gui_running")
418 se guifont=DejaVu_Sans_Mono:h10:cANSI
420 se guifont=DejaVu\ Sans\ Mono\ 10
425 if has("gui_running") || &t_Co > 16
432 " Ignore whitespace when diffing.
433 se diffopt=filler,iwhite
435 " Expand window when doing a vertical diff.
440 " Remember that we are opening the quickfix window.
441 au Mode BufWinEnter quickfix let g:quickfixing=1
442 au Mode BufUnload * if &ft == "qf" | let g:quickfixing=0 | endif
444 " Allow in-place editing of crontabs.
445 au Mode FileType crontab set backupcopy=yes
447 " Make * and # work the way you expect in visual mode.
448 vnoremap * y/\V<C-R>=substitute(escape(@@,"/\\"),"\n","\\\\n","ge")<CR><CR>
449 vnoremap # y?\V<C-R>=substitute(escape(@@,"?\\"),"\n","\\\\n","ge")<CR><CR>
451 " Set mark and update highlighting.
453 au Signs BufEnter * call <SID>Highlight_Signs()
454 au Signs CursorHold * call <SID>Highlight_Signs()
457 fun! <SID>Prep_Signs()
458 if ! exists("b:signdot") || ! g:marksigns
461 if ! exists("b:signdash") || ! g:marksigns
464 if ! exists("b:signquote") || ! g:marksigns
467 if ! exists("b:signcaret") || ! g:marksigns
470 if ! exists("b:signless") || ! g:marksigns
473 if ! exists("b:signgreater") || ! g:marksigns
476 if ! exists("b:signleft") || ! g:marksigns
479 if ! exists("b:signright") || ! g:marksigns
482 if ! exists("b:signa") || ! g:marksigns
485 if ! exists("b:signb") || ! g:marksigns
488 if ! exists("b:signc") || ! g:marksigns
491 if ! exists("b:signd") || ! g:marksigns
494 if ! exists("b:signe") || ! g:marksigns
497 if ! exists("b:signf") || ! g:marksigns
500 if ! exists("b:signA") || ! g:marksigns
503 if ! exists("b:signB") || ! g:marksigns
506 if ! exists("b:signC") || ! g:marksigns
509 if ! exists("b:signD") || ! g:marksigns
512 if ! exists("b:signE") || ! g:marksigns
515 if ! exists("b:signF") || ! g:marksigns
520 fun! <SID>Place_Sign(number, line, old, name)
525 exe "sign unplace " . (g:firstsign + a:number) . " buffer=" . bufnr("")
526 " Don't place the sign if it would conflict with the last change sign.
527 exe "sign place " . (g:firstsign + a:number) . " line=" . a:line . " name=" . a:name . " buffer=" . bufnr("")
531 fun! <SID>Highlight_Signs(...)
532 if ! has("signs") || ! g:marksigns
536 call <SID>Prep_Signs()
538 let b:signdot = <SID>Place_Sign(0, line("'."), b:signdot, "MarkDot")
539 let b:signdash = <SID>Place_Sign(1, line("''"), b:signdash, "MarkDash")
540 let b:signquote = <SID>Place_Sign(2, line("'\""), b:signquote, "MarkQuote")
541 let b:signcaret = <SID>Place_Sign(3, line("'^"), b:signcaret, "MarkCaret")
542 let b:signless = <SID>Place_Sign(4, line("'<"), b:signcaret, "MarkLess")
543 let b:signgreater = <SID>Place_Sign(5, line("'>"), b:signcaret, "MarkGreater")
544 let b:signleft = <SID>Place_Sign(6, line("'["), b:signcaret, "MarkLeft")
545 let b:signright = <SID>Place_Sign(7, line("']"), b:signcaret, "MarkRight")
547 let b:signa = <SID>Place_Sign(8, line("'a"), b:signa, "Marka")
548 let b:signb = <SID>Place_Sign(9, line("'b"), b:signb, "Markb")
549 let b:signc = <SID>Place_Sign(10, line("'c"), b:signc, "Markc")
550 let b:signd = <SID>Place_Sign(11, line("'d"), b:signd, "Markd")
551 let b:signe = <SID>Place_Sign(12, line("'e"), b:signe, "Marke")
552 let b:signf = <SID>Place_Sign(13, line("'f"), b:signf, "Markf")
553 let b:signA = <SID>Place_Sign(14, line("'A"), b:signA, "MarkA")
554 let b:signB = <SID>Place_Sign(15, line("'B"), b:signB, "MarkB")
555 let b:signC = <SID>Place_Sign(16, line("'C"), b:signC, "MarkC")
556 let b:signD = <SID>Place_Sign(17, line("'D"), b:signD, "MarkD")
557 let b:signE = <SID>Place_Sign(18, line("'E"), b:signE, "MarkE")
558 let b:signF = <SID>Place_Sign(19, line("'F"), b:signF, "MarkF")
562 fun! <SID>Cycle_Signs(resize)
567 let g:marksigns = ! g:marksigns
570 " Signs to highlight marks.
571 " Syntax won't work properly in Vim 6.
572 sign define MarkDash text=' texthl=MarkSign
573 sign define MarkDot text=* texthl=MarkDot
574 sign define MarkQuote text=" texthl=MarkSign
575 sign define MarkCaret text=^ texthl=MarkSign
576 sign define MarkLess text=< texthl=MarkSign
577 sign define MarkGreater text=> texthl=MarkSign
578 sign define MarkLeft text=[ texthl=MarkSign
579 sign define MarkRight text=] texthl=MarkSign
580 sign define Marka text=a texthl=MarkSign linehl=MarkLine
581 sign define Markb text=b texthl=MarkSign linehl=MarkLine
582 sign define Markc text=c texthl=MarkSign linehl=MarkLine
583 sign define Markd text=d texthl=MarkSign linehl=MarkLine
584 sign define Marke text=e texthl=MarkSign linehl=MarkLine
585 sign define Markf text=f texthl=MarkSign linehl=MarkLine
586 sign define MarkA text=A texthl=MarkSign linehl=MarkLine
587 sign define MarkB text=B texthl=MarkSign linehl=MarkLine
588 sign define MarkC text=C texthl=MarkSign linehl=MarkLine
589 sign define MarkD text=D texthl=MarkSign linehl=MarkLine
590 sign define MarkE text=E texthl=MarkSign linehl=MarkLine
591 sign define MarkF text=F texthl=MarkSign linehl=MarkLine
594 call Resize_Columns("+", 2)
596 call <SID>Highlight_Signs()
598 exe "sign unplace " . (g:firstsign + 0)
599 exe "sign unplace " . (g:firstsign + 1)
600 exe "sign unplace " . (g:firstsign + 2)
601 exe "sign unplace " . (g:firstsign + 3)
602 exe "sign unplace " . (g:firstsign + 4)
603 exe "sign unplace " . (g:firstsign + 5)
604 exe "sign unplace " . (g:firstsign + 6)
605 exe "sign unplace " . (g:firstsign + 7)
606 exe "sign unplace " . (g:firstsign + 8)
607 exe "sign unplace " . (g:firstsign + 9)
608 exe "sign unplace " . (g:firstsign + 10)
609 exe "sign unplace " . (g:firstsign + 11)
610 exe "sign unplace " . (g:firstsign + 12)
611 exe "sign unplace " . (g:firstsign + 13)
612 exe "sign unplace " . (g:firstsign + 14)
613 exe "sign unplace " . (g:firstsign + 15)
614 exe "sign unplace " . (g:firstsign + 16)
615 exe "sign unplace " . (g:firstsign + 17)
616 exe "sign unplace " . (g:firstsign + 18)
617 exe "sign unplace " . (g:firstsign + 19)
619 sign undefine MarkDash
620 sign undefine MarkDot
621 sign undefine MarkQuote
622 sign undefine MarkCaret
623 sign undefine MarkLess
624 sign undefine MarkGreater
625 sign undefine MarkLeft
626 sign undefine MarkRight
640 call <SID>Prep_Signs()
642 call Resize_Columns("-", 2)
649 let basic='tab:\\_,trail:_,extends:<,precedes:>'
651 let b:iainlist = b:iainlist + 1
657 elseif b:iainlist == 1
658 exec "set lcs=" . basic
661 exec "set lcs=" . basic . ",eol:$"
666 " Cycle between hex and decimal display of toolbar stuff.
667 fun! Cycle_HexStatusLine()
669 let b:iainhex = ! b:iainhex
670 call Show_StatusLine()
673 " Cycle verbose display of toolbar stuff.
674 fun! Cycle_VerboseStatusLine()
676 let b:iainverbose = ! b:iainverbose
677 call Show_StatusLine()
680 " Toggle quickfix window.
681 fun! Cycle_Quickfix()
682 if g:quickfixing == 1
690 " Swap hex/decimal statusline with \x.
691 call Mapping("x", ":call Cycle_HexStatusLine()<CR>:<CR>")
692 " Change statusline verbosity with \v.
693 call Mapping("v", ":call Cycle_VerboseStatusLine()<CR>:<CR>")
694 " Cycle list styles with \l.
695 call Mapping("l", ":call Cycle_List()<CR>:<CR>")
696 " Toggle tags with \t.
697 call Mapping("t", ":Tlist<CR>")
698 " Change foldmethod with \f.
699 call Mapping("f", ":se foldenable!<CR>:<CR>")
700 " Toggle quickfix window with \q.
701 call Mapping("q", ":call Cycle_Quickfix()<CR>:<CR>")
702 " Rerun filetype detection with \s. The s is for syntax, as this will be
703 " updated as a side-effect.
704 call Mapping("s", ":filetype detect<CR>:<CR>")
705 " Toggle marks with \m.
706 call Mapping("m", ":call <SID>Cycle_Signs(1)<CR>:<CR>")
708 fun! <SID>Iain_Colour(colour)
710 if a:colour == "darkblue"
712 elseif a:colour == "darkmagenta"
714 elseif a:colour == "darkred"
716 elseif a:colour == "red"
720 if a:colour == "darkblue"
722 elseif a:colour == "darkmagenta"
724 elseif a:colour == "darkred"
726 elseif a:colour == "red"
734 " Change status bar colour when various things happen.
735 " Flags: H/h: Cursor held/moved.
736 " F/f: Focus gained/lost.
737 " I/i: Insert mode entered/left.
738 fun! Highlight_StatusLine(flag)
739 " Get current status.
742 " Change the status based on the flag. XXX: Does Vim let us to do flags?
743 let re = "[" . tolower(a:flag) . toupper(a:flag) . "]"
744 let b:iainstatus = substitute(b:iainstatus, re, a:flag, "")
746 let l:normalcolour = "darkblue"
747 let l:editingcolour = "darkmagenta"
748 let l:warningcolour = "darkred"
749 let l:readonlycolour = "red"
752 let l:colour = l:normalcolour
753 " Maybe override depending on status.
754 if b:iainstatus =~# "H"
755 if b:iainstatus =~# "I"
756 " Held in insert mode. Add extra highlight if we don't have focus.
757 if b:iainstatus =~# "f"
758 let l:colour = l:warningcolour
760 let l:colour = l:editingcolour
764 if b:iainstatus =~# "I"
765 " Regular insert mode.
766 let l:colour = l:editingcolour
770 " Override again if readonly.
771 if l:colour != l:normalcolour
772 if getbufvar("", "&ro")
773 let l:colour = l:readonlycolour
777 let l:termcolour = <SID>Iain_Colour(l:colour)
779 exec "highlight StatusLine gui=bold term=bold cterm=bold guifg=white guibg=" . l:colour . " ctermfg=white ctermbg=" . l:termcolour
782 au Display VimEnter * call Highlight_StatusLine("")
784 " Show signs by default.
785 au Display VimEnter * call <SID>Cycle_Signs(0)
788 """"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
789 " Handle options only available in Vim 7 and above.
790 """"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
794 " Helper to show tab name.
795 fun! <SID>TabName(label, gui)
796 let l:label = a:label
798 let l:label = "No Name"
800 let l:label = "[" . l:label . "]"
803 let l:label = fnamemodify(l:label, ":t")
804 if strlen(l:label) >= 18
805 let l:label = l:label[0:17] . ".."
811 " Find out if any buffer was modified.
812 fun! <SID>TabModified(buflist)
814 while i < len(a:buflist)
815 if getbufvar(a:buflist[l:i], "&modified") == 1
825 let l:s = "%#TabLineFill#Tabs:"
828 while l:i < tabpagenr("$")
831 let l:buflist = tabpagebuflist(l:i)
832 let l:winnr = tabpagewinnr(l:i)
833 let l:n = tabpagewinnr(l:i, "$")
834 let l:label = <SID>TabName(bufname(l:buflist[l:winnr - 1]), 0)
835 let l:modified = <SID>TabModified(l:buflist)
837 " Choose highlighting.
838 if l:i == tabpagenr()
839 let l:s .= "%#TabLineSel#[" . l:n . l:modified . " " . l:label . "]"
841 let l:s .= "%#TabLine# " . l:n . l:modified . " " . l:label . " "
846 let l:s .= "%#TabLine#%T"
850 " Per tab label for the GUI.
851 fun! Show_GUITabLine()
852 let l:buflist = tabpagebuflist(v:lnum)
853 let l:winnr = tabpagewinnr(v:lnum)
854 let l:s = tabpagewinnr(v:lnum, "$")
855 let l:label = <SID>TabName(bufname(l:buflist[l:winnr - 1]), 1)
856 let l:modified = <SID>TabModified(l:buflist)
858 let l:s .= l:modified . " " . l:label
862 se tabline=%!Show_TabLine()
863 se guitablabel=%!Show_GUITabLine()
865 au StatusLine CursorHoldI * call Highlight_StatusLine("H")
866 au StatusLine CursorMovedI * call Highlight_StatusLine("h")
867 au StatusLine FocusGained * call Highlight_StatusLine("F")
868 au StatusLine FocusLost * call Highlight_StatusLine("f")
869 au StatusLine InsertEnter * call Highlight_StatusLine("I")
870 au StatusLine InsertLeave * call Highlight_StatusLine("i")
873 au Signs InsertEnter * call <SID>Highlight_Signs()
874 au Signs InsertLeave * call <SID>Highlight_Signs()
877 " Limit the size of the popup menu when completing.
880 " Make diffs vertical by default.
883 " Set size of numbers column.
886 " Add "previous tab" mapping as gb.
887 map gb :tabprevious<CR>:<CR>
894 " Yet more GUI options. Add tabs.
899 let g:p4Presets='P4CONFIG'