diff --git a/nerdtree_plugin/webdevicons.vim b/nerdtree_plugin/webdevicons.vim index 0774819..b8c689f 100644 --- a/nerdtree_plugin/webdevicons.vim +++ b/nerdtree_plugin/webdevicons.vim @@ -88,10 +88,7 @@ function! WebDevIconsNERDTreeUpDirCurrentRootClosedHandler() redraw! endfunction -" NERDTreeMapActivateNode and <2-LeftMouse> -" handle the user activating a tree node -" scope: global -function! WebDevIconsNERDTreeMapActivateNode(node) +function! WebDevIconsNERDTreeDirUpdateFlags(node, glyph) let path = a:node.path let isOpen = a:node.isOpen let padding = g:WebDevIconsNerdTreeAfterGlyphPadding @@ -112,12 +109,7 @@ function! WebDevIconsNERDTreeMapActivateNode(node) let prePadding .= ' ' endif - " toggle flag - if isOpen - let flag = prePadding . g:WebDevIconsUnicodeDecorateFolderNodesDefaultSymbol . padding - else - let flag = prePadding . g:DevIconsDefaultFolderOpenSymbol . padding - endif + let flag = prePadding . a:glyph . padding call a:node.path.flagSet.clearFlags('webdevicons') @@ -125,15 +117,125 @@ function! WebDevIconsNERDTreeMapActivateNode(node) call a:node.path.flagSet.addFlag('webdevicons', flag) call a:node.path.refreshFlags(b:NERDTree) endif +endfunction + +function! WebDevIconsNERDTreeDirClose(node) + let a:node.path.isOpen = 0 + let glyph = g:WebDevIconsUnicodeDecorateFolderNodesDefaultSymbol + call WebDevIconsNERDTreeDirUpdateFlags(a:node, glyph) +endfunction + +function! WebDevIconsNERDTreeDirOpen(node) + let a:node.path.isOpen = 1 + let glyph = g:DevIconsDefaultFolderOpenSymbol + call WebDevIconsNERDTreeDirUpdateFlags(a:node, glyph) +endfunction + +function! WebDevIconsNERDTreeDirOpenRecursively(node) + call WebDevIconsNERDTreeDirOpen(a:node) + for i in a:node.children + if i.path.isDirectory ==# 1 + call WebDevIconsNERDTreeDirOpenRecursively(i) + endif + endfor +endfunction + +function! WebDevIconsNERDTreeDirCloseRecursively(node) + call WebDevIconsNERDTreeDirClose(a:node) + for i in a:node.children + if i.path.isDirectory ==# 1 + call WebDevIconsNERDTreeDirCloseRecursively(i) + endif + endfor +endfunction +function! WebDevIconsNERDTreeDirCloseChildren(node) + for i in a:node.children + if i.path.isDirectory ==# 1 + call WebDevIconsNERDTreeDirClose(i) + endif + endfor +endfunction + +" NERDTreeMapActivateNode and <2-LeftMouse> +" handle the user activating a tree node +" scope: global +function! WebDevIconsNERDTreeMapActivateNode(node) + let isOpen = a:node.isOpen + if isOpen + let glyph = g:WebDevIconsUnicodeDecorateFolderNodesDefaultSymbol + else + let glyph = g:DevIconsDefaultFolderOpenSymbol + endif + let a:node.path.isOpen = !isOpen + call WebDevIconsNERDTreeDirUpdateFlags(a:node, glyph) " continue with normal activate logic call a:node.activate() + " glyph change possible artifact clean-up + redraw! +endfunction + +function! WebDevIconsNERDTreeMapOpenRecursively(node) + " normal original logic: + call nerdtree#echo("Recursively opening node. Please wait...") + call a:node.openRecursively() + call WebDevIconsNERDTreeDirOpenRecursively(a:node) + " continue with normal original logic: + call b:NERDTree.render() + " glyph change possible artifact clean-up + redraw! + call nerdtree#echo("Recursively opening node. Please wait... DONE") +endfunction + +function! WebDevIconsNERDTreeMapCloseChildren(node) + " close children but not current node: + call WebDevIconsNERDTreeDirCloseChildren(a:node) + " continue with normal original logic: + call a:node.closeChildren() + call b:NERDTree.render() + call a:node.putCursorHere(0, 0) + " glyph change possible artifact clean-up + redraw! +endfunction + +function! WebDevIconsNERDTreeMapCloseDir(node) + " continue with normal original logic: + let parent = a:node.parent + while g:NERDTreeCascadeOpenSingleChildDir && !parent.isRoot() + let childNodes = parent.getVisibleChildren() + if len(childNodes) == 1 && childNodes[0].path.isDirectory + let parent = parent.parent + else + break + endif + endwhile + if parent ==# {} || parent.isRoot() + call nerdtree#echo("cannot close tree root") + else + call parent.close() + " update the glyph + call WebDevIconsNERDTreeDirClose(parent) + call b:NERDTree.render() + call parent.putCursorHere(0, 0) + " glyph change possible artifact clean-up + redraw! + endif endfunction if g:webdevicons_enable == 1 && g:webdevicons_enable_nerdtree == 1 call s:SetupListeners() if g:DevIconsEnableFoldersOpenClose + + " These overrides are needed because we cannot + " simply use AddListener for reliably updating + " the folder open/close glyphs because the event + " path has no access to the 'isOpen' property + " some of these are a little more brittle/fragile + " than others + " TODO FIXME better way to reliably update + " open/close glyphs in NERDTreeWebDevIconsRefreshListener + " NERDTreeMapActivateNode call NERDTreeAddKeyMap({ \ 'key': g:NERDTreeMapActivateNode, @@ -141,6 +243,27 @@ if g:webdevicons_enable == 1 && g:webdevicons_enable_nerdtree == 1 \ 'override': 1, \ 'scope': 'DirNode' }) + " NERDTreeMapOpenRecursively + call NERDTreeAddKeyMap({ + \ 'key': g:NERDTreeMapOpenRecursively, + \ 'callback': 'WebDevIconsNERDTreeMapOpenRecursively', + \ 'override': 1, + \ 'scope': 'DirNode' }) + + " NERDTreeMapCloseChildren + call NERDTreeAddKeyMap({ + \ 'key': g:NERDTreeMapCloseChildren, + \ 'callback': 'WebDevIconsNERDTreeMapCloseChildren', + \ 'override': 1, + \ 'scope': 'DirNode' }) + + " NERDTreeMapCloseChildren + call NERDTreeAddKeyMap({ + \ 'key': g:NERDTreeMapCloseDir, + \ 'callback': 'WebDevIconsNERDTreeMapCloseDir', + \ 'override': 1, + \ 'scope': 'Node' }) + " <2-LeftMouse> call NERDTreeAddKeyMap({ \ 'key': '<2-LeftMouse>', diff --git a/plugin/webdevicons.vim b/plugin/webdevicons.vim index 3a919ee..61bc95f 100644 --- a/plugin/webdevicons.vim +++ b/plugin/webdevicons.vim @@ -728,12 +728,12 @@ function! NERDTreeWebDevIconsRefreshListener(event) if !path.isDirectory let flag = prePadding . WebDevIconsGetFileTypeSymbol(path.str()) . padding elseif path.isDirectory && g:WebDevIconsUnicodeDecorateFolderNodes == 1 - let directoryOpened = 0 if g:DevIconsEnableFoldersOpenClose && len(path.flagSet._flagsForScope('webdevicons')) > 0 - " isOpen is not available on the path listener, compare using symbols - if path.flagSet._flagsForScope('webdevicons')[0] == prePadding . g:DevIconsDefaultFolderOpenSymbol . padding + " isOpen is not available on the path listener directly + " but we added one via overriding particular keymappings for NERDTree + if has_key(path, 'isOpen') && path.isOpen == 1 let directoryOpened = 1 endif endif