simnalamburt / vim-mundo

:christmas_tree: Vim undo tree visualizer

Home Page:https://simnalamburt.github.io/vim-mundo

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Setting `g:mundo_right` and `g:mundo_close_on_revert` causes error on reversion

thisisrandy opened this issue · comments

If both g:mundo_right and g:mundo_close_on_revert are set to 1, an error is issued when we revert to the selected state. This is the error when a single window is open. The 2 would change otherwise:

Error detected while processing function <SNR>229_MundoPythonRestoreView:
line   20:
E16: Invalid range: 2wincmd w

This happens on line 425 of autoload/mundo.vim. I dug around a little bit, and it looks like the last time MundoPythonRestoreView is called during reversion, it's to wrap MundoRevert, which calls MundoToggle, closing all mundo windows before running line 425, which fails because the window no longer exists.

I believe what's happening is that when mundo is on the left, its winnr is 1, so after the mundo windows are closed, there's still a window 1 open and the command succeeds, even though it isn't really doing the thing it was intended to, namely, restoring the view of the mundo window. This isn't true when it's on the right, so the command fails.

I see a couple of hacky fixes to this:

  1. Check if a:fn is MundoRevert and g:mundo_close_on_revert is set before executing the latter part of MundoPythonRestoreView. It shouldn't be the responsibility of the caller to know about the innards of the callee, so even though this works, it's pretty awful from a software engineering perspective.
  2. Rewrite the offending line as execute 'silent! ' . currentWin . 'wincmd w'. This is a lot cleaner than (1), but it means that the rest of the function isn't necessarily doing valid things since it's operating on the buffer window and not the mundo window. However, this is exactly what it currently does when mundo is on the left, so it's probably okay.

I'm going to submit a PR with (2). Ideas for a more disciplined solution would be welcome.

I realized that my fix still allows winrestview to be called for the wrong window, which can drastically change the buffer view. This would also be true independent of my fix if g:mundo_right was not set. The better fix is to capture the mundo window's id and then check after the python call if it still exists, running (winnum)wincmd w and winrestview only if it does.

I somehow forgot to create a PR before. Now open.