1" Vim filetype plugin file
2" Language:	man
3" Maintainer:	SungHyun Nam <goweol@gmail.com>
4" Last Change:	2008 Sep 17
5
6" To make the ":Man" command available before editing a manual page, source
7" this script from your startup vimrc file.
8
9" If 'filetype' isn't "man", we must have been called to only define ":Man".
10if &filetype == "man"
11
12  " Only do this when not done yet for this buffer
13  if exists("b:did_ftplugin")
14    finish
15  endif
16  let b:did_ftplugin = 1
17
18  " allow dot and dash in manual page name.
19  setlocal iskeyword+=\.,-
20
21  " Add mappings, unless the user didn't want this.
22  if !exists("no_plugin_maps") && !exists("no_man_maps")
23    if !hasmapto('<Plug>ManBS')
24      nmap <buffer> <LocalLeader>h <Plug>ManBS
25    endif
26    nnoremap <buffer> <Plug>ManBS :%s/.\b//g<CR>:setl nomod<CR>''
27
28    nnoremap <buffer> <c-]> :call <SID>PreGetPage(v:count)<CR>
29    nnoremap <buffer> <c-t> :call <SID>PopPage()<CR>
30  endif
31
32endif
33
34if exists(":Man") != 2
35  com -nargs=+ Man call s:GetPage(<f-args>)
36  nmap <Leader>K :call <SID>PreGetPage(0)<CR>
37endif
38
39" Define functions only once.
40if !exists("s:man_tag_depth")
41
42let s:man_tag_depth = 0
43
44let s:man_sect_arg = ""
45let s:man_find_arg = "-w"
46try
47  if !has("win32") && $OSTYPE !~ 'cygwin\|linux' && system('uname -s') =~ "SunOS" && system('uname -r') =~ "^5"
48    let s:man_sect_arg = "-s"
49    let s:man_find_arg = "-l"
50  endif
51catch /E145:/
52  " Ignore the error in restricted mode
53endtry
54
55func <SID>PreGetPage(cnt)
56  if a:cnt == 0
57    let old_isk = &iskeyword
58    setl iskeyword+=(,)
59    let str = expand("<cword>")
60    let &l:iskeyword = old_isk
61    let page = substitute(str, '(*\(\k\+\).*', '\1', '')
62    let sect = substitute(str, '\(\k\+\)(\([^()]*\)).*', '\2', '')
63    if match(sect, '^[0-9 ]\+$') == -1
64      let sect = ""
65    endif
66    if sect == page
67      let sect = ""
68    endif
69  else
70    let sect = a:cnt
71    let page = expand("<cword>")
72  endif
73  call s:GetPage(sect, page)
74endfunc
75
76func <SID>GetCmdArg(sect, page)
77  if a:sect == ''
78    return a:page
79  endif
80  return s:man_sect_arg.' '.a:sect.' '.a:page
81endfunc
82
83func <SID>FindPage(sect, page)
84  let where = system("/usr/bin/man ".s:man_find_arg.' '.s:GetCmdArg(a:sect, a:page))
85  if where !~ "^/"
86    if matchstr(where, " [^ ]*$") !~ "^ /"
87      return 0
88    endif
89  endif
90  return 1
91endfunc
92
93func <SID>GetPage(...)
94  if a:0 >= 2
95    let sect = a:1
96    let page = a:2
97  elseif a:0 >= 1
98    let sect = ""
99    let page = a:1
100  else
101    return
102  endif
103
104  " To support:	    nmap K :Man <cword>
105  if page == '<cword>'
106    let page = expand('<cword>')
107  endif
108
109  if sect != "" && s:FindPage(sect, page) == 0
110    let sect = ""
111  endif
112  if s:FindPage(sect, page) == 0
113    echo "\nCannot find a '".page."'."
114    return
115  endif
116  exec "let s:man_tag_buf_".s:man_tag_depth." = ".bufnr("%")
117  exec "let s:man_tag_lin_".s:man_tag_depth." = ".line(".")
118  exec "let s:man_tag_col_".s:man_tag_depth." = ".col(".")
119  let s:man_tag_depth = s:man_tag_depth + 1
120
121  " Use an existing "man" window if it exists, otherwise open a new one.
122  if &filetype != "man"
123    let thiswin = winnr()
124    exe "norm! \<C-W>b"
125    if winnr() > 1
126      exe "norm! " . thiswin . "\<C-W>w"
127      while 1
128	if &filetype == "man"
129	  break
130	endif
131	exe "norm! \<C-W>w"
132	if thiswin == winnr()
133	  break
134	endif
135      endwhile
136    endif
137    if &filetype != "man"
138      new
139      setl nonu fdc=0
140    endif
141  endif
142  silent exec "edit $HOME/".page.".".sect."~"
143  " Avoid warning for editing the dummy file twice
144  setl buftype=nofile noswapfile
145
146  setl ma
147  silent exec "norm 1GdG"
148  let $MANWIDTH = winwidth(0)
149  silent exec "r!/usr/bin/man ".s:GetCmdArg(sect, page)." | col -b"
150  " Remove blank lines from top and bottom.
151  while getline(1) =~ '^\s*$'
152    silent norm ggdd
153  endwhile
154  while getline('$') =~ '^\s*$'
155    silent norm Gdd
156  endwhile
157  1
158  setl ft=man nomod
159  setl bufhidden=hide
160  setl nobuflisted
161endfunc
162
163func <SID>PopPage()
164  if s:man_tag_depth > 0
165    let s:man_tag_depth = s:man_tag_depth - 1
166    exec "let s:man_tag_buf=s:man_tag_buf_".s:man_tag_depth
167    exec "let s:man_tag_lin=s:man_tag_lin_".s:man_tag_depth
168    exec "let s:man_tag_col=s:man_tag_col_".s:man_tag_depth
169    exec s:man_tag_buf."b"
170    exec s:man_tag_lin
171    exec "norm ".s:man_tag_col."|"
172    exec "unlet s:man_tag_buf_".s:man_tag_depth
173    exec "unlet s:man_tag_lin_".s:man_tag_depth
174    exec "unlet s:man_tag_col_".s:man_tag_depth
175    unlet s:man_tag_buf s:man_tag_lin s:man_tag_col
176  endif
177endfunc
178
179endif
180
181" vim: set sw=2:
182