-
-
Notifications
You must be signed in to change notification settings - Fork 5.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
BufEnter is triggered when calling nvim_open_win with enter=false #15300
Comments
What does BufEnter mean for you? For me It means two things, my cursor enters the buffer but is also when the buffer is displayed in a window. Maybe the word enter in So to me opening a window and opening a buffer in said window even if I don't have focus is also a BufEnter. Here's a code example that demonstrate It works this way. ENTERED = {}
vim.cmd[[:e b0]]
local w0 = vim.api.nvim_get_current_win()
assert(w0 == vim.api.nvim_get_current_win())
print("Im on window 0")
vim.cmd[[:split b1]]
local w1 = vim.api.nvim_get_current_win()
-- Make sure I'm in window 1
assert(w1 == vim.api.nvim_get_current_win())
print("Im on window 1: " .. w1 )
-- Set autocommand for entering a buffer
vim.cmd[[au BufEnter * :lua table.insert(ENTERED, vim.fn.expand("<afile>"))]]
vim.cmd[[au WinEnter * :lua print("Im just entered window " .. vim.api.nvim_get_current_win())]]
print("Entered buffers: ", vim.inspect(ENTERED))
-- Create a test buffer
local f = io.open("/tmp/test.file", "w")
f:write("This is my test file wohoo")
f:close()
-- Load the buffer but do not show it in a window.
print("loading the buffer")
local buf = vim.fn.bufadd("/tmp/test.file")
-- Set it as the buffer for a window I can see but have not entered.
print("Setting the buffer in window 0")
vim.api.nvim_win_set_buf(w0, buf)
print("Entered buffers: ", vim.inspect(ENTERED))
assert(w1 == vim.api.nvim_get_current_win())
print("Im still on window 1")
--[[ The output
Im on window 0: 1000
Im on window 1: 1001
Entered buffers: {}
loading the buffer
Setting the buffer in window 0
Entered buffers: { "/tmp/test.file" }
Im still on window 1
--]] So to me is a problem of understanding what BufEnter does, and the docs could do a better job of that. I hope I was clear |
Meaning more then one thing is an issue itself but that predates neovim . BufEnter can effectively used to detect buf change but it seems some api functions are breaking this behaviour .Since there's no
This doesn't explain why |
I agree! Changing some autocommands to have a clear defined behavior and therefore a very clear definition would be amazing. I'd be happy to help. |
I don't think changing the behavior of existing events will be a good idea. If we change BufEnter to have a single role now . That will be huge breakage to vim compatability. And will break a ton of plugins . We can make BufEnters behavior consistent for api . Or add newer Events . |
some of them are caused by neovim/neovim#15300 some are neovim/neovim#19464 and other unknown bugs too So as workaround don't update statusline in autocmd context immediately instead defer the refresh to 50ms later in timer context. fixes #751 #753 #755
I just want to add some perspective to this. I have this autocommand configured: au BufEnter * if &buftype == "terminal" | startinsert | endif If I want to open up a read-only terminal window, even |
some of them are caused by neovim/neovim#15300 some are neovim/neovim#19464 and other unknown bugs too So as workaround don't update statusline in autocmd context immediately instead defer the refresh to 50ms later in timer context. fixes nvim-lualine#751 nvim-lualine#753 nvim-lualine#755
Neovim Version
v0.6.0-dev+111-gf22326ef0
Installation
built from repo
Steps to reproduce
Run
Then execute this script
Expected behavior
Since the cursor remains out of the float buffer . In the original buffer where we started at . I'd expect BufEnter to be not triggered at all (Since enter is false). Or it to be triggered twice once for going into the float buffer and one for getting out. In 1st case see no message at all and in 2nd case see 2 messages.
Actual behavior
But you'll see Entering buffer in messages once indicating BufEnter event was emited once for an unnamed buffer (float buffer).
For this anything keeping track of current buffer with
BufEnter
will be out of sync with the editor .Some background
I encountered this while tracking down nvim-lualine/lualine.nvim#286
vim.lsp.diagnostic.goto_next
callsvim.lsp.diagnostics.show_line_diagnostics
to show diagnostics . Which creates float withnvim_open_win
leading to the bug . It's possible to workarround this issue by passingnoautocmd
option tonvim_open_win
.Possible cause
I think this is what's happening
https://github.com/neovim/neovim/blob/e7bde44d6d2a88e67d68d5a1b9f0d037179dd14e/src/nvim/window#L586 this line changes currently active window to newly created float . this https://github.com/neovim/neovim/blob/e7bde44d6d2a88e67d68d5a1b9f0d037179dd14e/src/nvim/window#L606 restores the original window . These two doesn't trigger any auto commands . In the middle this https://github.com/neovim/neovim/blob/e7bde44d6d2a88e67d68d5a1b9f0d037179dd14e/src/nvim/window#L594 line changes the buffer . This triggers
BufEnter
for float buffer . So whennvim_open_win
is called with enter = false then we get one BufEnter and one BufLeave for getting out from current buffer and entering new one . But the cursor ends up in older win and buffer . So anything keeping track of Current active buffer withBufEnter
orBufLeave
gets out of sync .Possible solution
So what's a valid solution to this ? makeing switch_win and restore_win trigger auto commands ? ignoring BufEnter from that do_buffer call when enter is false or something else ?
The text was updated successfully, but these errors were encountered: