mirror of
https://github.com/neovim/neovim.git
synced 2024-12-24 05:05:00 -07:00
fix: check columns in root bounds
This commit is contained in:
parent
260b4bb3a5
commit
d43690d82a
@ -278,100 +278,128 @@ local function get_spell(capture_name)
|
||||
return nil, 0
|
||||
end
|
||||
|
||||
local function cmp_eq(rowa, cola, rowb, colb)
|
||||
return rowa == rowb and cola == colb
|
||||
end
|
||||
|
||||
local function cmp_lt(rowa, cola, rowb, colb)
|
||||
return rowa < rowb or (rowa == rowb and cola < colb)
|
||||
end
|
||||
|
||||
local function cmp_lte(rowa, cola, rowb, colb)
|
||||
return rowa < rowb or (rowa == rowb and cola <= colb)
|
||||
end
|
||||
|
||||
---@param self vim.treesitter.highlighter
|
||||
---@param buf integer
|
||||
---@param line integer
|
||||
---@param range_br integer
|
||||
---@param range_bc integer
|
||||
---@param range_er integer
|
||||
---@param range_ec integer
|
||||
---@param is_spell_nav boolean
|
||||
local function on_range_impl(self, buf, from_line, from_col, until_line, until_col, is_spell_nav)
|
||||
local function on_range_impl(self, buf, range_br, range_bc, range_er, range_ec, is_spell_nav)
|
||||
self:for_each_highlight_state(function(state)
|
||||
local root_node = state.tstree:root()
|
||||
local root_start_row, _, root_end_row, _ = root_node:range()
|
||||
local root_br, root_bc, root_er, root_ec = root_node:range()
|
||||
|
||||
-- Only consider trees that contain this line
|
||||
if root_start_row > until_line or root_end_row < from_line then
|
||||
local root_intersects = false
|
||||
|
||||
local range_empty = cmp_eq(range_br, range_bc, range_er, range_ec)
|
||||
local root_empty = cmp_eq(root_br, root_bc, root_er, root_ec)
|
||||
if not range_empty and not root_empty then
|
||||
root_intersects = cmp_lt(range_br, range_bc, root_er, root_ec)
|
||||
and cmp_lt(root_br, root_bc, range_er, range_ec)
|
||||
else
|
||||
root_intersects = cmp_lte(range_br, range_bc, root_er, root_ec)
|
||||
and cmp_lte(root_br, root_bc, range_er, range_ec)
|
||||
end
|
||||
|
||||
-- Only consider trees within the visible range
|
||||
if not root_intersects then
|
||||
return
|
||||
end
|
||||
|
||||
if
|
||||
state.iter == nil
|
||||
or state.next_row < from_line
|
||||
or (state.next_row == from_line and state.next_col < from_col)
|
||||
then
|
||||
local next_row = state.next_row
|
||||
local next_col = state.next_col
|
||||
|
||||
if state.iter == nil or cmp_lt(next_row, next_col, range_br, range_bc) then
|
||||
-- Mainly used to skip over folds
|
||||
|
||||
-- TODO(lewis6991): Creating a new iterator loses the cached predicate results for query
|
||||
-- matches. Move this logic inside iter_captures() so we can maintain the cache.
|
||||
state.iter = state.highlighter_query
|
||||
:query()
|
||||
:iter_captures2(root_node, self.bufnr, from_line, from_col, root_end_row + 1, 0)
|
||||
:iter_captures2(root_node, self.bufnr, range_br, range_bc, root_er + 1, 0)
|
||||
end
|
||||
|
||||
while
|
||||
until_line > state.next_row or (until_line == state.next_row and until_col > state.next_col)
|
||||
do
|
||||
local capture, node, metadata, match = state.iter(until_line, until_col)
|
||||
|
||||
local range = { root_end_row + 1, 0, root_end_row + 1, 0 }
|
||||
if node then
|
||||
range = vim.treesitter.get_range(node, buf, metadata and metadata[capture])
|
||||
while cmp_lt(next_row, next_col, range_er, range_ec) do
|
||||
local capture, node, metadata, match = state.iter(range_er, range_ec)
|
||||
if not node then
|
||||
next_row = math.huge
|
||||
next_col = math.huge
|
||||
break
|
||||
end
|
||||
|
||||
local range = vim.treesitter.get_range(node, buf, metadata and metadata[capture])
|
||||
local start_row, start_col, end_row, end_col = Range.unpack4(range)
|
||||
|
||||
if capture then
|
||||
local hl = state.highlighter_query:get_hl_from_capture(capture)
|
||||
|
||||
local capture_name = state.highlighter_query:query().captures[capture]
|
||||
|
||||
local spell, spell_pri_offset = get_spell(capture_name)
|
||||
|
||||
-- The "priority" attribute can be set at the pattern level or on a particular capture
|
||||
local priority = (
|
||||
tonumber(metadata.priority or metadata[capture] and metadata[capture].priority)
|
||||
or vim.hl.priorities.treesitter
|
||||
) + spell_pri_offset
|
||||
|
||||
-- The "conceal" attribute can be set at the pattern level or on a particular capture
|
||||
local conceal = metadata.conceal or metadata[capture] and metadata[capture].conceal
|
||||
|
||||
local url = get_url(match, buf, capture, metadata)
|
||||
|
||||
if hl and end_row >= from_line and (not is_spell_nav or spell ~= nil) then
|
||||
api.nvim_buf_set_extmark(buf, ns, start_row, start_col, {
|
||||
end_line = end_row,
|
||||
end_col = end_col,
|
||||
hl_group = hl,
|
||||
ephemeral = true,
|
||||
priority = priority,
|
||||
conceal = conceal,
|
||||
spell = spell,
|
||||
url = url,
|
||||
})
|
||||
end
|
||||
end
|
||||
|
||||
if start_row > until_line or (start_row == until_line and start_col >= until_col) then
|
||||
state.next_row = start_row
|
||||
state.next_col = start_col
|
||||
if cmp_lt(next_row, next_col, start_row, start_col) then
|
||||
next_row = start_row
|
||||
next_col = start_col
|
||||
end
|
||||
|
||||
if not capture then
|
||||
break
|
||||
end
|
||||
|
||||
local hl = state.highlighter_query:get_hl_from_capture(capture)
|
||||
local capture_name = state.highlighter_query:query().captures[capture]
|
||||
local spell, spell_pri_offset = get_spell(capture_name)
|
||||
|
||||
-- The "priority" attribute can be set at the pattern level or on a particular capture
|
||||
local priority = (
|
||||
tonumber(metadata.priority or metadata[capture] and metadata[capture].priority)
|
||||
or vim.hl.priorities.treesitter
|
||||
) + spell_pri_offset
|
||||
|
||||
-- The "conceal" attribute can be set at the pattern level or on a particular capture
|
||||
local conceal = metadata.conceal or metadata[capture] and metadata[capture].conceal
|
||||
|
||||
local url = get_url(match, buf, capture, metadata)
|
||||
|
||||
if not is_spell_nav or spell ~= nil then
|
||||
api.nvim_buf_set_extmark(buf, ns, start_row, start_col, {
|
||||
end_line = end_row,
|
||||
end_col = end_col,
|
||||
ephemeral = true,
|
||||
priority = priority,
|
||||
hl_group = hl,
|
||||
conceal = conceal,
|
||||
spell = spell,
|
||||
url = url,
|
||||
})
|
||||
end
|
||||
end
|
||||
|
||||
state.next_row = next_row
|
||||
state.next_col = next_col
|
||||
end)
|
||||
end
|
||||
|
||||
---@private
|
||||
---@param _win integer
|
||||
---@param buf integer
|
||||
---@param line integer
|
||||
function TSHighlighter._on_range(_, _win, buf, sr, sc, er, ec, _)
|
||||
---@param br integer
|
||||
---@param bc integer
|
||||
---@param er integer
|
||||
---@param ec integer
|
||||
function TSHighlighter._on_range(_, _win, buf, br, bc, er, ec, _)
|
||||
local self = TSHighlighter.active[buf]
|
||||
if not self then
|
||||
return
|
||||
end
|
||||
|
||||
on_range_impl(self, buf, sr, sc, er, ec, false)
|
||||
on_range_impl(self, buf, br, bc, er, ec, false)
|
||||
end
|
||||
|
||||
---@private
|
||||
|
@ -2588,8 +2588,8 @@ int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow, int col_rows, s
|
||||
bool added_decor = false;
|
||||
decor_providers_invoke_range(wp, lnum - 1, decor_provider_end_col,
|
||||
lnum, 0, &added_decor);
|
||||
decor_provider_end_col = INT_MAX;
|
||||
has_decor |= added_decor;
|
||||
// decor_provider_end_col = INT_MAX;
|
||||
// has_decor |= added_decor;
|
||||
}
|
||||
if (has_decor) {
|
||||
extra_check = true;
|
||||
|
Loading…
Reference in New Issue
Block a user