" Vimball Archiver by Charles E. Campbell, Jr., Ph.D. UseVimball finish autoload/spinner/buffer.vim [[[1 12 function! spinner#buffer#next() bnext endfunction function! spinner#buffer#previous() bNext endfunction function! spinner#buffer#load() endfunction autoload/spinner/most_recently_edited.vim [[[1 175 function! spinner#most_recently_edited#next() call spinner#most_recently_edited#open_next_file(1) endfunction function! spinner#most_recently_edited#previous() call spinner#most_recently_edited#open_next_file(0) endfunction function! spinner#most_recently_edited#load() call spinner#most_recently_edited#MRU_LoadList() endfunction if has('unix') || has('macunix') let spinner#most_recently_edited#SPINNER_MRU_FILE = $HOME . '/.vim_spinner_mru_files' else let spinner#most_recently_edited#SPINNER_MRU_FILE = $VIM . '/_vim_spinner_mru_files' if has('win32') " MS-Windows if $USERPROFILE != '' let spinner#most_recently_edited#SPINNER_MRU_FILE = $USERPROFILE . '\_vim_spinner_mru_files' endif endif endif " Control to temporarily lock the MRU list. Used to prevent files from " getting added to the MRU list when the ':vimgrep' command is executed. let g:spinner#most_recently_edited#MRU_LIST_LOCKED = 0 " MRU_LoadList " Load the latest MRU file list from the MRU file function! spinner#most_recently_edited#MRU_LoadList() " Read the list from the MRU file. if filereadable(g:spinner#most_recently_edited#SPINNER_MRU_FILE) let g:spinner#most_recently_edited#MRU_FILES = readfile(g:spinner#most_recently_edited#SPINNER_MRU_FILE) if g:spinner#most_recently_edited#MRU_FILES[0] =~# '^\s*" Most recently edited files in Vim' " Generated by the previous version of the MRU plugin. " Discard the list. let g:spinner#most_recently_edited#MRU_FILES = [] elseif g:spinner#most_recently_edited#MRU_FILES[0] =~# '^#' " Remove the comment line call remove(g:spinner#most_recently_edited#MRU_FILES, 0) else " Unsupported format let g:spinner#most_recently_edited#MRU_FILES = [] endif else let g:spinner#most_recently_edited#MRU_FILES = [] endif endfunction " MRU_SaveList " Save the MRU list to the file function! spinner#most_recently_edited#MRU_SaveList() let l = [] call add(l, '# Most recently edited files in Vim') call extend(l, g:spinner#most_recently_edited#MRU_FILES) call writefile(l, g:spinner#most_recently_edited#SPINNER_MRU_FILE) endfunction " MRU_AddFile " Add a file to the MRU file list function! spinner#most_recently_edited#MRU_AddFile(acmd_bufnr) if g:spinner#most_recently_edited#MRU_LIST_LOCKED " MRU list is currently locked return endif " Get the full path to the filename let fname = fnamemodify(bufname(a:acmd_bufnr + 0), ':p') if fname == '' return endif " Skip temporary buffer with buftype set if &buftype != '' return endif " If the filename is not already present in the MRU list and is not " readable then ignore it let idx = index(g:spinner#most_recently_edited#MRU_FILES, fname) if idx == -1 if !filereadable(fname) " File is not readable and is not in the MRU list return endif endif " Load the latest MRU file list call spinner#most_recently_edited#MRU_LoadList() " Remove the new file name from the existing MRU list (if already present) call filter(g:spinner#most_recently_edited#MRU_FILES, 'v:val !=# fname') " Add the new file list to the beginning of the updated old file list call insert(g:spinner#most_recently_edited#MRU_FILES, fname, 0) " Trim the list if len(g:spinner#most_recently_edited#MRU_FILES) > 10 call remove(g:spinner#most_recently_edited#MRU_FILES, 10, -1) endif " Save the updated MRU list call spinner#most_recently_edited#MRU_SaveList() endfunction " Autocommands to detect the most recently used files autocmd BufRead * call spinner#most_recently_edited#MRU_AddFile(expand('')) autocmd BufNewFile * call spinner#most_recently_edited#MRU_AddFile(expand('')) autocmd BufWritePost * call spinner#most_recently_edited#MRU_AddFile(expand('')) " The ':vimgrep' command adds all the files searched to the buffer list. " This also modifies the MRU list, even though the user didn't edit the " files. Use the following autocmds to prevent this. autocmd QuickFixCmdPre *vimgrep* let g:spinner#most_recently_edited#MRU_LIST_LOCKED = 1 autocmd QuickFixCmdPost *vimgrep* let g:spinner#most_recently_edited#MRU_LIST_LOCKED = 0 func! spinner#most_recently_edited#get_idx_of_list(lis, elem) let i = 0 while i < len(a:lis) if a:lis[i] ==# a:elem return i endif let i = i + 1 endwhile throw "not found" endfunc func! spinner#most_recently_edited#sort_compare(i, j) " alphabetically return a:i > a:j endfunc func! spinner#most_recently_edited#get_next_idx(files, advance, cnt) try " get current file idx let tailed = map(copy(a:files), 'fnamemodify(v:val, ":t")') let idx = spinner#most_recently_edited#get_idx_of_list(tailed, expand('%:t')) " move to next or previous let idx = a:advance ? idx + a:cnt : idx - a:cnt catch /^not found$/ " open the first file. let idx = 0 endtry return idx endfunc func! spinner#most_recently_edited#open_next_file(advance) let files = g:spinner#most_recently_edited#MRU_FILES if empty(files) | return | endif let idx = spinner#most_recently_edited#get_next_idx(files, a:advance, v:count1) if 0 <= idx && idx < len(files) " can access to files[idx] execute 'edit ' . fnameescape(files[idx]) else " wrap around if idx < 0 " fortunately recent LL languages support negative index :) let idx = -(abs(idx) % len(files)) " But if you want to access to 'real' index: " if idx != 0 " let idx = len(files) + idx " endif else let idx = idx % len(files) endif execute 'edit ' . fnameescape(files[idx]) endif endfunc autoload/spinner/quickfix.vim [[[1 12 function! spinner#quickfix#next() cnext endfunction function! spinner#quickfix#previous() cNext endfunction function! spinner#quickfix#load() endfunction autoload/spinner/quickfix_file.vim [[[1 12 function! spinner#quickfix_file#next() cnfile endfunction function! spinner#quickfix_file#previous() cNfile endfunction function! spinner#quickfix_file#load() endfunction autoload/spinner/same_directory_file.vim [[[1 116 function! spinner#same_directory_file#next() call spinner#same_directory_file#open_next_file(1) endfunction function! spinner#same_directory_file#previous() call spinner#same_directory_file#open_next_file(0) endfunction function! spinner#same_directory_file#load() let g:spinner#same_directory_file#exeextmap = {} if exists('$PATHEXT') let l:list = split($PATHEXT, ';') for l:i in l:list let g:spinner#same_directory_file#exeextmap[l:i] = 1 endfor endif endfunction func! spinner#same_directory_file#warn(msg) echohl WarningMsg echomsg a:msg echohl None endfunc func! spinner#same_directory_file#get_idx_of_list(lis, elem) let l:i = 0 while l:i < len(a:lis) if a:lis[l:i] ==# a:elem return l:i endif let l:i = l:i + 1 endwhile throw "not found" endfunc func! spinner#same_directory_file#glob_list(expr) let l:files = split(glob(a:expr), '\n') " get rid of '.' and '..' call filter(l:files, 'fnamemodify(v:val, ":t") !=# "." && fnamemodify(v:val, ":t") !=# ".."') return l:files endfunc func! spinner#same_directory_file#sort_compare(i, j) " alphabetically return a:i > a:j endfunc func! spinner#same_directory_file#get_files_list(...) " get files list let l:glob_expr = a:0 == 0 ? '*' : a:1 let l:globed = spinner#same_directory_file#glob_list(expand('%:p:h') . '/' . l:glob_expr) let l:files = [] for l:i in l:globed if isdirectory(l:i) continue endif if ! filereadable(l:i) continue endif let l:ext = fnamemodify(l:i, ":e") if has_key(g:spinner#same_directory_file#exeextmap, l:ext) continue endif call add(l:files, l:i) endfor return sort(l:files, 'spinner#same_directory_file#sort_compare') endfunc func! spinner#same_directory_file#get_next_idx(files, advance, cnt) try " get current file idx let l:tailed = map(copy(a:files), 'fnamemodify(v:val, ":t")') let l:idx = spinner#same_directory_file#get_idx_of_list(l:tailed, expand('%:t')) " move to next or previous let l:idx = a:advance ? l:idx + a:cnt : l:idx - a:cnt catch /^not found$/ " open the first file. let l:idx = 0 endtry return l:idx endfunc func! spinner#same_directory_file#open_next_file(advance) if expand('%') ==# '' return spinner#same_directory_file#warn("current file is empty.") endif let l:files = spinner#same_directory_file#get_files_list() if empty(l:files) | return | endif let l:idx = spinner#same_directory_file#get_next_idx(l:files, a:advance, v:count1) if 0 <= l:idx && l:idx < len(l:files) " can access to files[l:idx] execute 'edit ' . fnameescape(l:files[l:idx]) else " wrap around if l:idx < 0 " fortunately recent LL languages support negative index :) let l:idx = -(abs(l:idx) % len(l:files)) " But if you want to access to 'real' index: " if l:idx != 0 " let l:idx = len(l:files) + l:idx " endif else let l:idx = l:idx % len(l:files) endif execute 'edit ' . fnameescape(l:files[l:idx]) endif endfunc autoload/spinner/tab.vim [[[1 12 function! spinner#tab#next() tabnext endfunction function! spinner#tab#previous() tabNext endfunction function! spinner#tab#load() endfunction autoload/spinner/window.vim [[[1 12 function! spinner#window#next() wincmd w endfunction function! spinner#window#previous() wincmd W endfunction function! spinner#window#load() endfunction doc/spinner.txt [[[1 157 *spinner.txt* fast buffer/file/tab/... switching plugin with only 3 keys. Author: OMI TAKU *spinner-author* URL http://nanasi.jp/ email mail@nanasi.jp INTRODUCTION *spinner* a basic idea is easy pressable key, and quickly switchable search type . ** ** ** BASIC USAGE *spinner-mapping* *spinner-basic-usage* Default defined key map is mapping action ~ open next item . open previous item . switch spinner.vim search mode . spinner.vim search mode is switching, when you press . Defined search mode is 1. open next/previous buffer (initial) . 2. open next/previous file in currently opened file directory . 3. open next/previous most recently edited file (last 10 files) . 4. open next/previous tab . 5. open next/previous window . 6. open next/previous quickfix line . 7. open next/previous quickfix file . SPINNER SEARCH MODE DETAILS *spinner-search-mode* 1.open next/previous buffer (initial) . *spinner-buffer* open next buffer. open previous buffer. same with :bnext, :bNext . *spinner-same_directory_file* 2.open next/previous file in currently opened file directory . open alphabetically next file. open alphabetically previous file . opening files are searched in currently opened file directory. current test version use code from nextfile : open the next or previous file (vimscript #2605) *spinner-most_recently_edited* 3.open next/previous most recently edited file (last 10 files) . open alphabetically next file. open alphabetically previous file . recently edited file path are stored at openinig file (limit 10 item). stored file is placed at $HOME/.vim_spinner_mru_files , or $VIM/.vim_spinner_mru_files , or $USERPROFILE/_vim_spinner_mru_files . current test version use code from mru.vim : Plugin to manage Most Recently Used (MRU) files (vimscript #521) 4.open next/previous tab . *spinner-tab* go to next tab. go to previous tab. same with :tabnext, :tabNext . 5.open next/previous window . *spinner-window* move cursor to next splitted window. move cursor to previous splitted window. 6.open next/previous quickfix line . *spinner-quickfix* go to next error in quickfix list. go to previous error in quickfix list. same with :cnext, :cNext . 7.open next/previous quickfix file . *spinner-quickfix_file* go to next error file in quickfix list. go to previous error file in quickfix list. same with :cnfile, :cNfile . OTHER USAGE *spinner-other-usage* switch search mode with number. mapping action ~ 1 set switch spinner.vim mode to buffer type. 2 set switch spinner.vim mode to same_directory_file type. 3 set switch spinner.vim mode to most_recently_edited type. 4 set switch spinner.vim mode to tab type. 5 set switch spinner.vim mode to window type. 6 set switch spinner.vim mode to quickfix type. 7 set switch spinner.vim mode to quickfix_file type. this key map display current spinner search mode. ** ** mapping action ~ display current spinner mode . display current spinner mode . CONFIGURATIONS *spinner-configurations* *g:spinner_nextitem_key* *g:spinner_previousitem_key* *g:spinner_switchmode_key* *g:spinner_displaymode_key* ACTION KEY MAP *spinner-configurations-action-key* > let g:spinner_nextitem_key = {mapping} let g:spinner_previousitem_key = {mapping} let g:spinner_switchmode_key = {mapping} let g:spinner_displaymode_key = {mapping} < for example, > let g:spinner_nextitem_key = ',n' let g:spinner_previousitem_key = ',p' let g:spinner_switchmode_key = ',s' let g:spinner_displaymode_key = ',d' < caution!! default mapping is for GUI. default mapping do not work on Windows DOS prompt, PowerShell, Mac OSX Terminal, and all that. *g:spinner_initial_search_type* INITIAL SEARCH TYPE *spinner-configurations-initial-search-mode* > let g:spinner_initial_search_type = {seach type number} < for example, > let g:spinner_initial_search_type = 2 < number mode ~ 1 buffer (default) 2 same_directory_file 3 most_recently_edited 4 tab 5 window 6 quickfix 7 quickfix_file SOURCE REPOSITORY *spinner-project* http://code.google.com/p/spinner-vim-plugin/ CURRENT ISSUE *spinner-issue* - In "most_recently_edited" mode, "next file" command can only open last file. because history managed file will be updated when opening new file. INSTALL DETAILS *spinner-install* 1. open spinner-vim-plugin.vba with Vim editor. 2. extract spinner-vim-plugin with :source command. > source % < HISTORY *spinner-history* 0.5 2009/12/02 19:00:00 - Initial upload. 0.5.1 2009/12/03 20:20:00 - update some displaying messages. - add spinner.vim help document. - fix most_recently_edited mode initialize bug. 0.5.2 2009/12/09 18:00:00 - update plugins loading logic. - same_directory_file mode will not open $PATHEXT extension file. 1.0 2009/12/15 17:00:00 - to vimball archive. vim:tw=78:ts=8:ft=help:norl: plugin/spinner.vim [[[1 133 if &cp || exists("g:loaded_spinner") finish endif let g:loaded_spinner = 1 let s:save_cpo = &cpo set cpo&vim let s:modes = [ \ 'buffer', \ 'same_directory_file', \ 'most_recently_edited', \ 'tab', \ 'window', \ 'quickfix', \ 'quickfix_file', \ ] let s:mode_count = len(s:modes) " initial type if exists('g:spinner_initial_search_type') let s:current_mode = g:spinner_initial_search_type - 1 else let s:current_mode = 0 endif " mapping if exists('g:spinner_nextitem_key') let s:nextitem_map = g:spinner_nextitem_key else let s:nextitem_map = '' endif if exists('g:spinner_previousitem_key') let s:previousitem_map = g:spinner_previousitem_key else let s:previousitem_map = '' endif if exists('g:spinner_switchmode_key') let s:switchmode_map = g:spinner_switchmode_key else let s:switchmode_map = '' endif if exists('g:spinner_displaymode_key') let s:displaymode_maps = [ g:spinner_displaymode_key ] else let s:displaymode_maps = [ \ '', \ '', \ '', \ ] endif let s:next_cmd = "" let s:previous_cmd = "" " set custom mapping execute 'nnoremap ' . s:nextitem_map . ' :call g:NextSpinnerItem()' execute 'nnoremap ' . s:previousitem_map . ' :call g:PreviousSpinnerItem()' execute 'nnoremap ' . s:switchmode_map . ' :call g:SwitchSpinnerMode(v:count)' for i in s:displaymode_maps execute 'nnoremap ' . i . ' :call g:DisplayCurrentSpinnerMode()' endfor function! g:SwitchSpinnerMode(count) if a:count > 0 let s:current_mode = a:count - 1 else let s:current_mode += 1 endif if s:current_mode < s:mode_count else let s:current_mode = 0 endif call s:SwitchSpinnerModeTo(s:current_mode) echohl None | echo 'switch spinner mode to [' . s:modes[s:current_mode] . '].' | echohl None endfunction function! s:SwitchSpinnerModeTo(mode) let s:next_cmd = 'call spinner#' . s:modes[a:mode] . '#next()' let s:previous_cmd = 'call spinner#' . s:modes[a:mode] . '#previous()' endfunction function! g:NextSpinnerItem() execute s:next_cmd endfunction function! g:PreviousSpinnerItem() execute s:previous_cmd endfunction function! g:CurrentSpinnerMode() return s:modes[s:current_mode] endfunction function! g:DisplayCurrentSpinnerMode() echohl None | echo 'current spinner mode [' . s:modes[s:current_mode] . '].' | echohl None endfunction function! s:InitializeSpinner() call s:SwitchSpinnerModeTo(s:current_mode) " load plugins for i in s:modes execute 'call spinner#' . i . '#load()' endfor endfunction call s:InitializeSpinner() let &cpo = s:save_cpo finish ============================================================================== spinner.vim : fast buffer/file/tab/... switching plugin with only 3 keys. ------------------------------------------------------------------------------ $VIMRUNTIMEPATH/plugin/spinner.vim $VIMRUNTIMEPATH/doc/spinner.txt $VIMRUNTIMEPATH/autoload/spinner/buffer.vim $VIMRUNTIMEPATH/autoload/spinner/most_recently_edited.vim $VIMRUNTIMEPATH/autoload/spinner/quickfix.vim $VIMRUNTIMEPATH/autoload/spinner/quickfix_file.vim $VIMRUNTIMEPATH/autoload/spinner/same_directory_file.vim $VIMRUNTIMEPATH/autoload/spinner/tab.vim $VIMRUNTIMEPATH/autoload/spinner/window.vim ============================================================================== author : OMI TAKU url : http://nanasi.jp/ email : mail@nanasi.jp version : 2009/12/15 17:00:00 ============================================================================== " vim: set et ft=vim nowrap :