1

I'm trying to bind the key ^ so that it runs ^ in normal mode by default, but calls the function bound to - in netrw. - is bound to NetrwBrowseUpDir in netrw.vim, definition here .

Here's my first attempt to bind ^ to -

nnoremap <expr>  ^  &ft ==? "netrw" ? "-" : "^" 

This snippet will correctly detect whether the current buffer is a netrw view or not, but calls the ordinary - command, which moves to the first non-whitespace character of the previous line.

How do I call the plugin's function directly? In the definition I linked it's script-local, so I'm not sure how get a reference to it.

The motivation for this is that I use - and = to scroll pagewise, and so I need to shift around the default netrw bindings so they don't conflict.

nnoremap - <c-d> 
nnoremap = <c-u>
3

There is a hacky way to get a scripts <SID> and use it in mappings, but I always forget it.

One way to do it would be with:nmap, but this probably only works if you don’t already have a mapping for -:

nmap <expr> ^ &ft ==# 'netrw' ? '-' : '^'

I’ve looked at the docs and do not see a configuration variable for netrw’s mappings.

However, Matt mentions a <Plug> mapping in the comments, so:

nmap <expr> ^ &ft ==# 'netrw' ? "\<Plug>NetrwBrowseUpDir" : '^'
5
  • Netrw exports <plug>NetrwBrowseUpDir which seems the most suitable for this case.
    – Matt
    Jan 25 '20 at 15:16
  • on Vim 8.0, I can confirm that nmap <expr> ^ &ft ==# 'netrw' ? '-' : '^' successfully remaps ^ to go up a directory in netrw without interfering with the original binding. However, I can't get nmap <expr> ^ &ft ==# 'netrw' ? "\<Plug>NetrwBrowseUpDir" : '^' to call the right function. I've tested it, and ^ appears to be a no-op in a .vimrc consisting of just that line. Jan 25 '20 at 22:01
  • 1
    @GregoryNisbet what if you put nmap ^ <Plug>... in ~/.vim/after/ftplugin/netrw.vim ?
    – D. Ben Knoble
    Jan 25 '20 at 22:10
  • @D.BenKnoble After struggling with this a bit, I managed to call the right function using nmap ^ :<c-u>call netrw#Call('NetrwBrowseUpDir', 1)<cr> in the file ~/.vim/after/plugin/netrw.vim . However, I can't seem to set up the arguments to netrw#Call correctly. I keep seeing a type error E745: Using List as Number somewhere inside netrw#Call . Jan 25 '20 at 22:57
  • @GregoryNisbet i haven’t looked at the code, but I’m wondering if netrw#Call just forwards it’s arguments and is expecting a list? But then perhaps two lists are being added later, only now one is a number, so things seem weird?
    – D. Ben Knoble
    Jan 26 '20 at 3:11
0

Rather than using a global mapping and checking for the filetype in an expression, just set this mapping in a ftplugin for netrw and set it as a buffer-local mapping.

Create file ~/.vim/after/ftplugin/netrw.vim with the following line:

nmap <buffer> ^ <Plug>NetrwBrowseUpDir

NOTE 1: The original mapping also uses <silent> and <nowait>, you might consider adding those yourself as well.

NOTE 2: Usually, when you add settings from a script in ftplugin, you also want to append a snippet to the b:undo_ftplugin variable with commands to undo the effects of the script. In this case, that's probably not really necessary, since the netrw filetype is quite specific to netrw buffers and those don't really use undo_ftplugin.

NOTE 3: The code that sets up the mapping for - checks whether there's already a mapping for <Plug>NetrwBrowseUpDir and skips that mapping if one already exists. If you create your mapping from the ftplugin, your mapping will be created last, so the - command will continue to work on netrw buffers.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.