dotfiles/nvim/.config/nvim/plugin/wiki.vim
Marty Oehme d96870eadc
[nvim] Add Zettelkasten movement
Can move through wiki by Zettel anchor IDs. Replaces standard wiki
movement. Zettel IDs do not care about the directory they are in, as
long as the ID is the same the Zettel can be located anywhere within the
wiki root directory.

Will need refinement and speed improvements in the future.
2020-05-26 22:35:42 +02:00

93 lines
3.1 KiB
VimL

" PLUGIN: wiki.vim
if $WIKIROOT ==? ""
let g:wiki_root = expand('~/documents/notes')
else
let g:wiki_root = $WIKIROOT
endif
" filetypes to automatically enable the plugin for, seems to take file endings
" rather than vim ft
let g:wiki_filetypes = ['md', 'mkd', 'markdown', 'wiki']
let g:wiki_mappings_use_defaults = 'global'
let g:wiki_list_todos = ['[ ]', '[x]']
" wiki automatic link creation
" add .md to the end of links by default
let g:wiki_link_extension = '.md'
" add a link in the format [descr](target) by default
" not in wiki format [[link|descr]]
let g:wiki_link_target_type = 'md'
" change file opening scheme of external wiki links
function! WikiFileOpen(...) abort dict
" use xdg-open for now -- can still customize if need be, see
" :help wiki-config -> g:wiki_file_open for an example
silent execute '!xdg-open' fnameescape(self.path) '&'
return 1
endfunction
let g:wiki_file_open = 'WikiFileOpen'
" Zettelkasten functionality
" Creates a Zettelkasten compatible unique datestamp
function s:Getdatestamp()
if !exists("*strftime")
:echoerr "Date Stamp creation needs strftime available on system!"
endif
return strftime("%y%m%d%H%M")
endfunction
command! Datestamp :echom s:Getdatestamp()
" Appends Zettelkasten timestamp to beginning of links
function! ZettelLink(text) abort
" lowercase and replace spaces with dashes (-) to make links uniform
let l:text=substitute(tolower(a:text), '\s\+', '-', 'g')
" prepend datestamp
let l:text=substitute(l:text, '^', s:Getdatestamp() . ' '. '\0', 'g')
return l:text
endfunction
" sets wiki.vim to automatically apply datestamp function to created links
let g:wiki_map_link_create = "ZettelLink"
" Returns the full path to the Zettel owning the anchor id passed in
function! s:GetZettelPath(anchor) abort
" match first 10-digit-beggining file ending with .md
" e.g. 1906061330 My example-Zettel.md
let l:tomatch='/' . trim(a:anchor) . ' .*\.md'
let l:notes=split(globpath(g:wiki_root, '**'), '\n')
let l:match=match(l:notes, l:tomatch)
if l:match == -1
return ""
else
return fnameescape(l:notes[l:match])
endif
endfunction
command! -nargs=1 ZettelOpen execute ":e " . s:GetZettelPath(<q-args>)
" Returns only the anchor id in a file name
" - returns empty string if nothing was found
function! s:ExtractAnchor(file) abort
return trim(matchstr(a:file, '[:/]\d\{10,14} '), ' \t\r:/')
endfunction
" Uses the Zettel Anchor ID instead of the whole link structure to traverse
" the whole Wiki directory from its root and opens first fitting Zettel
function! ZettelOpenAtCursor(...) abort
let l:link = wiki#link#get_at_cursor()
try
let l:zettel = s:GetZettelPath( s:ExtractAnchor(l:link.url) )
" fall back to normal link opening otherwise
if l:zettel ==? ""
call call(l:link.open, a:000, l:link)
else
execute ":e " . l:zettel
" call call(l:link.open, a:000, l:link)
endif
catch /E716:/
call wiki#link#toggle(l:link)
catch /E37:/
echoerr 'E37: Can''t open link before you''ve saved the current buffer.'
endtry
endfunction
command! ZettelOpenAtCursor :call ZettelOpenAtCursor()