aboutsummaryrefslogtreecommitdiff
path: root/runtime/lua/vim
diff options
context:
space:
mode:
authorJustin M. Keyes <justinkz@gmail.com>2026-08-02 05:33:17 -0400
committerGitHub <noreply@github.com>2026-08-02 05:33:17 -0400
commitf7fbe0e0c8cf10963f35daec187fbba243544db2 (patch)
treef3e2b92eacd656fdd16866c6bf507a5d20ba5c92 /runtime/lua/vim
parent7604aa5ef0a4d8bf447822c875c5d2d176f0ec2e (diff)
parent8695579636b4f76561f54b92aac1a05ca00d09a1 (diff)
downloadrneovim-f7fbe0e0c8cf10963f35daec187fbba243544db2.tar.gz
rneovim-f7fbe0e0c8cf10963f35daec187fbba243544db2.tar.bz2
rneovim-f7fbe0e0c8cf10963f35daec187fbba243544db2.zip
Merge #41106 from altermo/selection-refactor-fix
Diffstat (limited to 'runtime/lua/vim')
-rw-r--r--runtime/lua/vim/lsp/buf.lua16
-rw-r--r--runtime/lua/vim/treesitter/_range.lua36
-rw-r--r--runtime/lua/vim/treesitter/_select.lua36
3 files changed, 45 insertions, 43 deletions
diff --git a/runtime/lua/vim/lsp/buf.lua b/runtime/lua/vim/lsp/buf.lua
index cacc0fa169..4364f098f1 100644
--- a/runtime/lua/vim/lsp/buf.lua
+++ b/runtime/lua/vim/lsp/buf.lua
@@ -7,6 +7,7 @@ local lsp = vim.lsp
local validate = vim.validate
local util = require('vim.lsp.util')
local npcall = vim.npcall
+local Range = require('vim.treesitter._range')
local M = {}
@@ -1432,22 +1433,13 @@ local selection_ranges = nil
---@param range lsp.Range
local function select_range(range)
- local start_line = range.start.line + 1
- local end_line = range['end'].line + 1
+ local start_line = range.start.line
+ local end_line = range['end'].line
local start_col = range.start.character
local end_col = range['end'].character
- -- If the selection ends at column 0, adjust the position to the end of the previous line.
- if end_col == 0 then
- end_line = end_line - 1
- local end_line_text = api.nvim_buf_get_lines(0, end_line - 1, end_line, true)[1]
- end_col = #end_line_text
- end
-
- vim.fn.setpos("'<", { 0, start_line, start_col + 1, 0 })
- vim.fn.setpos("'>", { 0, end_line, end_col, 0 })
- vim.cmd.normal({ 'gv', bang = true })
+ Range.visual_select({ start_line, start_col, end_line, end_col })
end
---@param range lsp.Range
diff --git a/runtime/lua/vim/treesitter/_range.lua b/runtime/lua/vim/treesitter/_range.lua
index b37135efc7..e6ee89d19e 100644
--- a/runtime/lua/vim/treesitter/_range.lua
+++ b/runtime/lua/vim/treesitter/_range.lua
@@ -172,4 +172,40 @@ function M.add_bytes(source, range)
return { start_row, start_col, start_byte, end_row, end_col, end_byte }
end
+---@param range Range
+function M.visual_select(range)
+ local start_row, start_col, end_row, end_col = M.unpack4(range)
+
+ -- If the selection ends at column 0, adjust the position to the end of the previous line.
+ if end_col == 0 then
+ end_row = end_row - 1
+ end_col = #vim.fn.getline(end_row + 1) + 1
+ end
+
+ if vim.fn.visualmode() ~= 'v' then
+ -- Reset visualmode() to 'v'
+ vim.cmd.normal({ 'v\27', bang = true })
+ end
+
+ local cursor_other_end_of_selection = false
+ local visual_col, visual_row = vim.fn.col('v'), vim.fn.line('v')
+ local cursor_col, cursor_row = vim.fn.col('.'), vim.fn.line('.')
+ if M.cmp_pos.gt(visual_row, visual_col, cursor_row, cursor_col) then
+ cursor_other_end_of_selection = true
+ end
+
+ if vim.o.selection == 'exclusive' then
+ end_col = end_col + 1
+ end
+
+ vim.fn.setpos("'<", { 0, start_row + 1, start_col + 1, 0 })
+ vim.fn.setpos("'>", { 0, end_row + 1, end_col, 0 })
+
+ if cursor_other_end_of_selection then
+ vim.cmd.normal({ 'gvo', bang = true })
+ else
+ vim.cmd.normal({ 'gv', bang = true })
+ end
+end
+
return M
diff --git a/runtime/lua/vim/treesitter/_select.lua b/runtime/lua/vim/treesitter/_select.lua
index 2fb5fc1561..e77e51a0c5 100644
--- a/runtime/lua/vim/treesitter/_select.lua
+++ b/runtime/lua/vim/treesitter/_select.lua
@@ -348,36 +348,6 @@ local function node_normalize_down(node)
return node
end
-local function visual_select(range)
- assert(type(range) == 'table')
- local srow, scol, erow, ecol = Range.unpack4(range)
- local cursor_other_end_of_visual = false
-
- local vcol, vrow = vim.fn.col('v'), vim.fn.line('v')
- local ccol, cline = vim.fn.col('.'), vim.fn.line('.')
- if vrow > cline or (vrow == cline and vcol > ccol) then
- cursor_other_end_of_visual = true
- end
-
- if ecol == 0 then
- erow = erow - 1
- ecol = #vim.fn.getline(erow + 1) + 1
- end
-
- if vim.fn.visualmode() ~= 'v' then
- -- reset visualmode() to 'v'
- vim.cmd.normal({ 'v\27', bang = true })
- end
-
- vim.fn.setpos("'<", { 0, srow + 1, scol + 1, 0 })
- vim.fn.setpos("'>", { 0, erow + 1, ecol, 0 })
- if cursor_other_end_of_visual then
- vim.cmd.normal({ 'gvo', bang = true })
- else
- vim.cmd.normal({ 'gv', bang = true })
- end
-end
-
--- @return Range4
local function get_selection()
local pos1 = vim.fn.getpos('v')
@@ -387,6 +357,10 @@ local function get_selection()
pos1, pos2 = pos2, pos1
end
+ if vim.o.selection == 'exclusive' then
+ pos2[3] = pos2[3] - 1
+ end
+
if pos2[3] == #vim.fn.getline(pos2[2]) + 1 then
pos2[2] = pos2[2] + 1
pos2[3] = 0
@@ -596,7 +570,7 @@ local function repeate_apply_range(count, fn)
end
if range and count ~= 0 then
- visual_select(range)
+ Range.visual_select(range)
end
end