nvimdev / indentmini.nvim

A minimal and blazing fast indentline plugin
MIT License
171 stars 12 forks source link

Implement performance improvements #16

Closed LokiNaBoki closed 3 months ago

LokiNaBoki commented 3 months ago

This PR introduces the performance improvements discussed in #14 plus some more caching not mentioned there. In summary (from oldest to newest commit):

  1. Check if the indents should be calculated in on_win() instead of on_line() - once per window not once per line
  2. Calculate the current line range in on_win() instead of on_line() - once per window not once per line
  3. Prefer nvim_buf_get_lines() over nvim_buf_get_text() for entire lines as is mentioned in the docs. Not sure if this improves performance.
  4. Get the line contents once per line not once per indent level
  5. Cache some calls to the api, so they are not recomputed multiple times per line
  6. The non_or_space() does not need to compare chars because indent() returns the number of leading spaces. I'm not 100% sure about this one, but it seems to work.
  7. Cache length and indent() of each line. Not sure if this is necessary.

I have not done any extensive testing, just checked a few different files and they looked alright. Also I don't know how to profile a plugin's performance, so I don't know by how much if at all each of these changes help.

glepnir commented 3 months ago

Prefer nvim_buf_get_lines() over nvim_buf_get_text() for entire lines as is mentioned in the docs. Not sure if this improves performance.

I checked the source of code of theme. yup get_text have more logic and take some malloc .

The non_or_space() does not need to compare chars because indent() returns the number of leading spaces. I'm not 100% sure about this one, but it seems to work.

it need works on an empty line like the empty line in indent 2 block but some times there has tab in expandtab true buffer avoid the draw a line override a col . so i use these function to check col has space or nothing .

I just give it a test no long work . yet another thgouth when i do :set sw=4 then the cache from on_win is still correct?

LokiNaBoki commented 3 months ago

it need works on an empty line like the empty line in indent 2 block but some times there has tab in expandtab true buffer avoid the draw a line override a col . so i use these function to check col has space or nothing .

ok I will revert the non_or_space() function

I just give it a test no long work

Yeah, sorry I was testing the wrong version. Fixed and force pushed to the fork

yet another thgouth when i do :set sw=4 then the cache from on_win is still correct?

When you change sw the screen is redrawn, so the on_win is called. I also gave it a check and changing sw properly updates the indent lines.

glepnir commented 3 months ago

I do some ffi C bindings avoid some object convert . not sure how much will be improved..

LokiNaBoki commented 3 months ago

Rebased, the first three commits look like easy wins to me, the last one adds a bit of complexity while its performance improvements are questionable, maybe it is better to drop it?

By the way how do you learn about these C functions? Do you just read the neovim source code or are there some docs for them?

glepnir commented 3 months ago

i am working on neovim as team member and i think i know where is waste time …let me do some change tomorrow

glepnir commented 3 months ago

take some advice from here :) but i can't find your email add into the co-authored and did you still get some points for improve with current code?

glepnir commented 3 months ago

I have tried cache the line_is_empty(bufnr, lnum) result in on_win but when i do quickly enter in insertmode it will crash by ml_get lnum error

LokiNaBoki commented 3 months ago

take some advice from here :) but i can't find your email add into the co-authored

Awesome, glad I could help

did you still get some points for improve with current code

Unfortunately not

I have tried cache the line_is_empty(bufnr, lnum) result in on_win but when i do quickly enter in insertmode it will crash by ml_get lnum error

No idea why that would happen, sorry

I will close this PR now, if anyone has some ideas it would probably be better to talk about them in #14.