diff --git a/lua/lazyvim/config/options.lua b/lua/lazyvim/config/options.lua index d1605f93..69e8e8d3 100644 --- a/lua/lazyvim/config/options.lua +++ b/lua/lazyvim/config/options.lua @@ -82,7 +82,7 @@ end -- HACK: causes freezes on <= 0.9, so only enable on >= 0.10 for now if vim.fn.has("nvim-0.10") == 1 then vim.opt.foldmethod = "expr" - vim.opt.foldexpr = "v:lua.vim.treesitter.foldexpr()" + vim.opt.foldexpr = "v:lua.require'lazyvim.util'.ui.foldexpr()" else vim.opt.foldmethod = "indent" end diff --git a/lua/lazyvim/util/ui.lua b/lua/lazyvim/util/ui.lua index c17a1e7b..68999eda 100644 --- a/lua/lazyvim/util/ui.lua +++ b/lua/lazyvim/util/ui.lua @@ -141,4 +141,42 @@ function M.fg(name) return fg and { fg = string.format("#%06x", fg) } or nil end +M.skip_foldexpr = {} ---@type table +local skip_check = assert(vim.loop.new_check()) + +function M.foldexpr() + local buf = vim.api.nvim_get_current_buf() + + -- still in the same tick and no parser + if M.skip_foldexpr[buf] then + return "0" + end + + -- don't use treesitter folds for non-file buffers + if vim.bo[buf].buftype ~= "" then + return "0" + end + + -- as long as we don't have a filetype, don't bother + -- checking if treesitter is available (it won't) + if vim.bo[buf].filetype == "" then + return "0" + end + + local ok = pcall(vim.treesitter.get_parser, buf) + + if ok then + return vim.treesitter.foldexpr() + end + + -- no parser available, so mark it as skip + -- in the next tick, all skip marks will be reset + M.skip_foldexpr[buf] = true + skip_check:start(function() + M.skip_foldexpr = {} + skip_check:stop() + end) + return "0" +end + return M