new forum thread - file navigation
[ikiwiki.git] / doc / forum / navigation_of_wiki_pages_on_local_filesystem_with_vim.mdwn
1 I wrote a vim function to help me navigate the wiki when I'm editing it. It extends the 'gf' (goto file) functionality. Once installed, you place the cursor on a wiki page name and press 'gf' (without the quotes); if the file exists, it gets loaded.
2
3 This function takes into account the ikiwiki linking rules when deciding which file to go to.
4
5 let me know what you think
6
7 To enable this functionality, paste the code below in your `.vim/ftplugin/ikiwiki.vim` file
8
9     " returns the directory which can be considered the root of the wiki the
10     " current buffer belongs to, or an empty string if we are not inside an
11     " ikiwiki wiki
12     "
13     " NOTE: the root of the wiki is considered the first directory that contains a
14     " .ikiwiki folder, except $HOME/.ikiwiki (the usual ikiwiki libdir)
15     "
16     " if you can think of a better heuristic to get ikiwiki's root, let me know!
17     function! GetWikiRootDir()
18       let check_str = '%:p:h'
19       let pos_wiki_root = expand(check_str)
20       while pos_wiki_root != '/'
21         if isdirectory(pos_wiki_root . '/.ikiwiki') && pos_wiki_root != $HOME
22           return pos_wiki_root
23         endif
24         let check_str = check_str . ':h'
25         let pos_wiki_root = expand(check_str)
26       endwhile
27       if isdirectory('/.ikiwiki')
28         return '/'
29       endif
30       return ''
31     endfunction
32     
33     " This function searches for a .mdwn file (<a:name>.mdwn) using the ikiwiki
34     " WikiLink rules and returns its full path.
35     "
36     " The rules are the following
37     "
38     " if the filename starts with '/', use as base dir the root directory of the
39     " wiki
40     "
41     " if not:
42     "
43     " try first ./<bufname>/<a:name>.mdwn
44     " then for  ./<a:name>.mdwn
45     " then for  <root_of_wiki>/<a:name>.mdwn
46     "
47     " return the first one that exists
48     "
49     " the base path (. above) is the directory that contains the current buffer
50     "
51     function! FileForWikiLink(name)
52       let target_fname=a:name . ".mdwn"
53       let wikiroot_dir = GetWikiRootDir()
54       if match(target_fname, '^/') >= 0
55         return wikiroot_dir . target_fname
56       endif
57       let subdir_file = expand('%:p:r') . "/" . target_fname
58       let currdir_file = expand('%:p:h') . "/" . target_fname
59       let wikiroot_file = wikiroot_dir . "/" . target_fname
60       if filewritable(subdir_file)
61         return subdir_file
62       endif
63       if filewritable(currdir_file)
64         return currdir_file
65       endif
66       if filewritable(wikiroot_file)
67         return wikiroot_file
68       endif
69       return a:name
70     endfunction
71     
72     setlocal includeexpr=FileForWikiLink(v:fname)