Skip to content
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

Unneeded (?) resettings of virtualedit/conceallevel may make context#util#update_state() extremely slow #109

Open
lyokha opened this issue Jul 27, 2021 · 0 comments

Comments

@lyokha
Copy link

lyokha commented Jul 27, 2021

I found that moving cursor in Normal mode is painfully slow in my auto-generated TeX files with long wrapped lines because of CursorMoved autocmd from the context plugin. My first attempt was to disable tex files using g:context_filetype_blacklist, but this did not help as this won't delete the context's augroup.

After some digging I found that the bottleneck was resetting virtualedit/conceallevel every time the cursor moves in Normal mode. It seems that switching these resettings off completely won't change correctness of the context behaviour: I checked this with all combinations of virtualedit, conceallevel, concealcursor, setting nunber/nonumber, adding marks on the sign column, etc. On the other hand, moving the cursor around got very fast and easy.

Here is my diff:

diff --git a/autoload/context/util.vim b/autoload/context/util.vim
index 5b6db1b..1b29124 100644
--- a/autoload/context/util.vim
+++ b/autoload/context/util.vim
@@ -113,12 +113,12 @@ function! context#util#update_state() abort
 
     " NOTE: we need to save and restore the cursor position because setting
     " 'virtualedit' resets curswant #84
-    let cursor = getcurpos()
-    let old = [&virtualedit, &conceallevel]
-    let [&virtualedit, &conceallevel] = ['all', 0]
+    "let cursor = getcurpos()
+    "let old = [&virtualedit, &conceallevel]
+    "let [&virtualedit, &conceallevel] = ['all', 0]
     let sign_width = wincol() - virtcol('.') - number_width
-    let [&virtualedit, &conceallevel] = old
-    call setpos('.', cursor)
+    "let [&virtualedit, &conceallevel] = old
+    "call setpos('.', cursor)
 
     " NOTE: sign_width can be negative if the cursor is on the wrapped part of
     " a wrapped line. in that case ignore the value

Probably, my Neovim 0.5 behaves differently than Vim. Or maybe I do not know some special scenarios when switching these settings is important, but I feel that virtualedit should not affect correctness of wincol() and virtcol(), while :help virtcol() says that it also ignores conceallevel (and it seems that wincol() does as well).

Historically, I tried to fix horizontal cursor motions by detecting this in context#update() and skipping the call to context#util#update_state(), here is the diff:

diff --git a/autoload/context.vim b/autoload/context.vim
index 9fcf894..0905db3 100644
--- a/autoload/context.vim
+++ b/autoload/context.vim
@@ -82,6 +82,17 @@ function! context#update(...) abort
                     \ }
     endif
 
+    " FIXME: does this always work as supposed?
+    " (at least, this has minor issues when unfolding text)
+    if source == 'CursorMoved' &&
+                \ (0
+                \     || !s:activated
+                \     || !context#util#active()
+                \     || w:context.cursor_line == line('.')
+                \ )
+        return
+    endif
+
     if 1
                 \ && w:context.peek
                 \ && source != 'CursorHold'

However, this is far not as important for the speed as the first hunk. And this has side effects when opening folds.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant