From 24830b03ec3101e482f684de09d293ab97afbaed Mon Sep 17 00:00:00 2001 From: Tobias Manske Date: Sat, 1 Sep 2018 11:00:23 +0200 Subject: [PATCH] VIM: Reinstall NERDTree Nerdtree is a rather slow, but extremely useful plugin. So I made the decission to reinstall it, but don't launch it on startup but with a keybinding. Signed-off-by: Tobias Manske --- .gitmodules | 3 + vim/config/plugin.vim | 13 + .../nerdtree/.github/ISSUE_TEMPLATE.md | 28 + vim/plugins/nerdtree/.gitignore | 3 + vim/plugins/nerdtree/CHANGELOG | 179 +++ vim/plugins/nerdtree/LICENCE | 13 + vim/plugins/nerdtree/README.markdown | 96 ++ vim/plugins/nerdtree/autoload/nerdtree.vim | 200 +++ .../nerdtree/autoload/nerdtree/ui_glue.vim | 661 +++++++++ vim/plugins/nerdtree/doc/NERDTree.txt | 1309 +++++++++++++++++ .../nerdtree_plugin/exec_menuitem.vim | 40 + .../nerdtree/nerdtree_plugin/fs_menu.vim | 365 +++++ vim/plugins/nerdtree/plugin/NERD_tree.vim | 219 +++ vim/plugins/nerdtree/screenshot.png | Bin 0 -> 87896 bytes vim/plugins/nerdtree/syntax/nerdtree.vim | 82 ++ 15 files changed, 3211 insertions(+) create mode 100644 vim/plugins/nerdtree/.github/ISSUE_TEMPLATE.md create mode 100644 vim/plugins/nerdtree/.gitignore create mode 100644 vim/plugins/nerdtree/CHANGELOG create mode 100644 vim/plugins/nerdtree/LICENCE create mode 100644 vim/plugins/nerdtree/README.markdown create mode 100644 vim/plugins/nerdtree/autoload/nerdtree.vim create mode 100644 vim/plugins/nerdtree/autoload/nerdtree/ui_glue.vim create mode 100644 vim/plugins/nerdtree/doc/NERDTree.txt create mode 100644 vim/plugins/nerdtree/nerdtree_plugin/exec_menuitem.vim create mode 100644 vim/plugins/nerdtree/nerdtree_plugin/fs_menu.vim create mode 100644 vim/plugins/nerdtree/plugin/NERD_tree.vim create mode 100644 vim/plugins/nerdtree/screenshot.png create mode 100644 vim/plugins/nerdtree/syntax/nerdtree.vim diff --git a/.gitmodules b/.gitmodules index 08b8a43..b530002 100644 --- a/.gitmodules +++ b/.gitmodules @@ -154,3 +154,6 @@ [submodule "vim/plugins/vim-window-resize-easy"] path = vim/plugins/vim-window-resize-easy url = https://github.com/roxma/vim-window-resize-easy +[submodule "vim/plugins/nerdtree"] + path = vim/plugins/nerdtree + url = https://github.com/scrooloose/nerdtree diff --git a/vim/config/plugin.vim b/vim/config/plugin.vim index 0b5d53d..f84daa3 100644 --- a/vim/config/plugin.vim +++ b/vim/config/plugin.vim @@ -41,6 +41,19 @@ let g:NERDCommentEmptyLines = 1 let g:NERDTrimTrailingWhitespace = 1 +" NerdTree +let NERDTreeMinimalUI = 1 +let g:NERDTreeDirArrowExpandable = '🗀' +let g:NERDTreeDirArrowCollapsible = '🗁' +let g:NERDTreeHighlightFolders = 1 +let g:NERDTreeHighlightFoldersFullName = 1 + +" autoclose if nerdtree is last open window +augroup NERDTree + autocmd! + autocmd bufenter * if (winnr("$") == 1 && exists("b:NERDTree") && b:NERDTree.isTabTree()) | q | endif +augroup end + " PyMode let g:pymode_lint = 0 let g:pymode_syntax = 1 diff --git a/vim/plugins/nerdtree/.github/ISSUE_TEMPLATE.md b/vim/plugins/nerdtree/.github/ISSUE_TEMPLATE.md new file mode 100644 index 0000000..c3ca5ef --- /dev/null +++ b/vim/plugins/nerdtree/.github/ISSUE_TEMPLATE.md @@ -0,0 +1,28 @@ + + +### Environment + + +* Operating System: +* Vim version `:version`: +* NERDTree version `git rev-parse --short HEAD`: +* NERDTree settings applied in your vimrc, if any: + ```vim + ``` + +### Process + + +1. + +### Current Result + + +### Expected Result + + +### Screenshot(s) + +### Possible Fix + + diff --git a/vim/plugins/nerdtree/.gitignore b/vim/plugins/nerdtree/.gitignore new file mode 100644 index 0000000..3698c0e --- /dev/null +++ b/vim/plugins/nerdtree/.gitignore @@ -0,0 +1,3 @@ +*~ +*.swp +tags diff --git a/vim/plugins/nerdtree/CHANGELOG b/vim/plugins/nerdtree/CHANGELOG new file mode 100644 index 0000000..6dac46d --- /dev/null +++ b/vim/plugins/nerdtree/CHANGELOG @@ -0,0 +1,179 @@ +Next + - Fix broken "t" and "T" mappings, tabs now open at end (lifecrisis) #759 + - Update doc with already existing mapping variables (asnr) #699 + - Fix the broken g:NERDTreeBookmarksSort setting (lifecrisis) #696 + - Correct NERDTreeIgnore pattern in doc (cntoplolicon) #648 + - Remove empty segments when splitting path (sooth-sayer) #574 + - Suppress autocmds less agressively (wincent) #578 #691 + - Add an Issues template to ask for more info initially. + - Fix markdown headers in readme (josephfrazier) #676 + - Don't touch @o and @h registers when rendering + - Fix bug with files and directories with dollar signs (alegen) #649 + - Reuse/reopen existing window trees where possible #244 + - Remove NERDTree.previousBuf() + - Change color of arrow (Leeiio) #630 + - Improved a tip in README.markdown (ggicci) #628 + - Shorten delete confimration of empty directory to 'y' (mikeperri) #530 + - Fix API call to open directory tree in window (devm33) #533 + - Change default arrows on non-Windows platforms (gwilk) #546 + - Update to README - combine cd and git clone (zwhitchcox) #584 + - Update to README - Tip: start NERDTree when vim starts (therealplato) #593 + - Escape filename when moving an open buffer (zacharyvoase) #595 + - Fixed incorrect :helptags command in README (curran) #619 + - Fixed incomplete escaping of folder arrows (adityanatraj) #548 + - Added NERDTreeCascadeSingleChildDir option (juanibiapina) #558 + - Replace strchars() with backward compatible workaround. + - Add support for copy command in Windows (SkylerLipthay) #231 + - Fixed typo in README.markdown - :Helptags -> :helptags + - Rename "primary" and "secondary" trees to "tab" and "window" trees. + - Move a bunch of buffer level variables into the NERDTree and UI classes. + - Display cascading dirs on one line to save vertical/horizontal space (@matt-gardner: brainstorming/testing) + - Remove the old style UI - Remove 'NERDTreeDirArrows' option. + - On windows default to + and ~ for expand/collapse directory symbols. + - Lots more refactoring. Move a bunch of b: level vars into b:NERDTree and friends. + +5.0.0 + - Refactor the code significantly: + * Break the classes out into their own files. + * Make the majority of the code OO - previously large parts were + effectively a tangle of "global" methods. + - Add an API to assign flags to nodes. This allows VCS plugins like + https://github.com/Xuyuanp/nerdtree-git-plugin to exist. Thanks to + Xuyuanp for helping design/test/build said API. + - add 'scope' argument to the key map API see :help NERDTreeAddKeyMap() + - add magic [[dir]] and [[file]] flags to NERDTreeIgnore + - add support for custom path filters. See :help NERDTreeAddPathFilter() + - add path listener API. See :help NERDTreePathListenerAPI. + - expand the fs menu functionality to list file properties (PhilRunninger, + apbarrero, JESii) + - make bookmarks work with `~` home shortcuts (hiberabyss) + - show OSX specific fsmenu options in regular vim on mac (evindor) + - make dir arrow icons configurable (PickRelated) + - optimise node sorting performance when opening large dirs (vtsang) + - make the root note render prettier by truncating it at a path slash (gcmt) + - remove NERDChristmasTree option - its always christmas now + - add "cascade" open and closing for dirs containing only another single + dir. See :help NERDTreeCascadeOpenSingleChildDir (pendulm) + + Many other fixes, doc updates and contributions from: + actionshrimp + SchDen + egalpin + cperl82 - many small fixes + toiffel + WoLpH + handcraftedbits + devmanhinton + xiaodili + zhangoose + gastropoda + mixvin + alvan + lucascaton + kelaban + shanesmith + staeff + pendulm + stephenprater + franksort + agrussellknives + AndrewRadev + Twinside + +4.2.0 + - Add NERDTreeDirArrows option to make the UI use pretty arrow chars + instead of the old +~| chars to define the tree structure (sickill) + - shift the syntax highlighting out into its own syntax file (gnap) + - add some mac specific options to the filesystem menu - for macvim + only (andersonfreitas) + - Add NERDTreeMinimalUI option to remove some non functional parts of the + nerdtree ui (camthompson) + - tweak the behaviour of :NERDTreeFind - see :help :NERDTreeFind for the + new behaviour (benjamingeiger) + - if no name is given to :Bookmark, make it default to the name of the + target file/dir (minyoung) + - use 'file' completion when doing copying, create, and move + operations (EvanDotPro) + - lots of misc bug fixes (paddyoloughlin, sdewald, camthompson, Vitaly + Bogdanov, AndrewRadev, mathias, scottstvnsn, kml, wycats, me RAWR!) + +4.1.0 + features: + - NERDTreeFind to reveal the node for the current buffer in the tree, + see |NERDTreeFind|. This effectively merges the FindInNERDTree plugin (by + Doug McInnes) into the script. + - make NERDTreeQuitOnOpen apply to the t/T keymaps too. Thanks to Stefan + Ritter and Rémi Prévost. + - truncate the root node if wider than the tree window. Thanks to Victor + Gonzalez. + + bugfixes: + - really fix window state restoring + - fix some win32 path escaping issues. Thanks to Stephan Baumeister, Ricky, + jfilip1024, and Chris Chambers + +4.0.0 + - add a new programmable menu system (see :help NERDTreeMenu). + - add new APIs to add menus/menu-items to the menu system as well as + custom key mappings to the NERD tree buffer (see :help NERDTreeAPI). + - removed the old API functions + - added a mapping to maximize/restore the size of nerd tree window, thanks + to Guillaume Duranceau for the patch. See :help NERDTree-A for details. + + - fix a bug where secondary nerd trees (netrw hijacked trees) and + NERDTreeQuitOnOpen didnt play nicely, thanks to Curtis Harvey. + - fix a bug where the script ignored directories whose name ended in a dot, + thanks to Aggelos Orfanakos for the patch. + - fix a bug when using the x mapping on the tree root, thanks to Bryan + Venteicher for the patch. + - fix a bug where the cursor position/window size of the nerd tree buffer + wasnt being stored on closing the window, thanks to Richard Hart. + - fix a bug where NERDTreeMirror would mirror the wrong tree + +3.1.1 + - fix a bug where a non-listed no-name buffer was getting created every + time the tree windows was created, thanks to Derek Wyatt and owen1 + - make behave the same as the 'o' mapping + - some helptag fixes in the doc, thanks strull + - fix a bug when using :set nohidden and opening a file where the previous + buf was modified. Thanks iElectric + - other minor fixes + +3.1.0 + New features: + - add mappings to open files in a vsplit, see :help NERDTree-s and :help + NERDTree-gs + - make the statusline for the nerd tree window default to something + hopefully more useful. See :help 'NERDTreeStatusline' + Bugfixes: + - make the hijack netrw functionality work when vim is started with "vim + " (thanks to Alf Mikula for the patch). + - fix a bug where the CWD wasnt being changed for some operations even when + NERDTreeChDirMode==2 (thanks to Lucas S. Buchala) + - add -bar to all the nerd tree :commands so they can chain with other + :commands (thanks to tpope) + - fix bugs when ignorecase was set (thanks to nach) + - fix a bug with the relative path code (thanks to nach) + - fix a bug where doing a :cd would cause :NERDTreeToggle to fail (thanks nach) + + +3.0.1 + Bugfixes: + - fix bugs with :NERDTreeToggle and :NERDTreeMirror when 'hidden + was not set + - fix a bug where :NERDTree would fail if was relative and + didnt start with a ./ or ../ Thanks to James Kanze. + - make the q mapping work with secondary (:e style) trees, + thanks to jamessan + - fix a bunch of small bugs with secondary trees + + More insane refactoring. + +3.0.0 + - hijack netrw so that doing an :edit will put a NERD tree in + the window rather than a netrw browser. See :help 'NERDTreeHijackNetrw' + - allow sharing of trees across tabs, see :help :NERDTreeMirror + - remove "top" and "bottom" as valid settings for NERDTreeWinPos + - change the '' mapping to 'i' + - change the 'H' mapping to 'I' + - lots of refactoring diff --git a/vim/plugins/nerdtree/LICENCE b/vim/plugins/nerdtree/LICENCE new file mode 100644 index 0000000..8b1a9d8 --- /dev/null +++ b/vim/plugins/nerdtree/LICENCE @@ -0,0 +1,13 @@ + DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE + Version 2, December 2004 + +Copyright (C) 2004 Sam Hocevar + +Everyone is permitted to copy and distribute verbatim or modified +copies of this license document, and changing it is allowed as long +as the name is changed. + + DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. You just DO WHAT THE FUCK YOU WANT TO. diff --git a/vim/plugins/nerdtree/README.markdown b/vim/plugins/nerdtree/README.markdown new file mode 100644 index 0000000..6efeb0b --- /dev/null +++ b/vim/plugins/nerdtree/README.markdown @@ -0,0 +1,96 @@ +The NERDTree +============= + +Introduction +------------ + +The NERDTree is a file system explorer for the Vim editor. Using this plugin, +users can visually browse complex directory hierarchies, quickly open files for +reading or editing, and perform basic file system operations. + +This plugin can also be extended with custom mappings using a special API. The +details of this API and of other NERDTree features are described in the +included documentation. + +![NERDTree Screenshot](https://github.com/scrooloose/nerdtree/raw/master/screenshot.png) + +Installation +------------ + +#### [pathogen.vim](https://github.com/tpope/vim-pathogen) + + git clone https://github.com/scrooloose/nerdtree.git ~/.vim/bundle/nerdtree + +Then reload Vim, run `:helptags ~/.vim/bundle/nerdtree/doc/` or `:Helptags`, and check out `:help NERDTree.txt`. + + +#### [apt-vim](https://github.com/egalpin/apt-vim) + + apt-vim install -y https://github.com/scrooloose/nerdtree.git + +F.A.Q. +------ + +> Is there any support for `git` flags? + +Yes, install [nerdtree-git-plugin](https://github.com/Xuyuanp/nerdtree-git-plugin). + +--- + +> Can I have the nerdtree on every tab automatically? + +Nope. If this is something you want then chances are you aren't using tabs and +buffers as they were intended to be used. Read this +http://stackoverflow.com/questions/102384/using-vims-tabs-like-buffers + +If you are interested in this behaviour then consider [vim-nerdtree-tabs](https://github.com/jistr/vim-nerdtree-tabs) + +--- +> How can I open a NERDTree automatically when vim starts up? + +Stick this in your vimrc: `autocmd vimenter * NERDTree` + +--- +> How can I open a NERDTree automatically when vim starts up if no files were specified? + +Stick this in your vimrc: + + autocmd StdinReadPre * let s:std_in=1 + autocmd VimEnter * if argc() == 0 && !exists("s:std_in") | NERDTree | endif + +Note: Now start vim with plain `vim`, not `vim .` + +--- +> How can I open NERDTree automatically when vim starts up on opening a directory? + + autocmd StdinReadPre * let s:std_in=1 + autocmd VimEnter * if argc() == 1 && isdirectory(argv()[0]) && !exists("s:std_in") | exe 'NERDTree' argv()[0] | wincmd p | ene | endif + +This window is tab-specific, meaning it's used by all windows in the tab. This trick also prevents NERDTree from hiding when first selecting a file. + +--- +> How can I map a specific key or shortcut to open NERDTree? + +Stick this in your vimrc to open NERDTree with `Ctrl+n` (you can set whatever key you want): + + map :NERDTreeToggle + +--- +> How can I close vim if the only window left open is a NERDTree? + +Stick this in your vimrc: + + autocmd bufenter * if (winnr("$") == 1 && exists("b:NERDTree") && b:NERDTree.isTabTree()) | q | endif + +--- +> Can I have different highlighting for different file extensions? + +See here: https://github.com/scrooloose/nerdtree/issues/433#issuecomment-92590696 + +--- +> How can I change default arrows? + +Use these variables in your vimrc. Note that below are default arrow symbols + + let g:NERDTreeDirArrowExpandable = '▸' + let g:NERDTreeDirArrowCollapsible = '▾' diff --git a/vim/plugins/nerdtree/autoload/nerdtree.vim b/vim/plugins/nerdtree/autoload/nerdtree.vim new file mode 100644 index 0000000..bdf3deb --- /dev/null +++ b/vim/plugins/nerdtree/autoload/nerdtree.vim @@ -0,0 +1,200 @@ +if exists("g:loaded_nerdtree_autoload") + finish +endif +let g:loaded_nerdtree_autoload = 1 + +function! nerdtree#version() + return '5.0.0' +endfunction + +" SECTION: General Functions {{{1 +"============================================================ + +"FUNCTION: nerdtree#checkForBrowse(dir) {{{2 +"inits a window tree in the current buffer if appropriate +function! nerdtree#checkForBrowse(dir) + if !isdirectory(a:dir) + return + endif + + if s:reuseWin(a:dir) + return + endif + + call g:NERDTreeCreator.CreateWindowTree(a:dir) +endfunction + +"FUNCTION: s:reuseWin(dir) {{{2 +"finds a NERDTree buffer with root of dir, and opens it. +function! s:reuseWin(dir) abort + let path = g:NERDTreePath.New(fnamemodify(a:dir, ":p")) + + for i in range(1, bufnr("$")) + unlet! nt + let nt = getbufvar(i, "NERDTree") + if empty(nt) + continue + endif + + if nt.isWinTree() && nt.root.path.equals(path) + call nt.setPreviousBuf(bufnr("#")) + exec "buffer " . i + return 1 + endif + endfor + + return 0 +endfunction + +" FUNCTION: nerdtree#completeBookmarks(A,L,P) {{{2 +" completion function for the bookmark commands +function! nerdtree#completeBookmarks(A,L,P) + return filter(g:NERDTreeBookmark.BookmarkNames(), 'v:val =~# "^' . a:A . '"') +endfunction + +"FUNCTION: nerdtree#compareNodes(dir) {{{2 +function! nerdtree#compareNodes(n1, n2) + return a:n1.path.compareTo(a:n2.path) +endfunction + +"FUNCTION: nerdtree#compareNodesBySortKey(n1, n2) {{{2 +function! nerdtree#compareNodesBySortKey(n1, n2) + let sortKey1 = a:n1.path.getSortKey() + let sortKey2 = a:n2.path.getSortKey() + let i = 0 + while i < min([len(sortKey1), len(sortKey2)]) + " Compare chunks upto common length. + " If chunks have different type, the one which has + " integer type is the lesser. + if type(sortKey1[i]) == type(sortKey2[i]) + if sortKey1[i] <# sortKey2[i] + return - 1 + elseif sortKey1[i] ># sortKey2[i] + return 1 + endif + elseif type(sortKey1[i]) == v:t_number + return -1 + elseif type(sortKey2[i]) == v:t_number + return 1 + endif + let i = i + 1 + endwhile + + " Keys are identical upto common length. + " The key which has smaller chunks is the lesser one. + if len(sortKey1) < len(sortKey2) + return -1 + elseif len(sortKey1) > len(sortKey2) + return 1 + else + return 0 + endif +endfunction + +" FUNCTION: nerdtree#deprecated(func, [msg]) {{{2 +" Issue a deprecation warning for a:func. If a second arg is given, use this +" as the deprecation message +function! nerdtree#deprecated(func, ...) + let msg = a:0 ? a:func . ' ' . a:1 : a:func . ' is deprecated' + + if !exists('s:deprecationWarnings') + let s:deprecationWarnings = {} + endif + if !has_key(s:deprecationWarnings, a:func) + let s:deprecationWarnings[a:func] = 1 + echomsg msg + endif +endfunction + +" FUNCTION: nerdtree#exec(cmd) {{{2 +" Same as :exec cmd but with eventignore set for the duration +" to disable the autocommands used by NERDTree (BufEnter, +" BufLeave and VimEnter) +function! nerdtree#exec(cmd) + let old_ei = &ei + set ei=BufEnter,BufLeave,VimEnter + exec a:cmd + let &ei = old_ei +endfunction + +" FUNCTION: nerdtree#has_opt(options, name) {{{2 +function! nerdtree#has_opt(options, name) + return has_key(a:options, a:name) && a:options[a:name] == 1 +endfunction + +" FUNCTION: nerdtree#loadClassFiles() {{{2 +function! nerdtree#loadClassFiles() + runtime lib/nerdtree/path.vim + runtime lib/nerdtree/menu_controller.vim + runtime lib/nerdtree/menu_item.vim + runtime lib/nerdtree/key_map.vim + runtime lib/nerdtree/bookmark.vim + runtime lib/nerdtree/tree_file_node.vim + runtime lib/nerdtree/tree_dir_node.vim + runtime lib/nerdtree/opener.vim + runtime lib/nerdtree/creator.vim + runtime lib/nerdtree/flag_set.vim + runtime lib/nerdtree/nerdtree.vim + runtime lib/nerdtree/ui.vim + runtime lib/nerdtree/event.vim + runtime lib/nerdtree/notifier.vim +endfunction + +" FUNCTION: nerdtree#postSourceActions() {{{2 +function! nerdtree#postSourceActions() + call g:NERDTreeBookmark.CacheBookmarks(1) + call nerdtree#ui_glue#createDefaultBindings() + + "load all nerdtree plugins + runtime! nerdtree_plugin/**/*.vim +endfunction + +"FUNCTION: nerdtree#runningWindows(dir) {{{2 +function! nerdtree#runningWindows() + return has("win16") || has("win32") || has("win64") +endfunction + +"FUNCTION: nerdtree#runningCygwin(dir) {{{2 +function! nerdtree#runningCygwin() + return has("win32unix") +endfunction + +" SECTION: View Functions {{{1 +"============================================================ + +"FUNCTION: nerdtree#echo {{{2 +"A wrapper for :echo. Appends 'NERDTree:' on the front of all messages +" +"Args: +"msg: the message to echo +function! nerdtree#echo(msg) + redraw + echomsg "NERDTree: " . a:msg +endfunction + +"FUNCTION: nerdtree#echoError {{{2 +"Wrapper for nerdtree#echo, sets the message type to errormsg for this message +"Args: +"msg: the message to echo +function! nerdtree#echoError(msg) + echohl errormsg + call nerdtree#echo(a:msg) + echohl normal +endfunction + +"FUNCTION: nerdtree#echoWarning {{{2 +"Wrapper for nerdtree#echo, sets the message type to warningmsg for this message +"Args: +"msg: the message to echo +function! nerdtree#echoWarning(msg) + echohl warningmsg + call nerdtree#echo(a:msg) + echohl normal +endfunction + +"FUNCTION: nerdtree#renderView {{{2 +function! nerdtree#renderView() + call b:NERDTree.render() +endfunction + +" vim: set sw=4 sts=4 et fdm=marker: diff --git a/vim/plugins/nerdtree/autoload/nerdtree/ui_glue.vim b/vim/plugins/nerdtree/autoload/nerdtree/ui_glue.vim new file mode 100644 index 0000000..6ba9ee6 --- /dev/null +++ b/vim/plugins/nerdtree/autoload/nerdtree/ui_glue.vim @@ -0,0 +1,661 @@ +if exists("g:loaded_nerdtree_ui_glue_autoload") + finish +endif +let g:loaded_nerdtree_ui_glue_autoload = 1 + +" FUNCTION: nerdtree#ui_glue#createDefaultBindings() {{{1 +function! nerdtree#ui_glue#createDefaultBindings() + let s = '' . s:SID() . '_' + + call NERDTreeAddKeyMap({ 'key': '', 'scope': 'all', 'callback': s . 'handleMiddleMouse' }) + call NERDTreeAddKeyMap({ 'key': '', 'scope': "all", 'callback': s."handleLeftClick" }) + call NERDTreeAddKeyMap({ 'key': '<2-LeftMouse>', 'scope': "DirNode", 'callback': s."activateDirNode" }) + call NERDTreeAddKeyMap({ 'key': '<2-LeftMouse>', 'scope': "FileNode", 'callback': s."activateFileNode" }) + call NERDTreeAddKeyMap({ 'key': '<2-LeftMouse>', 'scope': "Bookmark", 'callback': s."activateBookmark" }) + call NERDTreeAddKeyMap({ 'key': '<2-LeftMouse>', 'scope': "all", 'callback': s."activateAll" }) + + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapActivateNode, 'scope': "DirNode", 'callback': s."activateDirNode" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapActivateNode, 'scope': "FileNode", 'callback': s."activateFileNode" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapActivateNode, 'scope': "Bookmark", 'callback': s."activateBookmark" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapActivateNode, 'scope': "all", 'callback': s."activateAll" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapOpenSplit, 'scope': "Node", 'callback': s."openHSplit" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapOpenVSplit, 'scope': "Node", 'callback': s."openVSplit" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapPreview, 'scope': "Node", 'callback': s."previewNodeCurrent" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapPreviewVSplit, 'scope': "Node", 'callback': s."previewNodeVSplit" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapPreviewSplit, 'scope': "Node", 'callback': s."previewNodeHSplit" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapOpenRecursively, 'scope': "DirNode", 'callback': s."openNodeRecursively" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapUpdir, 'scope': 'all', 'callback': s . 'upDirCurrentRootClosed' }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapUpdirKeepOpen, 'scope': 'all', 'callback': s . 'upDirCurrentRootOpen' }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapChangeRoot, 'scope': 'Node', 'callback': s . 'chRoot' }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapChdir, 'scope': "Node", 'callback': s."chCwd" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapQuit, 'scope': "all", 'callback': s."closeTreeWindow" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapCWD, 'scope': "all", 'callback': "nerdtree#ui_glue#chRootCwd" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapRefreshRoot, 'scope': "all", 'callback': s."refreshRoot" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapRefresh, 'scope': "Node", 'callback': s."refreshCurrent" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapHelp, 'scope': "all", 'callback': s."displayHelp" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapToggleZoom, 'scope': "all", 'callback': s."toggleZoom" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapToggleHidden, 'scope': "all", 'callback': s."toggleShowHidden" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapToggleFilters, 'scope': "all", 'callback': s."toggleIgnoreFilter" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapToggleFiles, 'scope': "all", 'callback': s."toggleShowFiles" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapToggleBookmarks, 'scope': "all", 'callback': s."toggleShowBookmarks" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapCloseDir, 'scope': "Node", 'callback': s."closeCurrentDir" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapCloseChildren, 'scope': "DirNode", 'callback': s."closeChildren" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapMenu, 'scope': "Node", 'callback': s."showMenu" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapJumpParent, 'scope': "Node", 'callback': s."jumpToParent" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapJumpFirstChild, 'scope': "Node", 'callback': s."jumpToFirstChild" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapJumpLastChild, 'scope': "Node", 'callback': s."jumpToLastChild" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapJumpRoot, 'scope': "all", 'callback': s."jumpToRoot" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapJumpNextSibling, 'scope': "Node", 'callback': s."jumpToNextSibling" }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapJumpPrevSibling, 'scope': "Node", 'callback': s."jumpToPrevSibling" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapOpenInTab, 'scope': 'Node', 'callback': s . 'openInNewTab' }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapOpenInTabSilent, 'scope': 'Node', 'callback': s . 'openInNewTabSilent' }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapOpenInTab, 'scope': 'Bookmark', 'callback': s . 'openInNewTab' }) + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapOpenInTabSilent, 'scope': 'Bookmark', 'callback': s . 'openInNewTabSilent' }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapOpenExpl, 'scope': "DirNode", 'callback': s."openExplorer" }) + + call NERDTreeAddKeyMap({ 'key': g:NERDTreeMapDeleteBookmark, 'scope': "Bookmark", 'callback': s."deleteBookmark" }) +endfunction + + +"SECTION: Interface bindings {{{1 +"============================================================ + +"FUNCTION: s:activateAll() {{{1 +"handle the user activating the updir line +function! s:activateAll() + if getline(".") ==# g:NERDTreeUI.UpDirLine() + return nerdtree#ui_glue#upDir(0) + endif +endfunction + +" FUNCTION: s:activateDirNode(directoryNode) {{{1 +function! s:activateDirNode(directoryNode) + + if a:directoryNode.isRoot() && a:directoryNode.isOpen + call nerdtree#echo('cannot close tree root') + return + endif + + call a:directoryNode.activate() +endfunction + +"FUNCTION: s:activateFileNode() {{{1 +"handle the user activating a tree node +function! s:activateFileNode(node) + call a:node.activate({'reuse': 'all', 'where': 'p'}) +endfunction + +"FUNCTION: s:activateBookmark() {{{1 +"handle the user activating a bookmark +function! s:activateBookmark(bm) + call a:bm.activate(b:NERDTree, !a:bm.path.isDirectory ? {'where': 'p'} : {}) +endfunction + +" FUNCTION: nerdtree#ui_glue#bookmarkNode(name) {{{1 +" Associate the current node with the given name +function! nerdtree#ui_glue#bookmarkNode(...) + let currentNode = g:NERDTreeFileNode.GetSelected() + if currentNode != {} + let name = a:1 + if empty(name) + let name = currentNode.path.getLastPathComponent(0) + endif + try + call currentNode.bookmark(name) + call b:NERDTree.render() + catch /^NERDTree.IllegalBookmarkNameError/ + call nerdtree#echo("bookmark names must not contain spaces") + endtry + else + call nerdtree#echo("select a node first") + endif +endfunction + +" FUNCTION: s:chCwd(node) {{{1 +function! s:chCwd(node) + try + call a:node.path.changeToDir() + catch /^NERDTree.PathChangeError/ + call nerdtree#echoWarning("could not change cwd") + endtry +endfunction + +" FUNCTION: s:chRoot(node) {{{1 +" changes the current root to the selected one +function! s:chRoot(node) + call b:NERDTree.changeRoot(a:node) +endfunction + +" FUNCTION: s:nerdtree#ui_glue#chRootCwd() {{{1 +" changes the current root to CWD +function! nerdtree#ui_glue#chRootCwd() + try + let cwd = g:NERDTreePath.New(getcwd()) + catch /^NERDTree.InvalidArgumentsError/ + call nerdtree#echo("current directory does not exist.") + return + endtry + if cwd.str() == g:NERDTreeFileNode.GetRootForTab().path.str() + return + endif + call s:chRoot(g:NERDTreeDirNode.New(cwd, b:NERDTree)) +endfunction + +" FUNCTION: nnerdtree#ui_glue#clearBookmarks(bookmarks) {{{1 +function! nerdtree#ui_glue#clearBookmarks(bookmarks) + if a:bookmarks ==# '' + let currentNode = g:NERDTreeFileNode.GetSelected() + if currentNode != {} + call currentNode.clearBookmarks() + endif + else + for name in split(a:bookmarks, ' ') + let bookmark = g:NERDTreeBookmark.BookmarkFor(name) + call bookmark.delete() + endfor + endif + call b:NERDTree.root.refresh() + call b:NERDTree.render() +endfunction + +" FUNCTION: s:closeChildren(node) {{{1 +" closes all childnodes of the current node +function! s:closeChildren(node) + call a:node.closeChildren() + call b:NERDTree.render() + call a:node.putCursorHere(0, 0) +endfunction + +" FUNCTION: s:closeCurrentDir(node) {{{1 +" Close the parent directory of the current node. +function! s:closeCurrentDir(node) + + if a:node.isRoot() + call nerdtree#echo('cannot close parent of tree root') + return + endif + + let l:parent = a:node.parent + + while l:parent.isCascadable() + let l:parent = l:parent.parent + endwhile + + if l:parent.isRoot() + call nerdtree#echo('cannot close tree root') + return + endif + + call l:parent.close() + call b:NERDTree.render() + call l:parent.putCursorHere(0, 0) +endfunction + +" FUNCTION: s:closeTreeWindow() {{{1 +" close the tree window +function! s:closeTreeWindow() + if b:NERDTree.isWinTree() && b:NERDTree.previousBuf() != -1 + exec "buffer " . b:NERDTree.previousBuf() + else + if winnr("$") > 1 + call g:NERDTree.Close() + else + call nerdtree#echo("Cannot close last window") + endif + endif +endfunction + +" FUNCTION: s:deleteBookmark(bookmark) {{{1 +" Prompt the user to confirm the deletion of the selected bookmark. +function! s:deleteBookmark(bookmark) + let l:message = "Delete the bookmark \"" . a:bookmark.name + \ . "\" from the bookmark list?" + + let l:choices = "&Yes\n&No" + + echo | redraw + let l:selection = confirm(l:message, l:choices, 1, 'Warning') + + if l:selection != 1 + call nerdtree#echo('bookmark not deleted') + return + endif + + try + call a:bookmark.delete() + silent call b:NERDTree.root.refresh() + call b:NERDTree.render() + echo | redraw + catch /^NERDTree/ + call nerdtree#echoWarning('could not remove bookmark') + endtry +endfunction + +" FUNCTION: s:displayHelp() {{{1 +" toggles the help display +function! s:displayHelp() + call b:NERDTree.ui.toggleHelp() + call b:NERDTree.render() + call b:NERDTree.ui.centerView() +endfunction + +" FUNCTION: s:findAndRevealPath(pathStr) {{{1 +function! s:findAndRevealPath(pathStr) + let l:pathStr = !empty(a:pathStr) ? a:pathStr : expand('%:p') + + if empty(l:pathStr) + call nerdtree#echoWarning('no file for the current buffer') + return + endif + + try + let l:pathObj = g:NERDTreePath.New(l:pathStr) + catch /^NERDTree.InvalidArgumentsError/ + call nerdtree#echoWarning('invalid path') + return + endtry + + if !g:NERDTree.ExistsForTab() + try + let l:cwd = g:NERDTreePath.New(getcwd()) + catch /^NERDTree.InvalidArgumentsError/ + call nerdtree#echo('current directory does not exist.') + let l:cwd = l:pathObj.getParent() + endtry + + if l:pathObj.isUnder(l:cwd) + call g:NERDTreeCreator.CreateTabTree(l:cwd.str()) + else + call g:NERDTreeCreator.CreateTabTree(l:pathObj.getParent().str()) + endif + else + NERDTreeFocus + + if !l:pathObj.isUnder(b:NERDTree.root.path) + call s:chRoot(g:NERDTreeDirNode.New(l:pathObj.getParent(), b:NERDTree)) + endif + endif + + if l:pathObj.isHiddenUnder(b:NERDTree.root.path) + call b:NERDTree.ui.setShowHidden(1) + endif + + let l:node = b:NERDTree.root.reveal(l:pathObj) + call b:NERDTree.render() + call l:node.putCursorHere(1, 0) +endfunction + +"FUNCTION: s:handleLeftClick() {{{1 +"Checks if the click should open the current node +function! s:handleLeftClick() + let currentNode = g:NERDTreeFileNode.GetSelected() + if currentNode != {} + + "the dir arrows are multibyte chars, and vim's string functions only + "deal with single bytes - so split the line up with the hack below and + "take the line substring manually + let line = split(getline(line(".")), '\zs') + let startToCur = "" + for i in range(0,len(line)-1) + let startToCur .= line[i] + endfor + + if currentNode.path.isDirectory + if startToCur =~# g:NERDTreeUI.MarkupReg() && startToCur =~# '[+~'.g:NERDTreeDirArrowExpandable.g:NERDTreeDirArrowCollapsible.'] \?$' + call currentNode.activate() + return + endif + endif + + if (g:NERDTreeMouseMode ==# 2 && currentNode.path.isDirectory) || g:NERDTreeMouseMode ==# 3 + let char = strpart(startToCur, strlen(startToCur)-1, 1) + if char !~# g:NERDTreeUI.MarkupReg() + if currentNode.path.isDirectory + call currentNode.activate() + else + call currentNode.activate({'reuse': 'all', 'where': 'p'}) + endif + return + endif + endif + endif +endfunction + +" FUNCTION: s:handleMiddleMouse() {{{1 +function! s:handleMiddleMouse() + + " A middle mouse click does not automatically position the cursor as one + " would expect. Forcing the execution of a regular left mouse click here + " fixes this problem. + execute "normal! \" + + let l:currentNode = g:NERDTreeFileNode.GetSelected() + if empty(l:currentNode) + call nerdtree#echoError('use the pointer to select a node') + return + endif + + if l:currentNode.path.isDirectory + call l:currentNode.openExplorer() + else + call l:currentNode.open({'where': 'h'}) + endif +endfunction + +" FUNCTION: s:jumpToChild(direction) {{{2 +" Args: +" direction: 0 if going to first child, 1 if going to last +function! s:jumpToChild(currentNode, direction) + if a:currentNode.isRoot() + return nerdtree#echo("cannot jump to " . (a:direction ? "last" : "first") . " child") + end + let dirNode = a:currentNode.parent + let childNodes = dirNode.getVisibleChildren() + + let targetNode = childNodes[0] + if a:direction + let targetNode = childNodes[len(childNodes) - 1] + endif + + if targetNode.equals(a:currentNode) + let siblingDir = a:currentNode.parent.findOpenDirSiblingWithVisibleChildren(a:direction) + if siblingDir != {} + let indx = a:direction ? siblingDir.getVisibleChildCount()-1 : 0 + let targetNode = siblingDir.getChildByIndex(indx, 1) + endif + endif + + call targetNode.putCursorHere(1, 0) + + call b:NERDTree.ui.centerView() +endfunction + + +" FUNCTION: nerdtree#ui_glue#invokeKeyMap(key) {{{1 +"this is needed since I cant figure out how to invoke dict functions from a +"key map +function! nerdtree#ui_glue#invokeKeyMap(key) + call g:NERDTreeKeyMap.Invoke(a:key) +endfunction + +" FUNCTION: s:jumpToFirstChild() {{{1 +" wrapper for the jump to child method +function! s:jumpToFirstChild(node) + call s:jumpToChild(a:node, 0) +endfunction + +" FUNCTION: s:jumpToLastChild() {{{1 +" wrapper for the jump to child method +function! s:jumpToLastChild(node) + call s:jumpToChild(a:node, 1) +endfunction + +" FUNCTION: s:jumpToParent(node) {{{1 +" Move the cursor to the parent of the specified node. For a cascade, move to +" the parent of the cascade's highest node. At the root, do nothing. +function! s:jumpToParent(node) + let l:parent = a:node.parent + + " If "a:node" represents a directory, back out of its cascade. + if a:node.path.isDirectory + while !empty(l:parent) && !l:parent.isRoot() + if index(l:parent.getCascade(), a:node) >= 0 + let l:parent = l:parent.parent + else + break + endif + endwhile + endif + + if !empty(l:parent) + call l:parent.putCursorHere(1, 0) + call b:NERDTree.ui.centerView() + else + call nerdtree#echo('could not jump to parent node') + endif +endfunction + +" FUNCTION: s:jumpToRoot() {{{1 +" moves the cursor to the root node +function! s:jumpToRoot() + call b:NERDTree.root.putCursorHere(1, 0) + call b:NERDTree.ui.centerView() +endfunction + +" FUNCTION: s:jumpToNextSibling(node) {{{1 +function! s:jumpToNextSibling(node) + call s:jumpToSibling(a:node, 1) +endfunction + +" FUNCTION: s:jumpToPrevSibling(node) {{{1 +function! s:jumpToPrevSibling(node) + call s:jumpToSibling(a:node, 0) +endfunction + +" FUNCTION: s:jumpToSibling(currentNode, forward) {{{2 +" moves the cursor to the sibling of the current node in the given direction +" +" Args: +" forward: 1 if the cursor should move to the next sibling, 0 if it should +" move back to the previous sibling +function! s:jumpToSibling(currentNode, forward) + let sibling = a:currentNode.findSibling(a:forward) + + if !empty(sibling) + call sibling.putCursorHere(1, 0) + call b:NERDTree.ui.centerView() + endif +endfunction + +" FUNCTION: nerdtree#ui_glue#openBookmark(name) {{{1 +" Open the Bookmark that has the specified name. This function provides the +" implementation for the ":OpenBookmark" command. +function! nerdtree#ui_glue#openBookmark(name) + try + let l:bookmark = g:NERDTreeBookmark.BookmarkFor(a:name) + catch /^NERDTree.BookmarkNotFoundError/ + call nerdtree#echoError('bookmark "' . a:name . '" not found') + return + endtry + if l:bookmark.path.isDirectory + call l:bookmark.open(b:NERDTree) + else + call l:bookmark.open(b:NERDTree, {'where': 'p'}) + endif +endfunction + +" FUNCTION: s:openHSplit(target) {{{1 +function! s:openHSplit(target) + call a:target.activate({'where': 'h'}) +endfunction + +" FUNCTION: s:openVSplit(target) {{{1 +function! s:openVSplit(target) + call a:target.activate({'where': 'v'}) +endfunction + +" FUNCTION: s:openExplorer(node) {{{1 +function! s:openExplorer(node) + call a:node.openExplorer() +endfunction + +" FUNCTION: s:openInNewTab(target) {{{1 +function! s:openInNewTab(target) + let l:opener = g:NERDTreeOpener.New(a:target.path, {'where': 't'}) + call l:opener.open(a:target) +endfunction + +" FUNCTION: s:openInNewTabSilent(target) {{{1 +function! s:openInNewTabSilent(target) + let l:opener = g:NERDTreeOpener.New(a:target.path, {'where': 't', 'stay': 1}) + call l:opener.open(a:target) +endfunction + +" FUNCTION: s:openNodeRecursively(node) {{{1 +function! s:openNodeRecursively(node) + call nerdtree#echo("Recursively opening node. Please wait...") + call a:node.openRecursively() + call b:NERDTree.render() + redraw + call nerdtree#echo("Recursively opening node. Please wait... DONE") +endfunction + +"FUNCTION: s:previewNodeCurrent(node) {{{1 +function! s:previewNodeCurrent(node) + call a:node.open({'stay': 1, 'where': 'p', 'keepopen': 1}) +endfunction + +"FUNCTION: s:previewNodeHSplit(node) {{{1 +function! s:previewNodeHSplit(node) + call a:node.open({'stay': 1, 'where': 'h', 'keepopen': 1}) +endfunction + +"FUNCTION: s:previewNodeVSplit(node) {{{1 +function! s:previewNodeVSplit(node) + call a:node.open({'stay': 1, 'where': 'v', 'keepopen': 1}) +endfunction + +" FUNCTION: nerdtree#ui_glue#revealBookmark(name) {{{1 +" put the cursor on the node associate with the given name +function! nerdtree#ui_glue#revealBookmark(name) + try + let targetNode = g:NERDTreeBookmark.GetNodeForName(a:name, 0, b:NERDTree) + call targetNode.putCursorHere(0, 1) + catch /^NERDTree.BookmarkNotFoundError/ + call nerdtree#echo("Bookmark isnt cached under the current root") + endtry +endfunction + +" FUNCTION: s:refreshRoot() {{{1 +" Reloads the current root. All nodes below this will be lost and the root dir +" will be reloaded. +function! s:refreshRoot() + call nerdtree#echo("Refreshing the root node. This could take a while...") + call b:NERDTree.root.refresh() + call b:NERDTree.render() + redraw + call nerdtree#echo("Refreshing the root node. This could take a while... DONE") +endfunction + +" FUNCTION: s:refreshCurrent(node) {{{1 +" refreshes the root for the current node +function! s:refreshCurrent(node) + let node = a:node + if !node.path.isDirectory + let node = node.parent + endif + + call nerdtree#echo("Refreshing node. This could take a while...") + call node.refresh() + call b:NERDTree.render() + redraw + call nerdtree#echo("Refreshing node. This could take a while... DONE") +endfunction + +" FUNCTION: nerdtree#ui_glue#setupCommands() {{{1 +function! nerdtree#ui_glue#setupCommands() + command! -n=? -complete=dir -bar NERDTree :call g:NERDTreeCreator.CreateTabTree('') + command! -n=? -complete=dir -bar NERDTreeToggle :call g:NERDTreeCreator.ToggleTabTree('') + command! -n=0 -bar NERDTreeClose :call g:NERDTree.Close() + command! -n=1 -complete=customlist,nerdtree#completeBookmarks -bar NERDTreeFromBookmark call g:NERDTreeCreator.CreateTabTree('') + command! -n=0 -bar NERDTreeMirror call g:NERDTreeCreator.CreateMirror() + command! -n=? -complete=file -bar NERDTreeFind call s:findAndRevealPath('') + command! -n=0 -bar NERDTreeFocus call NERDTreeFocus() + command! -n=0 -bar NERDTreeCWD call NERDTreeCWD() +endfunction + +" Function: s:SID() {{{1 +function s:SID() + if !exists("s:sid") + let s:sid = matchstr(expand(''), '\zs\d\+\ze_SID$') + endif + return s:sid +endfun + +" FUNCTION: s:showMenu(node) {{{1 +function! s:showMenu(node) + let mc = g:NERDTreeMenuController.New(g:NERDTreeMenuItem.AllEnabled()) + call mc.showMenu() +endfunction + +" FUNCTION: s:toggleIgnoreFilter() {{{1 +function! s:toggleIgnoreFilter() + call b:NERDTree.ui.toggleIgnoreFilter() +endfunction + +" FUNCTION: s:toggleShowBookmarks() {{{1 +function! s:toggleShowBookmarks() + call b:NERDTree.ui.toggleShowBookmarks() +endfunction + +" FUNCTION: s:toggleShowFiles() {{{1 +function! s:toggleShowFiles() + call b:NERDTree.ui.toggleShowFiles() +endfunction + +" FUNCTION: s:toggleShowHidden() {{{1 +" toggles the display of hidden files +function! s:toggleShowHidden() + call b:NERDTree.ui.toggleShowHidden() +endfunction + +" FUNCTION: s:toggleZoom() {{{1 +function! s:toggleZoom() + call b:NERDTree.ui.toggleZoom() +endfunction + +" FUNCTION: nerdtree#ui_glue#upDir(preserveState) {{{1 +" Move the NERDTree up one level. +" +" Args: +" preserveState: if 1, the current root is left open when the new tree is +" rendered; if 0, the current root node is closed +function! nerdtree#ui_glue#upDir(preserveState) + + try + call b:NERDTree.root.cacheParent() + catch /^NERDTree.CannotCacheParentError/ + call nerdtree#echo('already at root directory') + return + endtry + + let l:oldRoot = b:NERDTree.root + let l:newRoot = b:NERDTree.root.parent + + call l:newRoot.open() + call l:newRoot.transplantChild(l:oldRoot) + + if !a:preserveState + call l:oldRoot.close() + endif + + call b:NERDTree.changeRoot(l:newRoot) + call l:oldRoot.putCursorHere(0, 0) +endfunction + +" FUNCTION: s:upDirCurrentRootOpen() {{{1 +function! s:upDirCurrentRootOpen() + call nerdtree#ui_glue#upDir(1) +endfunction + +" FUNCTION: s:upDirCurrentRootClosed() {{{1 +function! s:upDirCurrentRootClosed() + call nerdtree#ui_glue#upDir(0) +endfunction + +" vim: set sw=4 sts=4 et fdm=marker: diff --git a/vim/plugins/nerdtree/doc/NERDTree.txt b/vim/plugins/nerdtree/doc/NERDTree.txt new file mode 100644 index 0000000..a83c4e1 --- /dev/null +++ b/vim/plugins/nerdtree/doc/NERDTree.txt @@ -0,0 +1,1309 @@ +*NERDTree.txt* A tree explorer plugin that owns your momma! + + + + omg its ... ~ + + ________ ________ _ ____________ ____ __________ ____________~ + /_ __/ / / / ____/ / | / / ____/ __ \/ __ \ /_ __/ __ \/ ____/ ____/~ + / / / /_/ / __/ / |/ / __/ / /_/ / / / / / / / /_/ / __/ / __/ ~ + / / / __ / /___ / /| / /___/ _, _/ /_/ / / / / _, _/ /___/ /___ ~ + /_/ /_/ /_/_____/ /_/ |_/_____/_/ |_/_____/ /_/ /_/ |_/_____/_____/ ~ + + + Reference Manual~ + + + + +============================================================================== +CONTENTS *NERDTree-contents* + + 1.Intro...................................|NERDTree| + 2.Functionality provided..................|NERDTreeFunctionality| + 2.1.Global commands...................|NERDTreeGlobalCommands| + 2.2.Bookmarks.........................|NERDTreeBookmarks| + 2.2.1.The bookmark table..........|NERDTreeBookmarkTable| + 2.2.2.Bookmark commands...........|NERDTreeBookmarkCommands| + 2.2.3.Invalid bookmarks...........|NERDTreeInvalidBookmarks| + 2.3.NERD tree mappings................|NERDTreeMappings| + 2.4.The NERD tree menu................|NERDTreeMenu| + 3.Options.................................|NERDTreeOptions| + 3.1.Option summary....................|NERDTreeOptionSummary| + 3.2.Option details....................|NERDTreeOptionDetails| + 4.The NERD tree API.......................|NERDTreeAPI| + 4.1.Key map API.......................|NERDTreeKeymapAPI| + 4.2.Menu API..........................|NERDTreeMenuAPI| + 4.3.Menu API..........................|NERDTreeAddPathFilter()| + 4.4.Path Listener API.................|NERDTreePathListenerAPI| + 5.About...................................|NERDTreeAbout| + 6.License.................................|NERDTreeLicense| + +============================================================================== +1. Intro *NERDTree* + +What is this "NERD tree"?? + +The NERD tree allows you to explore your filesystem and to open files and +directories. It presents the filesystem to you in the form of a tree which you +manipulate with the keyboard and/or mouse. It also allows you to perform +simple filesystem operations. + +The following features and functionality are provided by the NERD tree: + * Files and directories are displayed in a hierarchical tree structure + * Different highlighting is provided for the following types of nodes: + * files + * directories + * sym-links + * windows .lnk files + * read-only files + * executable files + * Many (customisable) mappings are provided to manipulate the tree: + * Mappings to open/close/explore directory nodes + * Mappings to open files in new/existing windows/tabs + * Mappings to change the current root of the tree + * Mappings to navigate around the tree + * ... + * Directories and files can be bookmarked. + * Most NERD tree navigation can also be done with the mouse + * Filtering of tree content (can be toggled at runtime) + * custom file filters to prevent e.g. vim backup files being displayed + * optional displaying of hidden files (. files) + * files can be "turned off" so that only directories are displayed + * The position and size of the NERD tree window can be customised + * The order in which the nodes in the tree are listed can be customised. + * A model of your filesystem is created/maintained as you explore it. This + has several advantages: + * All filesystem information is cached and is only re-read on demand + * If you revisit a part of the tree that you left earlier in your + session, the directory nodes will be opened/closed as you left them + * The script remembers the cursor position and window position in the NERD + tree so you can toggle it off (or just close the tree window) and then + reopen it (with NERDTreeToggle) the NERD tree window will appear exactly + as you left it + * You can have a separate NERD tree for each tab, share trees across tabs, + or a mix of both. + * By default the script overrides the default file browser (netrw), so if + you :edit a directory a (slightly modified) NERD tree will appear in the + current window + * A programmable menu system is provided (simulates right clicking on a + node) + * one default menu plugin is provided to perform basic filesystem + operations (create/delete/move/copy files/directories) + * There's an API for adding your own keymappings + + +============================================================================== +2. Functionality provided *NERDTreeFunctionality* + +------------------------------------------------------------------------------ +2.1. Global Commands *NERDTreeGlobalCommands* + +:NERDTree [ | ] *:NERDTree* + Opens a fresh NERD tree. The root of the tree depends on the argument + given. There are 3 cases: If no argument is given, the current directory + will be used. If a directory is given, that will be used. If a bookmark + name is given, the corresponding directory will be used. For example: > + :NERDTree /home/marty/vim7/src + :NERDTree foo (foo is the name of a bookmark) +< +:NERDTreeFromBookmark *:NERDTreeFromBookmark* + Opens a fresh NERD tree with the root initialized to the dir for + . The only reason to use this command over :NERDTree is for + the completion (which is for bookmarks rather than directories). + +:NERDTreeToggle [ | ] *:NERDTreeToggle* + If a NERD tree already exists for this tab, it is reopened and rendered + again. If no NERD tree exists for this tab then this command acts the + same as the |:NERDTree| command. + +:NERDTreeFocus *:NERDTreeFocus* + Opens (or reopens) the NERD Tree if it is not currently visible; + otherwise, the cursor is moved to the already-open NERD Tree. + +:NERDTreeMirror *:NERDTreeMirror* + Shares an existing NERD tree, from another tab, in the current tab. + Changes made to one tree are reflected in both as they are actually the + same buffer. + + If only one other NERD tree exists, that tree is automatically mirrored. + If more than one exists, the script will ask which tree to mirror. + +:NERDTreeClose *:NERDTreeClose* + Close the NERD tree in this tab. + +:NERDTreeFind [] *:NERDTreeFind* + Without the optional argument, find and reveal the file for the active + buffer in the NERDTree window. With the argument, find and + reveal the specified path. + + Focus will be shifted to the NERDTree window, and the cursor will be + placed on the tree node for the determined path. If a NERDTree for the + current tab does not exist, a new one will be initialized. + +:NERDTreeCWD *:NERDTreeCWD* + Change tree root to current directory. If no NERD tree exists for this + tab, a new tree will be opened. + +------------------------------------------------------------------------------ +2.2. Bookmarks *NERDTreeBookmarks* + +Bookmarks in the NERD tree are a way to tag files or directories of interest. +For example, you could use bookmarks to tag all of your project directories. + +------------------------------------------------------------------------------ +2.2.1. The Bookmark Table *NERDTreeBookmarkTable* + +If the bookmark table is active (see |NERDTree-B| and +|'NERDTreeShowBookmarks'|), it will be rendered above the tree. You can double +click bookmarks or use the |NERDTree-o| mapping to activate them. See also, +|NERDTree-t| and |NERDTree-T| + +------------------------------------------------------------------------------ +2.2.2. Bookmark commands *NERDTreeBookmarkCommands* + +Note: The following commands are only available within the NERDTree buffer. + +:Bookmark [] + Bookmark the current node as . If there is already a + bookmark, it is overwritten. must not contain spaces. + If is not provided, it defaults to the file or directory name. + For directories, a trailing slash is present. + +:BookmarkToRoot + Make the directory corresponding to the new root. If a treenode + corresponding to is already cached somewhere in the tree then + the current tree will be used, otherwise a fresh tree will be opened. + Note that if points to a file then its parent will be used + instead. + +:RevealBookmark + If the node is cached under the current root then it will be revealed + (i.e. directory nodes above it will be opened) and the cursor will be + placed on it. + +:OpenBookmark + The Bookmark named is opened as if |NERDTree-o| was applied to + its entry in the Bookmark table. If the Bookmark points to a directory, + it is made the new root of the current NERDTree. If the Bookmark points + to a file, that file is opened for editing in another window. + +:ClearBookmarks [] + Remove all the given bookmarks. If no bookmarks are given then remove all + bookmarks on the current node. + +:ClearAllBookmarks + Remove all bookmarks. + +:ReadBookmarks + Re-read the bookmarks in the |'NERDTreeBookmarksFile'|. + +See also |:NERDTree| and |:NERDTreeFromBookmark|. + +------------------------------------------------------------------------------ +2.2.3. Invalid Bookmarks *NERDTreeInvalidBookmarks* + +If invalid bookmarks are detected, the script will issue an error message and +the invalid bookmarks will become unavailable for use. + +These bookmarks will still be stored in the bookmarks file (see +|'NERDTreeBookmarksFile'|), down the bottom. There will always be a blank line +after the valid bookmarks but before the invalid ones. + +Each line in the bookmarks file represents one bookmark. The proper format is: + + +After you have corrected any invalid bookmarks, either restart vim, or go +:ReadBookmarks from the NERD tree window. + +------------------------------------------------------------------------------ +2.3. NERD tree Mappings *NERDTreeMappings* + +Default Description~ help-tag~ +Key~ + +o.......Open files, directories and bookmarks....................|NERDTree-o| +go......Open selected file, but leave cursor in the NERDTree.....|NERDTree-go| +t.......Open selected node/bookmark in a new tab.................|NERDTree-t| +T.......Same as 't' but keep the focus on the current tab........|NERDTree-T| +i.......Open selected file in a split window.....................|NERDTree-i| +gi......Same as i, but leave the cursor on the NERDTree..........|NERDTree-gi| +s.......Open selected file in a new vsplit.......................|NERDTree-s| +gs......Same as s, but leave the cursor on the NERDTree..........|NERDTree-gs| +O.......Recursively open the selected directory..................|NERDTree-O| +x.......Close the current nodes parent...........................|NERDTree-x| +X.......Recursively close all children of the current node.......|NERDTree-X| +e.......Edit the current dir.....................................|NERDTree-e| + +...............same as |NERDTree-o|. +double-click.......same as the |NERDTree-o| map. +middle-click.......same as |NERDTree-i| for files, same as + |NERDTree-e| for dirs. + +D.......Delete the current bookmark .............................|NERDTree-D| + +P.......Jump to the root node....................................|NERDTree-P| +p.......Jump to current nodes parent.............................|NERDTree-p| +K.......Jump up inside directories at the current tree depth.....|NERDTree-K| +J.......Jump down inside directories at the current tree depth...|NERDTree-J| +...Jump down to the next sibling of the current directory...|NERDTree-C-J| +...Jump up to the previous sibling of the current directory.|NERDTree-C-K| + +C.......Change the tree root to the selected dir.................|NERDTree-C| +u.......Move the tree root up one directory......................|NERDTree-u| +U.......Same as 'u' except the old root node is left open........|NERDTree-U| +r.......Recursively refresh the current directory................|NERDTree-r| +R.......Recursively refresh the current root.....................|NERDTree-R| +m.......Display the NERD tree menu...............................|NERDTree-m| +cd......Change the CWD to the dir of the selected node...........|NERDTree-cd| +CD......Change tree root to the CWD..............................|NERDTree-CD| + +I.......Toggle whether hidden files displayed....................|NERDTree-I| +f.......Toggle whether the file filters are used.................|NERDTree-f| +F.......Toggle whether files are displayed.......................|NERDTree-F| +B.......Toggle whether the bookmark table is displayed...........|NERDTree-B| + +q.......Close the NERDTree window................................|NERDTree-q| +A.......Zoom (maximize/minimize) the NERDTree window.............|NERDTree-A| +?.......Toggle the display of the quick help.....................|NERDTree-?| + +------------------------------------------------------------------------------ + *NERDTree-o* +Default key: o +Map option: NERDTreeMapActivateNode +Applies to: files and directories. + +If a file node is selected, it is opened in the previous window. + +If a directory is selected it is opened or closed depending on its current +state. + +If a bookmark that links to a directory is selected then that directory +becomes the new root. + +If a bookmark that links to a file is selected then that file is opened in the +previous window. + +------------------------------------------------------------------------------ + *NERDTree-go* +Default key: go +Map option: NERDTreeMapPreview +Applies to: files. + +If a file node is selected, it is opened in the previous window, but the +cursor does not move. + +The default key combo for this mapping is "g" + NERDTreeMapActivateNode (see +|NERDTree-o|). + +------------------------------------------------------------------------------ + *NERDTree-t* +Default key: t +Map option: NERDTreeMapOpenInTab +Applies to: files and directories. + +Opens the selected file in a new tab. If a directory is selected, a fresh +NERD Tree for that directory is opened in a new tab. + +If a bookmark which points to a directory is selected, open a NERD tree for +that directory in a new tab. If the bookmark points to a file, open that file +in a new tab. + +------------------------------------------------------------------------------ + *NERDTree-T* +Default key: T +Map option: NERDTreeMapOpenInTabSilent +Applies to: files and directories. + +The same as |NERDTree-t| except that the focus is kept in the current tab. + +------------------------------------------------------------------------------ + *NERDTree-i* +Default key: i +Map option: NERDTreeMapOpenSplit +Applies to: files. + +Opens the selected file in a new split window and puts the cursor in the new +window. + +------------------------------------------------------------------------------ + *NERDTree-gi* +Default key: gi +Map option: NERDTreeMapPreviewSplit +Applies to: files. + +The same as |NERDTree-i| except that the cursor is not moved. + +The default key combo for this mapping is "g" + NERDTreeMapOpenSplit (see +|NERDTree-i|). + +------------------------------------------------------------------------------ + *NERDTree-s* +Default key: s +Map option: NERDTreeMapOpenVSplit +Applies to: files. + +Opens the selected file in a new vertically split window and puts the cursor in +the new window. + +------------------------------------------------------------------------------ + *NERDTree-gs* +Default key: gs +Map option: NERDTreeMapPreviewVSplit +Applies to: files. + +The same as |NERDTree-s| except that the cursor is not moved. + +The default key combo for this mapping is "g" + NERDTreeMapOpenVSplit (see +|NERDTree-s|). + +------------------------------------------------------------------------------ + *NERDTree-O* +Default key: O +Map option: NERDTreeMapOpenRecursively +Applies to: directories. + +Recursively opens the selected directory. + +All files and directories are cached, but if a directory would not be +displayed due to file filters (see |'NERDTreeIgnore'| |NERDTree-f|) or the +hidden file filter (see |'NERDTreeShowHidden'|) then its contents are not +cached. This is handy, especially if you have .svn directories. + +------------------------------------------------------------------------------ + *NERDTree-x* +Default key: x +Map option: NERDTreeMapCloseDir +Applies to: files and directories. + +Closes the parent of the selected node. + +------------------------------------------------------------------------------ + *NERDTree-X* +Default key: X +Map option: NERDTreeMapCloseChildren +Applies to: directories. + +Recursively closes all children of the selected directory. + +Tip: To quickly "reset" the tree, use |NERDTree-P| with this mapping. + +------------------------------------------------------------------------------ + *NERDTree-e* +Default key: e +Map option: NERDTreeMapOpenExpl +Applies to: files and directories. + +|:edit|s the selected directory, or the selected file's directory. This could +result in a NERD tree or a netrw being opened, depending on +|'NERDTreeHijackNetrw'|. + +------------------------------------------------------------------------------ + *NERDTree-D* +Default key: D +Map option: NERDTreeMapDeleteBookmark +Applies to: lines in the bookmarks table + +Deletes the currently selected bookmark. + +------------------------------------------------------------------------------ + *NERDTree-P* +Default key: P +Map option: NERDTreeMapJumpRoot +Applies to: no restrictions. + +Jump to the tree root. + +------------------------------------------------------------------------------ + *NERDTree-p* +Default key: p +Map option: NERDTreeMapJumpParent +Applies to: files and directories. + +Jump to the parent node of the selected node. + +------------------------------------------------------------------------------ + *NERDTree-K* +Default key: K +Map option: NERDTreeMapJumpFirstChild +Applies to: files and directories. + +Jump to the first child of the current nodes parent. + +If the cursor is already on the first node then do the following: + * loop back thru the siblings of the current nodes parent until we find an + open dir with children + * go to the first child of that node + +------------------------------------------------------------------------------ + *NERDTree-J* +Default key: J +Map option: NERDTreeMapJumpLastChild +Applies to: files and directories. + +Jump to the last child of the current nodes parent. + +If the cursor is already on the last node then do the following: + * loop forward thru the siblings of the current nodes parent until we find + an open dir with children + * go to the last child of that node + +------------------------------------------------------------------------------ + *NERDTree-C-J* +Default key: +Map option: NERDTreeMapJumpNextSibling +Applies to: files and directories. + +Jump to the next sibling of the selected node. + +------------------------------------------------------------------------------ + *NERDTree-C-K* +Default key: +Map option: NERDTreeMapJumpPrevSibling +Applies to: files and directories. + +Jump to the previous sibling of the selected node. + +------------------------------------------------------------------------------ + *NERDTree-C* +Default key: C +Map option: NERDTreeMapChangeRoot +Applies to: files and directories. + +Make the selected directory node the new tree root. If a file is selected, its +parent is used. + +------------------------------------------------------------------------------ + *NERDTree-u* +Default key: u +Map option: NERDTreeMapUpdir +Applies to: no restrictions. + +Move the tree root up a dir (like doing a "cd .."). + +------------------------------------------------------------------------------ + *NERDTree-U* +Default key: U +Map option: NERDTreeMapUpdirKeepOpen +Applies to: no restrictions. + +Like |NERDTree-u| except that the old tree root is kept open. + +------------------------------------------------------------------------------ + *NERDTree-r* +Default key: r +Map option: NERDTreeMapRefresh +Applies to: files and directories. + +If a dir is selected, recursively refresh that dir, i.e. scan the filesystem +for changes and represent them in the tree. + +If a file node is selected then the above is done on it's parent. + +------------------------------------------------------------------------------ + *NERDTree-R* +Default key: R +Map option: NERDTreeMapRefreshRoot +Applies to: no restrictions. + +Recursively refresh the tree root. + +------------------------------------------------------------------------------ + *NERDTree-m* +Default key: m +Map option: NERDTreeMapMenu +Applies to: files and directories. + +Display the NERD tree menu. See |NERDTreeMenu| for details. + +------------------------------------------------------------------------------ + *NERDTree-cd* +Default key: cd +Map option: NERDTreeMapChdir +Applies to: files and directories. + +Change vims current working directory to that of the selected node. + +------------------------------------------------------------------------------ + *NERDTree-CD* +Default key: CD +Map option: NERDTreeMapCWD +Applies to: no restrictions. + +Change tree root to vims current working directory. + +------------------------------------------------------------------------------ + *NERDTree-I* +Default key: I +Map option: NERDTreeMapToggleHidden +Applies to: no restrictions. + +Toggles whether hidden files (i.e. "dot files") are displayed. + +------------------------------------------------------------------------------ + *NERDTree-f* +Default key: f +Map option: NERDTreeMapToggleFilters +Applies to: no restrictions. + +Toggles whether file filters are used. See |'NERDTreeIgnore'| for details. + +------------------------------------------------------------------------------ + *NERDTree-F* +Default key: F +Map option: NERDTreeMapToggleFiles +Applies to: no restrictions. + +Toggles whether file nodes are displayed. + +------------------------------------------------------------------------------ + *NERDTree-B* +Default key: B +Map option: NERDTreeMapToggleBookmarks +Applies to: no restrictions. + +Toggles whether the bookmarks table is displayed. + +------------------------------------------------------------------------------ + *NERDTree-q* +Default key: q +Map option: NERDTreeMapQuit +Applies to: no restrictions. + +Closes the NERDtree window. + +------------------------------------------------------------------------------ + *NERDTree-A* +Default key: A +Map option: NERDTreeMapToggleZoom +Applies to: no restrictions. + +Maximize (zoom) and minimize the NERDtree window. + +------------------------------------------------------------------------------ + *NERDTree-?* +Default key: ? +Map option: NERDTreeMapHelp +Applies to: no restrictions. + +Toggles whether the quickhelp is displayed. + +------------------------------------------------------------------------------ +2.3. The NERD tree menu *NERDTreeMenu* + +The NERD tree has a menu that can be programmed via the an API (see +|NERDTreeMenuAPI|). The idea is to simulate the "right click" menus that most +file explorers have. + +The script comes with two default menu plugins: exec_menuitem.vim and +fs_menu.vim. fs_menu.vim adds some basic filesystem operations to the menu for +creating/deleting/moving/copying files and dirs. exec_menuitem.vim provides a +menu item to execute executable files. + +Related tags: |NERDTree-m| |NERDTreeApi| + +============================================================================== +3. Customisation *NERDTreeOptions* + + +------------------------------------------------------------------------------ +3.1. Customisation summary *NERDTreeOptionSummary* + +The script provides the following options that can customise the behaviour the +NERD tree. These options should be set in your vimrc. + +|'loaded_nerd_tree'| Turns off the script. + +|'NERDTreeAutoCenter'| Controls whether the NERD tree window centers + when the cursor moves within a specified + distance to the top/bottom of the window. + +|'NERDTreeAutoCenterThreshold'| Controls the sensitivity of autocentering. + +|'NERDTreeCaseSensitiveSort'| Tells the NERD tree whether to be case + sensitive or not when sorting nodes. + +|'NERDTreeNaturalSort'| Tells the NERD tree whether to use + natural sort order or not when sorting nodes. + +|'NERDTreeSortHiddenFirst'| Tells the NERD tree whether to take the dot + at the beginning of the hidden file names + into account when sorting nodes. + +|'NERDTreeChDirMode'| Tells the NERD tree if/when it should change + vim's current working directory. + +|'NERDTreeHighlightCursorline'| Tell the NERD tree whether to highlight the + current cursor line. + +|'NERDTreeHijackNetrw'| Tell the NERD tree whether to replace the netrw + autocommands for exploring local directories. + +|'NERDTreeIgnore'| Tells the NERD tree which files to ignore. + +|'NERDTreeRespectWildIgnore'| Tells the NERD tree to respect |'wildignore'|. + +|'NERDTreeBookmarksFile'| Where the bookmarks are stored. + +|'NERDTreeBookmarksSort'| Control how the Bookmark table is sorted. + +|'NERDTreeMarkBookmarks'| Render bookmarked nodes with markers. + +|'NERDTreeMouseMode'| Manage the interpretation of mouse clicks. + +|'NERDTreeQuitOnOpen'| Closes the tree window after opening a file. + +|'NERDTreeShowBookmarks'| Tells the NERD tree whether to display the + bookmarks table on startup. + +|'NERDTreeShowFiles'| Tells the NERD tree whether to display files + in the tree on startup. + +|'NERDTreeShowHidden'| Tells the NERD tree whether to display hidden + files on startup. + +|'NERDTreeShowLineNumbers'| Tells the NERD tree whether to display line + numbers in the tree window. + +|'NERDTreeSortOrder'| Tell the NERD tree how to sort the nodes in + the tree. + +|'NERDTreeStatusline'| Set a statusline for NERD tree windows. + +|'NERDTreeWinPos'| Tells the script where to put the NERD tree + window. + +|'NERDTreeWinSize'| Sets the window size when the NERD tree is + opened. + +|'NERDTreeMinimalUI'| Disables display of the 'Bookmarks' label and + 'Press ? for help' text. + +|'NERDTreeCascadeSingleChildDir'| + Collapses on the same line directories that + have only one child directory. + +|'NERDTreeCascadeOpenSingleChildDir'| + Cascade open while selected directory has only + one child that also is a directory. + +|'NERDTreeAutoDeleteBuffer'| Tells the NERD tree to automatically remove + a buffer when a file is being deleted or renamed + via a context menu command. + +|'NERDTreeCreatePrefix'| Specify a prefix to be used when creating the + NERDTree window. + +|'NERDTreeRemoveFileCmd'| Specify a custom shell command to be used when + deleting files. Note that it should include + one space character at the end of the command + and it applies only to files. + +|'NERDTreeRemoveDirCmd'| Specify a custom shell command to be used when + deleting directories. Note that it should + include one space character at the end of the + command and it applies only to directories. + +------------------------------------------------------------------------------ +3.2. Customisation details *NERDTreeOptionDetails* + +To enable any of the below options you should put the given line in your +~/.vimrc + + *'loaded_nerd_tree'* +If this plugin is making you feel homicidal, it may be a good idea to turn it +off with this line in your vimrc: > + let loaded_nerd_tree=1 +< + +------------------------------------------------------------------------------ + *'NERDTreeAutoCenter'* +Values: 0 or 1. +Default: 1 + +If set to 1, the NERD tree window will center around the cursor if it moves to +within |'NERDTreeAutoCenterThreshold'| lines of the top/bottom of the window. + +This is ONLY done in response to tree navigation mappings, +i.e. |NERDTree-J| |NERDTree-K| |NERDTree-C-J| |NERDTree-C-K| |NERDTree-p| +|NERDTree-P| + +The centering is done with a |zz| operation. + +------------------------------------------------------------------------------ + *'NERDTreeAutoCenterThreshold'* +Values: Any natural number. +Default: 3 + +This option controls the "sensitivity" of the NERD tree auto centering. See +|'NERDTreeAutoCenter'| for details. + +------------------------------------------------------------------------------ + *'NERDTreeCaseSensitiveSort'* +Values: 0 or 1. +Default: 0. + +By default the NERD tree does not sort nodes case sensitively, i.e. nodes +could appear like this: > + bar.c + Baz.c + blarg.c + boner.c + Foo.c +< +But, if you set this option to 1 then the case of the nodes will be taken into +account. The above nodes would then be sorted like this: > + Baz.c + Foo.c + bar.c + blarg.c + boner.c +< +------------------------------------------------------------------------------ + *'NERDTreeNaturalSort'* +Values: 0 or 1. +Default: 0. + +By default the NERD tree does not sort nodes in natural sort order, i.e. nodes +could appear like this: > + z1.txt + z10.txt + z100.txt + z11.txt + z110.txt + z2.txt + z20.txt + z3.txt +< +But if you set this option to 1 then the natural sort order will be used. The +above nodes would then be sorted like this: > + z1.txt + z2.txt + z3.txt + z10.txt + z11.txt + z20.txt + z100.txt + z110.txt +< +------------------------------------------------------------------------------ + *'NERDTreeChDirMode'* + +Values: 0, 1 or 2. +Default: 0. + +Use this option to tell the script when (if at all) to change the current +working directory (CWD) for vim. + +If it is set to 0 then the CWD is never changed by the NERD tree. + +If set to 1 then the CWD is changed when the NERD tree is first loaded to the +directory it is initialized in. For example, if you start the NERD tree with > + :NERDTree /home/marty/foobar +< +then the CWD will be changed to /home/marty/foobar and will not be changed +again unless you init another NERD tree with a similar command. + +If the option is set to 2 then it behaves the same as if set to 1 except that +the CWD is changed whenever the tree root is changed. For example, if the CWD +is /home/marty/foobar and you make the node for /home/marty/foobar/baz the new +root then the CWD will become /home/marty/foobar/baz. + +------------------------------------------------------------------------------ + *'NERDTreeHighlightCursorline'* +Values: 0 or 1. +Default: 1. + +If set to 1, the current cursor line in the NERD tree buffer will be +highlighted. This is done using the |'cursorline'| option. + +------------------------------------------------------------------------------ + *'NERDTreeHijackNetrw'* +Values: 0 or 1. +Default: 1. + +If set to 1, doing a > + :edit +< +will open up a window level NERD tree instead of a netrw in the target window. + +Window level trees behaves slightly different from a regular trees in the +following respects: + 1. 'o' will open the selected file in the same window as the tree, + replacing it. + 2. you can have one tree per window - instead of per tab. + +------------------------------------------------------------------------------ + *'NERDTreeIgnore'* +Values: a list of regular expressions. +Default: ['\~$']. + +This option is used to specify which files the NERD tree should ignore. It +must be a list of regular expressions. When the NERD tree is rendered, any +files/dirs that match any of the regex's in 'NERDTreeIgnore' wont be +displayed. + +For example if you put the following line in your vimrc: > + let NERDTreeIgnore=['\.vim$', '\~$'] +< +then all files ending in .vim or ~ will be ignored. + +There are 2 magic flags that can be appended to the end of each regular +expression to specify that the regex should match only files or only dirs. +These flags are "[[dir]]" and "[[file]]". Example: > + let NERDTreeIgnore=['\.d$[[dir]]', '\.o$[[file]]'] +< +This will cause all dirs ending in ".d" to be ignored and all files ending in +".o" to be ignored. + +Note: to tell the NERD tree not to ignore any files you must use the following +line: > + let NERDTreeIgnore=[] +< + +The file filters can be turned on and off dynamically with the |NERDTree-f| +mapping. + +------------------------------------------------------------------------------ + *'NERDTreeRespectWildIgnore'* +Values: 0 or 1. +Default: 0. + +If set to 1, the |'wildignore'| setting is respected. + +------------------------------------------------------------------------------ + *'NERDTreeBookmarksFile'* +Values: a path +Default: $HOME/.NERDTreeBookmarks + +This is where bookmarks are saved. See |NERDTreeBookmarkCommands|. + +------------------------------------------------------------------------------ + *'NERDTreeBookmarksSort'* +Values: 0, 1, or 2 +Default: 1 + +This option controls the method by which the list of user bookmarks is +sorted. When sorted, bookmarks will render in alphabetical order by name. + +If set to 0, the bookmarks list is not sorted. +If set to 1, the bookmarks list is sorted in a case-insensitive manner. +If set to 2, the bookmarks list is sorted in a case-sensitive manner. + +------------------------------------------------------------------------------ + *'NERDTreeMarkBookmarks'* +Values: 0 or 1 +Default: 1 + +If set to 1, Bookmarks will be specially marked whenever the NERDTree is +rendered. Users of the |'NERDTreeMinimalUI'| setting may prefer to disable +this setting for even less visual clutter. + +------------------------------------------------------------------------------ + *'NERDTreeMouseMode'* +Values: 1, 2 or 3. +Default: 1. + +If set to 1 then a double click on a node is required to open it. +If set to 2 then a single click will open directory nodes, while a double +click will still be required for file nodes. +If set to 3 then a single click will open any node. + +Note: a double click anywhere on a line that a tree node is on will +activate it, but all single-click activations must be done on name of the node +itself. For example, if you have the following node: > + | | |-application.rb +< +then (to single click activate it) you must click somewhere in +'application.rb'. + +------------------------------------------------------------------------------ + *'NERDTreeQuitOnOpen'* + +Values: 0 or 1. +Default: 0 + +If set to 1, the NERD tree window will close after opening a file with the +|NERDTree-o|, |NERDTree-i|, |NERDTree-t| and |NERDTree-T| mappings. + +------------------------------------------------------------------------------ + *'NERDTreeShowBookmarks'* +Values: 0 or 1. +Default: 0. + +If this option is set to 1 then the bookmarks table will be displayed. + +This option can be toggled dynamically, per tree, with the |NERDTree-B| +mapping. + +------------------------------------------------------------------------------ + *'NERDTreeShowFiles'* +Values: 0 or 1. +Default: 1. + +If this option is set to 1 then files are displayed in the NERD tree. If it is +set to 0 then only directories are displayed. + +This option can be toggled dynamically, per tree, with the |NERDTree-F| +mapping and is useful for drastically shrinking the tree when you are +navigating to a different part of the tree. + +------------------------------------------------------------------------------ + *'NERDTreeShowHidden'* +Values: 0 or 1. +Default: 0. + +This option tells vim whether to display hidden files by default. This option +can be dynamically toggled, per tree, with the |NERDTree-I| mapping. Use one +of the follow lines to set this option: > + let NERDTreeShowHidden=0 + let NERDTreeShowHidden=1 +< + +------------------------------------------------------------------------------ + *'NERDTreeShowLineNumbers'* +Values: 0 or 1. +Default: 0. + +This option tells vim whether to display line numbers for the NERD tree +window. Use one of the follow lines to set this option: > + let NERDTreeShowLineNumbers=0 + let NERDTreeShowLineNumbers=1 +< + +------------------------------------------------------------------------------ + *'NERDTreeSortOrder'* +Values: a list of regular expressions. +Default: ['\/$', '*', '\.swp$', '\.bak$', '\~$'] + +This option is set to a list of regular expressions which are used to +specify the order of nodes under their parent. + +For example, if the option is set to: > + ['\.vim$', '\.c$', '\.h$', '*', 'foobar'] +< +then all .vim files will be placed at the top, followed by all .c files then +all .h files. All files containing the string 'foobar' will be placed at the +end. The star is a special flag: it tells the script that every node that +doesnt match any of the other regexps should be placed here. + +If no star is present in 'NERDTreeSortOrder' then one is automatically +appended to the array. + +The regex '\/$' should be used to match directory nodes. + +After this sorting is done, the files in each group are sorted alphabetically. + +Other examples: > + (1) ['*', '\/$'] + (2) [] + (3) ['\/$', '\.rb$', '\.php$', '*', '\.swp$', '\.bak$', '\~$'] +< +1. Directories will appear last, everything else will appear above. +2. Everything will simply appear in alphabetical order. +3. Dirs will appear first, then ruby and php. Swap files, bak files and vim + backup files will appear last with everything else preceding them. + +------------------------------------------------------------------------------ + *'NERDTreeStatusline'* +Values: Any valid |'statusline'| setting. +Default: %{exists('b:NERDTree')?b:NERDTree.root.path.str():''} + +Defines the value for the |'statusline'| setting in NERDTree windows. + +Note: The setting is actually applied using |:let-&|, not |:set|, so +escaping spaces is not necessary. + +Setting this option to -1 will will deactivate it so that your global +|'statusline'| setting is used. + +------------------------------------------------------------------------------ + *'NERDTreeWinPos'* +Values: "left" or "right" +Default: "left". + +This option is used to determine where NERD tree window is placed on the +screen. + +This option makes it possible to use two different explorer plugins +simultaneously. For example, you could have the taglist plugin on the left of +the window and the NERD tree on the right. + +------------------------------------------------------------------------------ + *'NERDTreeWinSize'* +Values: a positive integer. +Default: 31. + +This option is used to change the size of the NERD tree when it is loaded. + +------------------------------------------------------------------------------ + *'NERDTreeMinimalUI'* +Values: 0 or 1 +Default: 0 + +This options disables the 'Bookmarks' label 'Press ? for help' text. Use one +of the following lines to set this option: > + let NERDTreeMinimalUI=0 + let NERDTreeMinimalUI=1 +< + +------------------------------------------------------------------------------ + *'NERDTreeCascadeSingleChildDir'* +Values: 0 or 1 +Default: 1. + +When displaying dir nodes, this option tells NERDTree to collapse dirs that +have only one child. Use one of the follow lines to set this option: > + let NERDTreeCascadeSingleChildDir=0 + let NERDTreeCascadeSingleChildDir=1 +< + +------------------------------------------------------------------------------ + *'NERDTreeCascadeOpenSingleChildDir'* +Values: 0 or 1 +Default: 1. + +When opening dir nodes, this option tells NERDTree to recursively open dirs +that have only one child which is also a dir. NERDTree will stop when it finds +a dir that contains anything but another single dir. This option also causes +the |NERDTree-x| mapping to close dirs in the same manner. This option may be +useful for Java projects. Use one of the follow lines to set this option: > + let NERDTreeCascadeOpenSingleChildDir=0 + let NERDTreeCascadeOpenSingleChildDir=1 +< + +------------------------------------------------------------------------------ + *'NERDTreeAutoDeleteBuffer'* +Values: 0 or 1 +Default: 0. + +When using a context menu to delete or rename a file you may also want to delete +the buffer which is no more valid. If the option is not set you will see a +confirmation if you really want to delete an old buffer. If you always press 'y' +then it worths to set this option to 1. Use one of the follow lines to set this +option: > + let NERDTreeAutoDeleteBuffer=0 + let NERDTreeAutoDeleteBuffer=1 +< +------------------------------------------------------------------------------ + *'NERDTreeCreatePrefix'* +Values: Any valid command prefix. +Default: "silent". + +Internally, NERDTree uses the |:edit| command to create a buffer in which to +display its tree view. You can augment this behavior by specifying a prefix +string such as "keepalt" or similar. For example, to have NERDTree create its +tree window using `silent keepalt keepjumps edit`: + let NERDTreeCreatePrefix='silent keepalt keepjumps' +< + +============================================================================== +4. The NERD tree API *NERDTreeAPI* + +The NERD tree script allows you to add custom key mappings and menu items via +a set of API calls. Any scripts that use this API should be placed in +~/.vim/nerdtree_plugin/ (*nix) or ~/vimfiles/nerdtree_plugin (windows). + +The script exposes some prototype objects that can be used to manipulate the +tree and/or get information from it: > + g:NERDTreePath + g:NERDTreeDirNode + g:NERDTreeFileNode + g:NERDTreeBookmark +< +See the code/comments in NERD_tree.vim to find how to use these objects. The +following code conventions are used: + * class members start with a capital letter + * instance members start with a lower case letter + * private members start with an underscore + +See this blog post for more details: + http://got-ravings.blogspot.com/2008/09/vim-pr0n-prototype-based-objects.html + +------------------------------------------------------------------------------ +4.1. Key map API *NERDTreeKeymapAPI* + +NERDTreeAddKeyMap({options}) *NERDTreeAddKeyMap()* + Adds a new keymapping for all NERD tree buffers. + {options} must be a dictionary, and must contain the following keys: + "key" - the trigger key for the new mapping + "callback" - the function the new mapping will be bound to + "quickhelpText" - the text that will appear in the quickhelp (see + |NERDTree-?|) + "override" - if 1 then this new mapping will override whatever previous + mapping was defined for the key/scope combo. Useful for overriding the + default mappings. + + Additionally, a "scope" argument may be supplied. This constrains the + mapping so that it is only activated if the cursor is on a certain object. + That object is then passed into the handling method. Possible values are: + + "FileNode" .... a file node + "DirNode" ..... a directory node + "Node" ........ a file node OR a directory node + "Bookmark" .... a bookmark + "all" ......... global scope; handler receives no arguments (default) + + Example: > + call NERDTreeAddKeyMap({ + \ 'key': 'foo', + \ 'callback': 'NERDTreeCDHandler', + \ 'quickhelpText': 'echo full path of current node', + \ 'scope': 'DirNode' }) + + function! NERDTreeCDHandler(dirnode) + call a:dirnode.changeToDir() + endfunction +< + This code should sit in a file like ~/.vim/nerdtree_plugin/mymapping.vim. + It adds a (redundant) mapping on 'foo' which changes vim's CWD to that of + the current dir node. Note this mapping will only fire when the cursor is + on a directory node. + +------------------------------------------------------------------------------ +4.2. Menu API *NERDTreeMenuAPI* + +NERDTreeAddSubmenu({options}) *NERDTreeAddSubmenu()* + Creates and returns a new submenu. + + {options} must be a dictionary and must contain the following keys: + "text" - the text of the submenu that the user will see + "shortcut" - a shortcut key for the submenu (need not be unique) + + The following keys are optional: + "isActiveCallback" - a function that will be called to determine whether + this submenu item will be displayed or not. The callback function must return + 0 or 1. + "parent" - the parent submenu of the new submenu (returned from a previous + invocation of NERDTreeAddSubmenu()). If this key is left out then the new + submenu will sit under the top level menu. + + See below for an example. + +NERDTreeAddMenuItem({options}) *NERDTreeAddMenuItem()* + Adds a new menu item to the NERD tree menu (see |NERDTreeMenu|). + + {options} must be a dictionary and must contain the + following keys: + "text" - the text of the menu item which the user will see + "shortcut" - a shortcut key for the menu item (need not be unique) + "callback" - the function that will be called when the user activates the + menu item. + + The following keys are optional: + "isActiveCallback" - a function that will be called to determine whether + this menu item will be displayed or not. The callback function must return + 0 or 1. + "parent" - if the menu item belongs under a submenu then this key must be + specified. This value for this key will be the object that + was returned when the submenu was created with |NERDTreeAddSubmenu()|. + + See below for an example. + +NERDTreeAddMenuSeparator([{options}]) *NERDTreeAddMenuSeparator()* + Adds a menu separator (a row of dashes). + + {options} is an optional dictionary that may contain the following keys: + "isActiveCallback" - see description in |NERDTreeAddMenuItem()|. + +Below is an example of the menu API in action. > + call NERDTreeAddMenuSeparator() + + call NERDTreeAddMenuItem({ + \ 'text': 'a (t)op level menu item', + \ 'shortcut': 't', + \ 'callback': 'SomeFunction' }) + + let submenu = NERDTreeAddSubmenu({ + \ 'text': 'a (s)ub menu', + \ 'shortcut': 's' }) + + call NERDTreeAddMenuItem({ + \ 'text': '(n)ested item 1', + \ 'shortcut': 'n', + \ 'callback': 'SomeFunction', + \ 'parent': submenu }) + + call NERDTreeAddMenuItem({ + \ 'text': '(n)ested item 2', + \ 'shortcut': 'n', + \ 'callback': 'SomeFunction', + \ 'parent': submenu }) +< +This will create the following menu: > + -------------------- + a (t)op level menu item + a (s)ub menu +< +Where selecting "a (s)ub menu" will lead to a second menu: > + (n)ested item 1 + (n)ested item 2 +< +When any of the 3 concrete menu items are selected the function "SomeFunction" +will be called. + +------------------------------------------------------------------------------ +4.3 NERDTreeAddPathFilter(callback) *NERDTreeAddPathFilter()* + +Path filters are essentially a more powerful version of |NERDTreeIgnore|. +If the simple regex matching in |NERDTreeIgnore| is not enough then use +|NERDTreeAddPathFilter()| to add a callback function that paths will be +checked against when the decision to ignore them is made. Example > + + call NERDTreeAddPathFilter('MyFilter') + + function! MyFilter(params) + "params is a dict containing keys: 'nerdtree' and 'path' which are + "g:NERDTree and g:NERDTreePath objects + + "return 1 to ignore params['path'] or 0 otherwise + endfunction +< +------------------------------------------------------------------------------ +4.4 Path Listener API *NERDTreePathListenerAPI* + +Use this API if you want to run a callback for events on Path objects. E.G > + + call g:NERDTreePathNotifier.AddListener("init", "MyListener") + + ".... + + function! MyListener(event) + "This function will be called whenever a Path object is created. + + "a:event is an object that contains a bunch of relevant info - + "including the path in question. See lib/nerdtree/event.vim for details. + endfunction +< +Current events supported: + init ~ + refresh ~ + refreshFlags ~ + +------------------------------------------------------------------------------ +NERDTreeRender() *NERDTreeRender()* + Re-renders the NERD tree buffer. Useful if you change the state of the + tree and you want to it to be reflected in the UI. + +============================================================================== +5. About *NERDTreeAbout* + +The author of the NERD tree is a terrible terrible monster called Martyzilla +who gobbles up small children with milk and sugar for breakfast. + +He can be reached at martin.grenfell at gmail dot com. He would love to hear +from you, so feel free to send him suggestions and/or comments about this +plugin. Don't be shy --- the worst he can do is slaughter you and stuff you in +the fridge for later ;) + +The latest stable versions can be found at + http://www.vim.org/scripts/script.php?script_id=1658 + +The latest dev versions are on github + http://github.com/scrooloose/nerdtree + +============================================================================== +6. License *NERDTreeLicense* + +The NERD tree is released under the wtfpl. +See http://sam.zoy.org/wtfpl/COPYING. diff --git a/vim/plugins/nerdtree/nerdtree_plugin/exec_menuitem.vim b/vim/plugins/nerdtree/nerdtree_plugin/exec_menuitem.vim new file mode 100644 index 0000000..c53650a --- /dev/null +++ b/vim/plugins/nerdtree/nerdtree_plugin/exec_menuitem.vim @@ -0,0 +1,40 @@ +" ============================================================================ +" File: exec_menuitem.vim +" Description: plugin for NERD Tree that provides an execute file menu item +" Maintainer: Martin Grenfell +" License: This program is free software. It comes without any warranty, +" to the extent permitted by applicable law. You can redistribute +" it and/or modify it under the terms of the Do What The Fuck You +" Want To Public License, Version 2, as published by Sam Hocevar. +" See http://sam.zoy.org/wtfpl/COPYING for more details. +" +" ============================================================================ +if exists("g:loaded_nerdtree_exec_menuitem") + finish +endif +let g:loaded_nerdtree_exec_menuitem = 1 + +call NERDTreeAddMenuItem({ + \ 'text': '(!)Execute file', + \ 'shortcut': '!', + \ 'callback': 'NERDTreeExecFile', + \ 'isActiveCallback': 'NERDTreeExecFileActive' }) + +function! NERDTreeExecFileActive() + let node = g:NERDTreeFileNode.GetSelected() + return !node.path.isDirectory && node.path.isExecutable +endfunction + +function! NERDTreeExecFile() + let treenode = g:NERDTreeFileNode.GetSelected() + echo "==========================================================\n" + echo "Complete the command to execute (add arguments etc):\n" + let cmd = treenode.path.str({'escape': 1}) + let cmd = input(':!', cmd . ' ') + + if cmd != '' + exec ':!' . cmd + else + echo "Aborted" + endif +endfunction diff --git a/vim/plugins/nerdtree/nerdtree_plugin/fs_menu.vim b/vim/plugins/nerdtree/nerdtree_plugin/fs_menu.vim new file mode 100644 index 0000000..c9897ce --- /dev/null +++ b/vim/plugins/nerdtree/nerdtree_plugin/fs_menu.vim @@ -0,0 +1,365 @@ +" ============================================================================ +" File: fs_menu.vim +" Description: plugin for the NERD Tree that provides a file system menu +" Maintainer: Martin Grenfell +" License: This program is free software. It comes without any warranty, +" to the extent permitted by applicable law. You can redistribute +" it and/or modify it under the terms of the Do What The Fuck You +" Want To Public License, Version 2, as published by Sam Hocevar. +" See http://sam.zoy.org/wtfpl/COPYING for more details. +" +" ============================================================================ +if exists("g:loaded_nerdtree_fs_menu") + finish +endif +let g:loaded_nerdtree_fs_menu = 1 + +"Automatically delete the buffer after deleting or renaming a file +if !exists("g:NERDTreeAutoDeleteBuffer") + let g:NERDTreeAutoDeleteBuffer = 0 +endif + +call NERDTreeAddMenuItem({'text': '(a)dd a childnode', 'shortcut': 'a', 'callback': 'NERDTreeAddNode'}) +call NERDTreeAddMenuItem({'text': '(m)ove the current node', 'shortcut': 'm', 'callback': 'NERDTreeMoveNode'}) +call NERDTreeAddMenuItem({'text': '(d)elete the current node', 'shortcut': 'd', 'callback': 'NERDTreeDeleteNode'}) + +if has("gui_mac") || has("gui_macvim") || has("mac") + call NERDTreeAddMenuItem({'text': '(r)eveal in Finder the current node', 'shortcut': 'r', 'callback': 'NERDTreeRevealInFinder'}) + call NERDTreeAddMenuItem({'text': '(o)pen the current node with system editor', 'shortcut': 'o', 'callback': 'NERDTreeExecuteFile'}) + call NERDTreeAddMenuItem({'text': '(q)uicklook the current node', 'shortcut': 'q', 'callback': 'NERDTreeQuickLook'}) +endif + +if executable("xdg-open") + call NERDTreeAddMenuItem({'text': '(r)eveal the current node in file manager', 'shortcut': 'r', 'callback': 'NERDTreeRevealFileLinux'}) + call NERDTreeAddMenuItem({'text': '(o)pen the current node with system editor', 'shortcut': 'o', 'callback': 'NERDTreeExecuteFileLinux'}) +endif + +if g:NERDTreePath.CopyingSupported() + call NERDTreeAddMenuItem({'text': '(c)opy the current node', 'shortcut': 'c', 'callback': 'NERDTreeCopyNode'}) +endif + +if has("unix") || has("osx") + call NERDTreeAddMenuItem({'text': '(l)ist the current node', 'shortcut': 'l', 'callback': 'NERDTreeListNode'}) +else + call NERDTreeAddMenuItem({'text': '(l)ist the current node', 'shortcut': 'l', 'callback': 'NERDTreeListNodeWin32'}) +endif + +"FUNCTION: s:promptToDelBuffer(bufnum, msg){{{1 +"prints out the given msg and, if the user responds by pushing 'y' then the +"buffer with the given bufnum is deleted +" +"Args: +"bufnum: the buffer that may be deleted +"msg: a message that will be echoed to the user asking them if they wish to +" del the buffer +function! s:promptToDelBuffer(bufnum, msg) + echo a:msg + if g:NERDTreeAutoDeleteBuffer || nr2char(getchar()) ==# 'y' + " 1. ensure that all windows which display the just deleted filename + " now display an empty buffer (so a layout is preserved). + " Is not it better to close single tabs with this file only ? + let s:originalTabNumber = tabpagenr() + let s:originalWindowNumber = winnr() + " Go to the next buffer in buffer list if at least one extra buffer is listed + " Otherwise open a new empty buffer + if v:version >= 800 + let l:listedBufferCount = len(getbufinfo({'buflisted':1})) + elseif v:version >= 702 + let l:listedBufferCount = len(filter(range(1, bufnr('$')), 'buflisted(v:val)')) + else + " Ignore buffer count in this case to make sure we keep the old + " behavior + let l:listedBufferCount = 0 + endif + if l:listedBufferCount > 1 + exec "tabdo windo if winbufnr(0) == " . a:bufnum . " | exec ':bnext! ' | endif" + else + exec "tabdo windo if winbufnr(0) == " . a:bufnum . " | exec ':enew! ' | endif" + endif + exec "tabnext " . s:originalTabNumber + exec s:originalWindowNumber . "wincmd w" + " 3. We don't need a previous buffer anymore + exec "bwipeout! " . a:bufnum + endif +endfunction + +"FUNCTION: s:promptToRenameBuffer(bufnum, msg){{{1 +"prints out the given msg and, if the user responds by pushing 'y' then the +"buffer with the given bufnum is replaced with a new one +" +"Args: +"bufnum: the buffer that may be deleted +"msg: a message that will be echoed to the user asking them if they wish to +" del the buffer +function! s:promptToRenameBuffer(bufnum, msg, newFileName) + echo a:msg + if g:NERDTreeAutoDeleteBuffer || nr2char(getchar()) ==# 'y' + let quotedFileName = fnameescape(a:newFileName) + " 1. ensure that a new buffer is loaded + exec "badd " . quotedFileName + " 2. ensure that all windows which display the just deleted filename + " display a buffer for a new filename. + let s:originalTabNumber = tabpagenr() + let s:originalWindowNumber = winnr() + let editStr = g:NERDTreePath.New(a:newFileName).str({'format': 'Edit'}) + exec "tabdo windo if winbufnr(0) == " . a:bufnum . " | exec ':e! " . editStr . "' | endif" + exec "tabnext " . s:originalTabNumber + exec s:originalWindowNumber . "wincmd w" + " 3. We don't need a previous buffer anymore + exec "bwipeout! " . a:bufnum + endif +endfunction +"FUNCTION: NERDTreeAddNode(){{{1 +function! NERDTreeAddNode() + let curDirNode = g:NERDTreeDirNode.GetSelected() + + let newNodeName = input("Add a childnode\n". + \ "==========================================================\n". + \ "Enter the dir/file name to be created. Dirs end with a '/'\n" . + \ "", curDirNode.path.str() . g:NERDTreePath.Slash(), "file") + + if newNodeName ==# '' + call nerdtree#echo("Node Creation Aborted.") + return + endif + + try + let newPath = g:NERDTreePath.Create(newNodeName) + let parentNode = b:NERDTree.root.findNode(newPath.getParent()) + + let newTreeNode = g:NERDTreeFileNode.New(newPath, b:NERDTree) + if empty(parentNode) + call b:NERDTree.root.refresh() + call b:NERDTree.render() + elseif parentNode.isOpen || !empty(parentNode.children) + call parentNode.addChild(newTreeNode, 1) + call NERDTreeRender() + call newTreeNode.putCursorHere(1, 0) + endif + catch /^NERDTree/ + call nerdtree#echoWarning("Node Not Created.") + endtry +endfunction + +"FUNCTION: NERDTreeMoveNode(){{{1 +function! NERDTreeMoveNode() + let curNode = g:NERDTreeFileNode.GetSelected() + let newNodePath = input("Rename the current node\n" . + \ "==========================================================\n" . + \ "Enter the new path for the node: \n" . + \ "", curNode.path.str(), "file") + + if newNodePath ==# '' + call nerdtree#echo("Node Renaming Aborted.") + return + endif + + try + let bufnum = bufnr("^".curNode.path.str()."$") + + call curNode.rename(newNodePath) + call b:NERDTree.root.refresh() + call NERDTreeRender() + + "if the node is open in a buffer, ask the user if they want to + "close that buffer + if bufnum != -1 + let prompt = "\nNode renamed.\n\nThe old file is open in buffer ". bufnum . (bufwinnr(bufnum) ==# -1 ? " (hidden)" : "") .". Replace this buffer with the new file? (yN)" + call s:promptToRenameBuffer(bufnum, prompt, newNodePath) + endif + + call curNode.putCursorHere(1, 0) + + redraw + catch /^NERDTree/ + call nerdtree#echoWarning("Node Not Renamed.") + endtry +endfunction + +" FUNCTION: NERDTreeDeleteNode() {{{1 +function! NERDTreeDeleteNode() + let currentNode = g:NERDTreeFileNode.GetSelected() + let confirmed = 0 + + if currentNode.path.isDirectory && ((currentNode.isOpen && currentNode.getChildCount() > 0) || + \ (len(currentNode._glob('*', 1)) > 0)) + let choice =input("Delete the current node\n" . + \ "==========================================================\n" . + \ "STOP! Directory is not empty! To delete, type 'yes'\n" . + \ "" . currentNode.path.str() . ": ") + let confirmed = choice ==# 'yes' + else + echo "Delete the current node\n" . + \ "==========================================================\n". + \ "Are you sure you wish to delete the node:\n" . + \ "" . currentNode.path.str() . " (yN):" + let choice = nr2char(getchar()) + let confirmed = choice ==# 'y' + endif + + + if confirmed + try + call currentNode.delete() + call NERDTreeRender() + + "if the node is open in a buffer, ask the user if they want to + "close that buffer + let bufnum = bufnr("^".currentNode.path.str()."$") + if buflisted(bufnum) + let prompt = "\nNode deleted.\n\nThe file is open in buffer ". bufnum . (bufwinnr(bufnum) ==# -1 ? " (hidden)" : "") .". Delete this buffer? (yN)" + call s:promptToDelBuffer(bufnum, prompt) + endif + + redraw + catch /^NERDTree/ + call nerdtree#echoWarning("Could not remove node") + endtry + else + call nerdtree#echo("delete aborted") + endif + +endfunction + +" FUNCTION: NERDTreeListNode() {{{1 +function! NERDTreeListNode() + let treenode = g:NERDTreeFileNode.GetSelected() + if !empty(treenode) + let s:uname = system("uname") + let stat_cmd = 'stat -c "%s" ' + + if s:uname =~? "Darwin" + let stat_cmd = 'stat -f "%z" ' + endif + + let cmd = 'size=$(' . stat_cmd . shellescape(treenode.path.str()) . ') && ' . + \ 'size_with_commas=$(echo $size | sed -e :a -e "s/\(.*[0-9]\)\([0-9]\{3\}\)/\1,\2/;ta") && ' . + \ 'ls -ld ' . shellescape(treenode.path.str()) . ' | sed -e "s/ $size / $size_with_commas /"' + + let metadata = split(system(cmd),'\n') + call nerdtree#echo(metadata[0]) + else + call nerdtree#echo("No information available") + endif +endfunction + +" FUNCTION: NERDTreeListNodeWin32() {{{1 +function! NERDTreeListNodeWin32() + let l:node = g:NERDTreeFileNode.GetSelected() + + if !empty(l:node) + + let l:save_shell = &shell + set shell& + + if exists('+shellslash') + let l:save_shellslash = &shellslash + set noshellslash + endif + + let l:command = 'DIR /Q ' + \ . shellescape(l:node.path.str()) + \ . ' | FINDSTR "^[012][0-9]/[0-3][0-9]/[12][0-9][0-9][0-9]"' + + let l:metadata = split(system(l:command), "\n") + + if v:shell_error == 0 + call nerdtree#echo(l:metadata[0]) + else + call nerdtree#echoError('shell command failed') + endif + + let &shell = l:save_shell + + if exists('l:save_shellslash') + let &shellslash = l:save_shellslash + endif + + return + endif + + call nerdtree#echo('node not recognized') +endfunction + +" FUNCTION: NERDTreeCopyNode() {{{1 +function! NERDTreeCopyNode() + let currentNode = g:NERDTreeFileNode.GetSelected() + let newNodePath = input("Copy the current node\n" . + \ "==========================================================\n" . + \ "Enter the new path to copy the node to: \n" . + \ "", currentNode.path.str(), "file") + + if newNodePath != "" + "strip trailing slash + let newNodePath = substitute(newNodePath, '\/$', '', '') + + let confirmed = 1 + if currentNode.path.copyingWillOverwrite(newNodePath) + call nerdtree#echo("Warning: copying may overwrite files! Continue? (yN)") + let choice = nr2char(getchar()) + let confirmed = choice ==# 'y' + endif + + if confirmed + try + let newNode = currentNode.copy(newNodePath) + if empty(newNode) + call b:NERDTree.root.refresh() + call b:NERDTree.render() + else + call NERDTreeRender() + call newNode.putCursorHere(0, 0) + endif + catch /^NERDTree/ + call nerdtree#echoWarning("Could not copy node") + endtry + endif + else + call nerdtree#echo("Copy aborted.") + endif + redraw +endfunction + +" FUNCTION: NERDTreeQuickLook() {{{1 +function! NERDTreeQuickLook() + let treenode = g:NERDTreeFileNode.GetSelected() + if treenode != {} + call system("qlmanage -p 2>/dev/null '" . treenode.path.str() . "'") + endif +endfunction + +" FUNCTION: NERDTreeRevealInFinder() {{{1 +function! NERDTreeRevealInFinder() + let treenode = g:NERDTreeFileNode.GetSelected() + if treenode != {} + call system("open -R '" . treenode.path.str() . "'") + endif +endfunction + +" FUNCTION: NERDTreeExecuteFile() {{{1 +function! NERDTreeExecuteFile() + let treenode = g:NERDTreeFileNode.GetSelected() + if treenode != {} + call system("open '" . treenode.path.str() . "'") + endif +endfunction + +" FUNCTION: NERDTreeRevealFileLinux() {{{1 +function! NERDTreeRevealFileLinux() + let treenode = g:NERDTreeFileNode.GetSelected() + let parentnode = treenode.parent + if parentnode != {} + call system("xdg-open '" . parentnode.path.str() . "' &") + endif +endfunction + +" FUNCTION: NERDTreeExecuteFileLinux() {{{1 +function! NERDTreeExecuteFileLinux() + let treenode = g:NERDTreeFileNode.GetSelected() + if treenode != {} + call system("xdg-open '" . treenode.path.str() . "' &") + endif +endfunction + +" vim: set sw=4 sts=4 et fdm=marker: + diff --git a/vim/plugins/nerdtree/plugin/NERD_tree.vim b/vim/plugins/nerdtree/plugin/NERD_tree.vim new file mode 100644 index 0000000..71d719a --- /dev/null +++ b/vim/plugins/nerdtree/plugin/NERD_tree.vim @@ -0,0 +1,219 @@ +" ============================================================================ +" File: NERD_tree.vim +" Maintainer: Martin Grenfell +" License: This program is free software. It comes without any warranty, +" to the extent permitted by applicable law. You can redistribute +" it and/or modify it under the terms of the Do What The Fuck You +" Want To Public License, Version 2, as published by Sam Hocevar. +" See http://sam.zoy.org/wtfpl/COPYING for more details. +" +" ============================================================================ +" +" SECTION: Script init stuff {{{1 +"============================================================ +if exists("loaded_nerd_tree") + finish +endif +if v:version < 700 + echoerr "NERDTree: this plugin requires vim >= 7. DOWNLOAD IT! You'll thank me later!" + finish +endif +let loaded_nerd_tree = 1 + +"for line continuation - i.e dont want C in &cpo +let s:old_cpo = &cpo +set cpo&vim + +"Function: s:initVariable() function {{{2 +"This function is used to initialise a given variable to a given value. The +"variable is only initialised if it does not exist prior +" +"Args: +"var: the name of the var to be initialised +"value: the value to initialise var to +" +"Returns: +"1 if the var is set, 0 otherwise +function! s:initVariable(var, value) + if !exists(a:var) + exec 'let ' . a:var . ' = ' . "'" . substitute(a:value, "'", "''", "g") . "'" + return 1 + endif + return 0 +endfunction + +"SECTION: Init variable calls and other random constants {{{2 +call s:initVariable("g:NERDTreeAutoCenter", 1) +call s:initVariable("g:NERDTreeAutoCenterThreshold", 3) +call s:initVariable("g:NERDTreeCaseSensitiveSort", 0) +call s:initVariable("g:NERDTreeNaturalSort", 0) +call s:initVariable("g:NERDTreeSortHiddenFirst", 1) +call s:initVariable("g:NERDTreeChDirMode", 0) +call s:initVariable("g:NERDTreeCreatePrefix", "silent") +call s:initVariable("g:NERDTreeMinimalUI", 0) +if !exists("g:NERDTreeIgnore") + let g:NERDTreeIgnore = ['\~$'] +endif +call s:initVariable("g:NERDTreeBookmarksFile", expand('$HOME') . '/.NERDTreeBookmarks') +call s:initVariable("g:NERDTreeBookmarksSort", 1) +call s:initVariable("g:NERDTreeHighlightCursorline", 1) +call s:initVariable("g:NERDTreeHijackNetrw", 1) +call s:initVariable('g:NERDTreeMarkBookmarks', 1) +call s:initVariable("g:NERDTreeMouseMode", 1) +call s:initVariable("g:NERDTreeNotificationThreshold", 100) +call s:initVariable("g:NERDTreeQuitOnOpen", 0) +call s:initVariable("g:NERDTreeRespectWildIgnore", 0) +call s:initVariable("g:NERDTreeShowBookmarks", 0) +call s:initVariable("g:NERDTreeShowFiles", 1) +call s:initVariable("g:NERDTreeShowHidden", 0) +call s:initVariable("g:NERDTreeShowLineNumbers", 0) +call s:initVariable("g:NERDTreeSortDirs", 1) + +if !nerdtree#runningWindows() && !nerdtree#runningCygwin() + call s:initVariable("g:NERDTreeDirArrowExpandable", "▸") + call s:initVariable("g:NERDTreeDirArrowCollapsible", "▾") +else + call s:initVariable("g:NERDTreeDirArrowExpandable", "+") + call s:initVariable("g:NERDTreeDirArrowCollapsible", "~") +endif +call s:initVariable("g:NERDTreeCascadeOpenSingleChildDir", 1) +call s:initVariable("g:NERDTreeCascadeSingleChildDir", 1) + +if !exists("g:NERDTreeSortOrder") + let g:NERDTreeSortOrder = ['\/$', '*', '\.swp$', '\.bak$', '\~$'] +endif +let g:NERDTreeOldSortOrder = [] + +call s:initVariable("g:NERDTreeGlyphReadOnly", "RO") + +if !exists('g:NERDTreeStatusline') + + "the exists() crap here is a hack to stop vim spazzing out when + "loading a session that was created with an open nerd tree. It spazzes + "because it doesnt store b:NERDTree(its a b: var, and its a hash) + let g:NERDTreeStatusline = "%{exists('b:NERDTree')?b:NERDTree.root.path.str():''}" + +endif +call s:initVariable("g:NERDTreeWinPos", "left") +call s:initVariable("g:NERDTreeWinSize", 31) + +"init the shell commands that will be used to copy nodes, and remove dir trees +" +"Note: the space after the command is important +if nerdtree#runningWindows() + call s:initVariable("g:NERDTreeRemoveDirCmd", 'rmdir /s /q ') + call s:initVariable("g:NERDTreeCopyDirCmd", 'xcopy /s /e /i /y /q ') + call s:initVariable("g:NERDTreeCopyFileCmd", 'copy /y ') +else + call s:initVariable("g:NERDTreeRemoveDirCmd", 'rm -rf ') + call s:initVariable("g:NERDTreeCopyCmd", 'cp -r ') +endif + + +"SECTION: Init variable calls for key mappings {{{2 +call s:initVariable("g:NERDTreeMapActivateNode", "o") +call s:initVariable("g:NERDTreeMapChangeRoot", "C") +call s:initVariable("g:NERDTreeMapChdir", "cd") +call s:initVariable("g:NERDTreeMapCloseChildren", "X") +call s:initVariable("g:NERDTreeMapCloseDir", "x") +call s:initVariable("g:NERDTreeMapDeleteBookmark", "D") +call s:initVariable("g:NERDTreeMapMenu", "m") +call s:initVariable("g:NERDTreeMapHelp", "?") +call s:initVariable("g:NERDTreeMapJumpFirstChild", "K") +call s:initVariable("g:NERDTreeMapJumpLastChild", "J") +call s:initVariable("g:NERDTreeMapJumpNextSibling", "") +call s:initVariable("g:NERDTreeMapJumpParent", "p") +call s:initVariable("g:NERDTreeMapJumpPrevSibling", "") +call s:initVariable("g:NERDTreeMapJumpRoot", "P") +call s:initVariable("g:NERDTreeMapOpenExpl", "e") +call s:initVariable("g:NERDTreeMapOpenInTab", "t") +call s:initVariable("g:NERDTreeMapOpenInTabSilent", "T") +call s:initVariable("g:NERDTreeMapOpenRecursively", "O") +call s:initVariable("g:NERDTreeMapOpenSplit", "i") +call s:initVariable("g:NERDTreeMapOpenVSplit", "s") +call s:initVariable("g:NERDTreeMapPreview", "g" . NERDTreeMapActivateNode) +call s:initVariable("g:NERDTreeMapPreviewSplit", "g" . NERDTreeMapOpenSplit) +call s:initVariable("g:NERDTreeMapPreviewVSplit", "g" . NERDTreeMapOpenVSplit) +call s:initVariable("g:NERDTreeMapQuit", "q") +call s:initVariable("g:NERDTreeMapRefresh", "r") +call s:initVariable("g:NERDTreeMapRefreshRoot", "R") +call s:initVariable("g:NERDTreeMapToggleBookmarks", "B") +call s:initVariable("g:NERDTreeMapToggleFiles", "F") +call s:initVariable("g:NERDTreeMapToggleFilters", "f") +call s:initVariable("g:NERDTreeMapToggleHidden", "I") +call s:initVariable("g:NERDTreeMapToggleZoom", "A") +call s:initVariable("g:NERDTreeMapUpdir", "u") +call s:initVariable("g:NERDTreeMapUpdirKeepOpen", "U") +call s:initVariable("g:NERDTreeMapCWD", "CD") + +"SECTION: Load class files{{{2 +call nerdtree#loadClassFiles() + +" SECTION: Commands {{{1 +"============================================================ +call nerdtree#ui_glue#setupCommands() + +" SECTION: Auto commands {{{1 +"============================================================ +augroup NERDTree + "Save the cursor position whenever we close the nerd tree + exec "autocmd BufLeave ". g:NERDTreeCreator.BufNamePrefix() ."* if g:NERDTree.IsOpen() | call b:NERDTree.ui.saveScreenState() | endif" + + "disallow insert mode in the NERDTree + exec "autocmd BufEnter ". g:NERDTreeCreator.BufNamePrefix() ."* stopinsert" +augroup END + +if g:NERDTreeHijackNetrw + augroup NERDTreeHijackNetrw + autocmd VimEnter * silent! autocmd! FileExplorer + au BufEnter,VimEnter * call nerdtree#checkForBrowse(expand("")) + augroup END +endif + +" SECTION: Public API {{{1 +"============================================================ +function! NERDTreeAddMenuItem(options) + call g:NERDTreeMenuItem.Create(a:options) +endfunction + +function! NERDTreeAddMenuSeparator(...) + let opts = a:0 ? a:1 : {} + call g:NERDTreeMenuItem.CreateSeparator(opts) +endfunction + +function! NERDTreeAddSubmenu(options) + return g:NERDTreeMenuItem.Create(a:options) +endfunction + +function! NERDTreeAddKeyMap(options) + call g:NERDTreeKeyMap.Create(a:options) +endfunction + +function! NERDTreeRender() + call nerdtree#renderView() +endfunction + +function! NERDTreeFocus() + if g:NERDTree.IsOpen() + call g:NERDTree.CursorToTreeWin() + else + call g:NERDTreeCreator.ToggleTabTree("") + endif +endfunction + +function! NERDTreeCWD() + call NERDTreeFocus() + call nerdtree#ui_glue#chRootCwd() +endfunction + +function! NERDTreeAddPathFilter(callback) + call g:NERDTree.AddPathFilter(a:callback) +endfunction + +" SECTION: Post Source Actions {{{1 +call nerdtree#postSourceActions() + +"reset &cpo back to users setting +let &cpo = s:old_cpo + +" vim: set sw=4 sts=4 et fdm=marker: diff --git a/vim/plugins/nerdtree/screenshot.png b/vim/plugins/nerdtree/screenshot.png new file mode 100644 index 0000000000000000000000000000000000000000..c410c5dbb648c394dc74b90393939aa0ea252bb2 GIT binary patch literal 87896 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�OkEM>-if5oLqld#XMc7@CEE>NzgY860qx#tdl$~ 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
  • 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 F{67l|-0c7W literal 0 HcmV?d00001 diff --git a/vim/plugins/nerdtree/syntax/nerdtree.vim b/vim/plugins/nerdtree/syntax/nerdtree.vim new file mode 100644 index 0000000..7c80605 --- /dev/null +++ b/vim/plugins/nerdtree/syntax/nerdtree.vim @@ -0,0 +1,82 @@ +let s:tree_up_dir_line = '.. (up a dir)' +syn match NERDTreeIgnore #\~# +exec 'syn match NERDTreeIgnore #\['.g:NERDTreeGlyphReadOnly.'\]#' + +"highlighting for the .. (up dir) line at the top of the tree +execute "syn match NERDTreeUp #\\V". s:tree_up_dir_line ."#" + +"quickhelp syntax elements +syn match NERDTreeHelpKey #" \{1,2\}[^ ]*:#ms=s+2,me=e-1 +syn match NERDTreeHelpKey #" \{1,2\}[^ ]*,#ms=s+2,me=e-1 +syn match NERDTreeHelpTitle #" .*\~$#ms=s+2,me=e-1 +syn match NERDTreeToggleOn #(on)#ms=s+1,he=e-1 +syn match NERDTreeToggleOff #(off)#ms=e-3,me=e-1 +syn match NERDTreeHelpCommand #" :.\{-}\>#hs=s+3 +syn match NERDTreeHelp #^".*# contains=NERDTreeHelpKey,NERDTreeHelpTitle,NERDTreeIgnore,NERDTreeToggleOff,NERDTreeToggleOn,NERDTreeHelpCommand + +"highlighting for sym links +syn match NERDTreeLinkTarget #->.*# containedin=NERDTreeDir,NERDTreeFile +syn match NERDTreeLinkFile #.* ->#me=e-3 containedin=NERDTreeFile +syn match NERDTreeLinkDir #.*/ ->#me=e-3 containedin=NERDTreeDir + +"highlighing for directory nodes and file nodes +syn match NERDTreeDirSlash #/# containedin=NERDTreeDir + +exec 'syn match NERDTreeClosable #' . escape(g:NERDTreeDirArrowCollapsible, '~') . '\ze .*/# containedin=NERDTreeDir,NERDTreeFile' +exec 'syn match NERDTreeOpenable #' . escape(g:NERDTreeDirArrowExpandable, '~') . '\ze .*/# containedin=NERDTreeDir,NERDTreeFile' + +let s:dirArrows = escape(g:NERDTreeDirArrowCollapsible, '~]\-').escape(g:NERDTreeDirArrowExpandable, '~]\-') +exec 'syn match NERDTreeDir #[^'.s:dirArrows.' ].*/#' +syn match NERDTreeExecFile #^ .*\*\($\| \)# contains=NERDTreeRO,NERDTreeBookmark +exec 'syn match NERDTreeFile #^[^"\.'.s:dirArrows.'] *[^'.s:dirArrows.']*# contains=NERDTreeLink,NERDTreeRO,NERDTreeBookmark,NERDTreeExecFile' + +"highlighting for readonly files +exec 'syn match NERDTreeRO # *\zs.*\ze \['.g:NERDTreeGlyphReadOnly.'\]# contains=NERDTreeIgnore,NERDTreeBookmark,NERDTreeFile' + +syn match NERDTreeFlags #^ *\zs\[.\]# containedin=NERDTreeFile,NERDTreeExecFile +syn match NERDTreeFlags #\[.\]# containedin=NERDTreeDir + +syn match NERDTreeCWD #^[# +syn match NERDTreeBookmarksHeader #^>-\+Bookmarks-\+$# contains=NERDTreeBookmarksLeader +syn match NERDTreeBookmarkName #^>.\{-} #he=e-1 contains=NERDTreeBookmarksLeader +syn match NERDTreeBookmark #^>.*$# contains=NERDTreeBookmarksLeader,NERDTreeBookmarkName,NERDTreeBookmarksHeader + +hi def link NERDTreePart Special +hi def link NERDTreePartFile Type +hi def link NERDTreeExecFile Title +hi def link NERDTreeDirSlash Identifier + +hi def link NERDTreeBookmarksHeader statement +hi def link NERDTreeBookmarksLeader ignore +hi def link NERDTreeBookmarkName Identifier +hi def link NERDTreeBookmark normal + +hi def link NERDTreeHelp String +hi def link NERDTreeHelpKey Identifier +hi def link NERDTreeHelpCommand Identifier +hi def link NERDTreeHelpTitle Macro +hi def link NERDTreeToggleOn Question +hi def link NERDTreeToggleOff WarningMsg + +hi def link NERDTreeLinkTarget Type +hi def link NERDTreeLinkFile Macro +hi def link NERDTreeLinkDir Macro + +hi def link NERDTreeDir Directory +hi def link NERDTreeUp Directory +hi def link NERDTreeFile Normal +hi def link NERDTreeCWD Statement +hi def link NERDTreeOpenable Directory +hi def link NERDTreeClosable Directory +hi def link NERDTreeIgnore ignore +hi def link NERDTreeRO WarningMsg +hi def link NERDTreeBookmark Statement +hi def link NERDTreeFlags Number + +hi def link NERDTreeCurrentNode Search