mirror of
https://github.com/hexedtech/codemp-nvim.git
synced 2024-11-22 15:34:53 +01:00
fix: properly send and apply precise changes
this was really crazy but it seems to work?? can probably be simplified a ton but not rn
This commit is contained in:
parent
9ea11d41ac
commit
84afc0a864
2 changed files with 57 additions and 31 deletions
|
@ -42,11 +42,20 @@ local function attach(name, force)
|
||||||
on_bytes = function(_, buf, tick, start_row, start_col, start_offset, old_end_row, old_end_col, old_end_byte_len, new_end_row, new_end_col, new_byte_len)
|
on_bytes = function(_, buf, tick, start_row, start_col, start_offset, old_end_row, old_end_col, old_end_byte_len, new_end_row, new_end_col, new_byte_len)
|
||||||
if tick <= ticks[buf] then return end
|
if tick <= ticks[buf] then return end
|
||||||
if id_buffer_map[buf] == nil then return true end -- unregister callback handler
|
if id_buffer_map[buf] == nil then return true end -- unregister callback handler
|
||||||
local content = table.concat(
|
print(string.format(
|
||||||
vim.api.nvim_buf_get_text(buf, start_row, start_col, start_row + new_end_row, start_col + new_end_col, {}),
|
"start(row:%s, col:%s) offset:%s end(row:%s, col:%s new(row:%s, col:%s)) len(old:%s, new:%s)",
|
||||||
'\n'
|
start_row, start_col, start_offset, old_end_row, old_end_col, new_end_row, new_end_col, old_end_byte_len, new_byte_len
|
||||||
)
|
))
|
||||||
-- print(string.format("%s %s %s %s -- '%s'", start_row, start_col, start_row + new_end_row, start_col + new_end_col, content))
|
local content
|
||||||
|
if new_byte_len == 0 then
|
||||||
|
content = ""
|
||||||
|
else
|
||||||
|
content = table.concat(
|
||||||
|
vim.api.nvim_buf_get_text(buf, start_row, start_col, start_row + new_end_row, start_col + new_end_col, {}),
|
||||||
|
'\n'
|
||||||
|
)
|
||||||
|
end
|
||||||
|
print(string.format("sending: %s %s %s %s -- '%s'", start_row, start_col, start_row + new_end_row, start_col + new_end_col, content))
|
||||||
controller:send(start_offset, start_offset + old_end_byte_len, content)
|
controller:send(start_offset, start_offset + old_end_byte_len, content)
|
||||||
end,
|
end,
|
||||||
})
|
})
|
||||||
|
@ -54,6 +63,8 @@ local function attach(name, force)
|
||||||
-- hook clientbound callbacks
|
-- hook clientbound callbacks
|
||||||
async.handler(name, controller, function(event)
|
async.handler(name, controller, function(event)
|
||||||
ticks[buffer] = vim.api.nvim_buf_get_changedtick(buffer)
|
ticks[buffer] = vim.api.nvim_buf_get_changedtick(buffer)
|
||||||
|
-- print(" ~~ applying change ~~ " .. event.first .. ".." .. event.last .. "::[" .. event.content .. "]")
|
||||||
|
utils.buffer.set_content(buffer, event.content, event.first, event.last)
|
||||||
if event.hash ~= nil then
|
if event.hash ~= nil then
|
||||||
if utils.hash(utils.buffer.get_content(buffer)) ~= event.hash then
|
if utils.hash(utils.buffer.get_content(buffer)) ~= event.hash then
|
||||||
-- OUT OF SYNC!
|
-- OUT OF SYNC!
|
||||||
|
@ -63,8 +74,6 @@ local function attach(name, force)
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
-- print(" ~~ applying change ~~ " .. event.first .. ".." .. event.last .. "::" .. event.content)
|
|
||||||
utils.buffer.set_content(buffer, event.content, event.first, event.last)
|
|
||||||
end, 20) -- wait 20ms before polling again because it overwhelms libuv?
|
end, 20) -- wait 20ms before polling again because it overwhelms libuv?
|
||||||
|
|
||||||
print(" ++ attached to buffer " .. name)
|
print(" ++ attached to buffer " .. name)
|
||||||
|
|
|
@ -1,16 +1,5 @@
|
||||||
local native = require('codemp.loader').load()
|
local native = require('codemp.loader').load()
|
||||||
|
|
||||||
local function split_without_trim(str, sep)
|
|
||||||
local res = vim.fn.split(str, sep)
|
|
||||||
if str:sub(1,1) == "\n" then
|
|
||||||
table.insert(res, 1, '')
|
|
||||||
end
|
|
||||||
if str:sub(-1) == "\n" then
|
|
||||||
table.insert(res, '')
|
|
||||||
end
|
|
||||||
return res
|
|
||||||
end
|
|
||||||
|
|
||||||
local function order_tuples(x) -- TODO send help...
|
local function order_tuples(x) -- TODO send help...
|
||||||
if x[1][1] < x[2][1] then
|
if x[1][1] < x[2][1] then
|
||||||
return { { x[1][1], x[1][2] }, { x[2][1], x[2][2] } }
|
return { { x[1][1], x[1][2] }, { x[2][1], x[2][2] } }
|
||||||
|
@ -54,31 +43,60 @@ local function buffer_get_content(buf)
|
||||||
return table.concat(lines, '\n')
|
return table.concat(lines, '\n')
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- TODO this seems to work but i lost my sanity over it. if you want
|
||||||
|
-- to try and make it better be warned api is madness but i will
|
||||||
|
-- thank you a lot because this is an ugly mess...
|
||||||
|
--
|
||||||
|
-- edge cases to test:
|
||||||
|
-- - [x] add newline in buffer
|
||||||
|
-- - [x] append newline to buffer
|
||||||
|
-- - [x] delete multiline
|
||||||
|
-- - [x] append at end of buffer
|
||||||
|
-- - [x] delete at end of buffer
|
||||||
|
-- - [x] delete line at end of buffer
|
||||||
|
-- - [x] delete multiline at end of buffer
|
||||||
|
-- - [x] autocomplete
|
||||||
local function buffer_set_content(buf, content, first, last)
|
local function buffer_set_content(buf, content, first, last)
|
||||||
if first == nil and last == nil then
|
if first == nil and last == nil then
|
||||||
local lines = split_without_trim(content, "\n")
|
local lines = vim.split(content, "\n", {trimempty=false})
|
||||||
vim.api.nvim_buf_set_lines(buf, 0, -1, false, lines)
|
vim.api.nvim_buf_set_lines(buf, 0, -1, false, lines)
|
||||||
else
|
else
|
||||||
local first_row, first_col, last_row, last_col
|
local first_row, first_col, last_row, last_col
|
||||||
vim.api.nvim_buf_call(buf, function()
|
vim.api.nvim_buf_call(buf, function()
|
||||||
first_row = vim.fn.byte2line(first + 1) - 1
|
first_row = vim.fn.byte2line(first + 1) - 1
|
||||||
if first_row == -2 then
|
if first_row == -2 then
|
||||||
|
-- print("?? clamping start_row to start")
|
||||||
first_row = vim.fn.line('$') - 1
|
first_row = vim.fn.line('$') - 1
|
||||||
end
|
end
|
||||||
first_col = first - (vim.fn.line2byte(first_row + 1) - 1)
|
local first_col_byte = vim.fn.line2byte(first_row + 1) - 1
|
||||||
last_row = vim.fn.byte2line(last + 1) - 1
|
if first_col_byte == -2 then
|
||||||
if last_row == -2 then
|
-- print("?? clamping start_col to 0")
|
||||||
local sp = vim.split(content, "\n", {trimempty=false})
|
first_col = 0
|
||||||
last_row = first_row + (#sp - 1)
|
|
||||||
last_col = string.len(sp[#sp])
|
|
||||||
else
|
else
|
||||||
last_col = last - (vim.fn.line2byte(last_row + 1) - 1)
|
first_col = first - first_col_byte
|
||||||
|
end
|
||||||
|
if first == last then
|
||||||
|
last_row = first_row
|
||||||
|
last_col = first_col
|
||||||
|
else
|
||||||
|
last_row = vim.fn.byte2line(last + 1) - 1
|
||||||
|
if last_row == -2 then
|
||||||
|
print("?? clamping end_row to end")
|
||||||
|
last_row = vim.fn.line('$') - 1
|
||||||
|
last_col = last - vim.fn.line2byte(last_row + 1)
|
||||||
|
else
|
||||||
|
last_col = last - (vim.fn.line2byte(last_row + 1) - 1)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
end)
|
end)
|
||||||
vim.api.nvim_buf_set_text(
|
local content_array
|
||||||
buf, first_row, first_col, last_row, last_col,
|
if content == "" then
|
||||||
split_without_trim(content, "\n")
|
content_array = {}
|
||||||
)
|
else
|
||||||
|
content_array = vim.split(content, "\n", {trimempty=false})
|
||||||
|
end
|
||||||
|
-- print(string.format("set [%s..%s::'%s'] -> start(row:%s col:%s) end(row:%s, col:%s)", first, last, content, first_row, first_col, last_row, last_col))
|
||||||
|
vim.api.nvim_buf_set_text(buf, first_row, first_col, last_row, last_col, content_array)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -120,7 +138,6 @@ end
|
||||||
|
|
||||||
|
|
||||||
return {
|
return {
|
||||||
split_without_trim = split_without_trim,
|
|
||||||
order_tuples = order_tuples,
|
order_tuples = order_tuples,
|
||||||
multiline_highlight = multiline_highlight,
|
multiline_highlight = multiline_highlight,
|
||||||
cursor = {
|
cursor = {
|
||||||
|
|
Loading…
Reference in a new issue