1 files changed,
39 insertions(+),
25 deletions(-)
Author:
Oleksandr Smirnov
olexsmir@gmail.com
Committed at:
2026-08-27 22:51:08 +0300
Authored at:
2026-08-27 21:45:23 +0300
Change ID:
oqvvpvqzomomrsylvmzpnnsnyxysmtuk
Parent:
2cae25a
M
plugin/viye.lua
··· 1 +if vim.g.loaded_viye_plugin ~= nil then return end 2 +vim.g.loaded_viye_plugin = true 3 + 1 4 local function indent(t) return #t:match("^%s*") end 2 -local function line_type(line) 3 - if not line:find("%S") then return "empty" end 4 - return line:find("^%s*[|:]") and "data" or "node" 5 + 6 +local function tokenize(s) 7 + local out, buf, q = {}, "", nil 8 + for i = 1, #s do 9 + local c = s:sub(i, i) 10 + if q then 11 + if c == q then q = nil else buf = buf .. c end 12 + elseif c == "'" or c == '"' then 13 + q = c 14 + elseif c:match("%s") then 15 + if #buf > 0 then 16 + table.insert(out, buf); buf = "" 17 + end 18 + else 19 + buf = buf .. c 20 + end 21 + end 22 + if #buf > 0 then table.insert(out, buf) end 23 + return out 5 24 end 6 25 7 26 local function children_of(cmd_lnum) ··· 19 38 local d = indent(vim.fn.getline(lnum)) 20 39 for i = lnum - 1, 1, -1 do 21 40 local l = vim.fn.getline(i) 22 - if line_type(l) == "node" and indent(l) < d then return i end 41 + if l:find("%S") and not l:match("^%s*[|:]") and indent(l) < d then return i end 23 42 end 24 - return nil 25 43 end 26 44 27 45 local function ancestors(cmd_lnum) 28 - local parts = {} 29 - local lnum = cmd_lnum 46 + local parts, lnum = {}, cmd_lnum 30 47 while lnum do 31 48 local l = vim.fn.getline(lnum) 32 49 local line = l:match("^%s*[+-] (.*)") or vim.trim(l) 33 - local words = vim.split(line, "%s+") 50 + local words = tokenize(line) 34 51 for i = #words, 1, -1 do table.insert(parts, 1, words[i]) end 35 52 lnum = parent_of(lnum) 36 53 end ··· 45 62 for i = first, last do 46 63 local l = vim.fn.getline(i) 47 64 local val = indent(l) == depth + 2 and l:match("^%s*: (.*)") 48 - if val then table.insert(body, ": " .. val) end 65 + if val then 66 + for _, tok in ipairs(tokenize(val)) do table.insert(body, ": " .. tok) end 67 + end 49 68 end 50 69 end 51 70 return body ··· 55 74 local cmd = ancestors(cmd_lnum) 56 75 if #cmd == 0 then return end 57 76 table.insert(cmd, 1, "viye") 58 - 59 77 local body = body_of(cmd_lnum) 60 78 if #body > 0 then vim.list_extend(vim.list_extend(cmd, { "--" }), body) end 61 - 62 79 local res = vim.system(cmd, { text = true }):wait(2000) 63 80 if res.code ~= 0 then 64 81 vim.notify(vim.trim(res.stderr), vim.log.levels.ERROR) ··· 70 87 local function insert_output(cmd_lnum, out) 71 88 local pad = string.rep(" ", indent(vim.fn.getline(cmd_lnum)) + 2) 72 89 local lines = vim.split(out, "\n", { trimempty = true }) 73 - for i, l in ipairs(lines) do 74 - lines[i] = pad .. l 75 - end 90 + for i, l in ipairs(lines) do lines[i] = pad .. l end 76 91 vim.fn.append(cmd_lnum, lines) 77 92 end 78 93 ··· 85 100 local function exec() 86 101 local lnum = vim.fn.line(".") 87 102 local line = vim.fn.getline(lnum) 88 - local cmd_lnum = line_type(line) == "data" and parent_of(lnum) or lnum 89 - if not cmd_lnum then return end 90 - local first, last = children_of(cmd_lnum) 91 - local has_children = last ~= nil 92 - local on_cmd = cmd_lnum == lnum 93 - if on_cmd and not has_children then 94 - return 103 + local is_out = line:match("^%s*|") 104 + local cmd_lnum = (line:match("^%s*[|:]") and parent_of(lnum)) or lnum 105 + if not cmd_lnum or vim.fn.getline(cmd_lnum):match("^==%s") then return end 106 + local out 107 + if not is_out then 108 + out = run(cmd_lnum) 109 + if not out then return end 95 110 end 96 - local out = run(cmd_lnum) 97 - if not out then return end 111 + local first, last = children_of(cmd_lnum) 98 112 if last then vim.cmd(string.format("%d,%ddelete _", first, last)) end 99 - if out ~= "" then insert_output(cmd_lnum, out) end 100 - toggle_bullet(cmd_lnum) 113 + if out and out ~= "" then insert_output(cmd_lnum, out) end 114 + if not is_out then toggle_bullet(cmd_lnum) end 101 115 end 102 116 103 117 vim.filetype.add { extension = { viye = "viye" } }