diff options
| author | Robert Günzler <r@gnzler.io> | 2026-09-27 17:38:39 +0200 |
|---|---|---|
| committer | Robert Günzler <r@gnzler.io> | 2026-09-27 17:38:39 +0200 |
| commit | 0860db73ae6fd9a6f6347219d820bf026a6b8b91 (patch) | |
| tree | 11318c3670d1c32c5aa0bf404c22fba3bf63fc53 /.config/nvim/lua/mod/win.lua | |
| parent | 4e34cbf9673aeaba252e01df554a0d204e83c5e2 (diff) | |
| download | dotfiles-master.tar.gz | |
Automated-commit-by: dots Signed-off-by: Robert Günzler <r@gnzler.io>
Diffstat (limited to '')
| -rw-r--r-- | .config/nvim/lua/mod/win.lua | 110 |
1 files changed, 110 insertions, 0 deletions
diff --git a/.config/nvim/lua/mod/win.lua b/.config/nvim/lua/mod/win.lua new file mode 100644 index 0000000..e5c5f71 --- /dev/null +++ b/.config/nvim/lua/mod/win.lua @@ -0,0 +1,110 @@ +local M = {} + +function M.open(name, content, opts) + if name == '' then + return + end + if #content == 0 then + return + end + + local opts = opts or {} + local autoclose = opts.autoclose or false + local buf_opts = opts.buf or { buftype = '' } + + local win_opts = opts.win or false + -- profiles + if type(win_opts) == 'table' and type(win_opts[1] == 'string') then + local profile = win_opts[1] + local overwrites = unpack(win_opts, 2) + if profile == 'emplace' then + win_opts = false + elseif profile == 'smallsplit' then + win_opts = { + split = 'above', + win = 0, + height = 20, + } + elseif profile == 'popup' then + local winh = vim.api.nvim_win_get_height(0) + local winw = vim.api.nvim_win_get_width(0) + local winsize = 0.5 + win_opts = { + relative = 'win', + height = math.floor(winh * winsize), + width = math.floor(winw * winsize), + row = math.floor((winh * 0.5) - (0.5 * (winh * winsize))), + col = math.floor((winw * 0.5) - (0.5 * (winw * winsize))), + style = 'minimal', + border = 'single', + zindex = 99, + title = name, + } + end + if overwrites then + for k, v in pairs(overwrites) do + win_opts[k] = v + end + end + end + + local bufnr = vim.api.nvim_create_buf(false, true) + assert(bufnr ~= 0, 'Failed to create buffer') + + vim.bo[bufnr].modifiable = true + vim.api.nvim_buf_set_name(bufnr, name) + vim.api.nvim_buf_set_lines(bufnr, 0, -1, true, content) + for k, v in pairs(buf_opts) do + vim.bo[bufnr][k] = v + end + + -- without win_opts (by default) replace current buffer + local winid = 0 + if win_opts then + winid = vim.api.nvim_open_win(0, not autoclose, win_opts) + assert(winid ~= 0, 'Failed to create window') + end + + vim.keymap.set('n', 'q', '<cmd>quit!<cr>', { silent = true, buffer = bufnr }) + + if autoclose then + local group = 'modwin_' .. vim.base64.encode(vim.uv.random(16)) + local group_id = vim.api.nvim_create_augroup(group, {}) + + vim.api.nvim_create_autocmd('WinClosed', { + pattern = tostring(winid), + group = group_id, + callback = function() + vim.api.nvim_create_augroup(group, {}) + M.winid = nil + end, + }) + vim.api.nvim_create_autocmd({ 'CursorMoved', 'CursorMovedI' }, { + group = group_id, + callback = function() + vim.api.nvim_create_augroup(group, {}) + pcall(vim.api.nvim_win_close, winid, true) + end, + }) + end + + vim.api.nvim_win_set_buf(winid, bufnr) + return { bufnr, winid } +end + +function M.popup(name, content, opts) + local defaults = { + autoclose = true, + buf = { + bufhidden = 'wipe', + buftype = 'nofile', + modifiable = false, + }, + win = { 'popup' }, + } + opts = opts or {} + opts = vim.tbl_deep_extend('force', defaults, opts) + M.open(name, content, opts) +end + +return M |