Something went wrong. Try again.
🫙 tiny scratch terminal for Neovim
Something went wrong. Try again.
3.2 kB · 145 lines
Lua
at main
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146---@return vim.api.keyset.win_configlocal function get_winopts() local horiz = vim.opt.fillchars:get().horiz or "─"
local height = math.ceil(vim.o.lines * 0.3) local offset = vim.o.cmdheight + 1
return { relative = "editor", col = 0, row = vim.o.lines - height - offset - 1, height = height, width = vim.o.columns, style = "minimal", border = { horiz, horiz, horiz, "", "", "", "", "" }, }end
---@class jamjar.Terminal.proto---@field cmd? string---@field cwd? string---@field winoptsfn? fun(): vim.api.keyset.win_config---@field on_open? fun(self: jamjar.Terminal)
---@class jamjar.Terminal : jamjar.Terminal.proto---@field cmd string---@field buf integer---@field win? integerlocal Terminal = {}Terminal.__index = Terminal
local function get_defaultopts() return { cmd = vim.o.shell, on_open = function(self) vim.api.nvim_set_option_value( "winhighlight", "Normal:Normal,NormalNC:NormalNC,FloatBorder:WinSeparator", { win = self.win } ) end, }end
---@param opts? jamjar.Terminal.protofunction Terminal:new(opts) return setmetatable(vim.tbl_extend("force", get_defaultopts(), opts or {}), self)end
function Terminal:isbufvalid() return self.buf and vim.api.nvim_buf_is_valid(self.buf)end
function Terminal:ensurebuf() if not self:isbufvalid() then self:init() endend
function Terminal:init() self.buf = vim.api.nvim_create_buf(true, true) vim.api.nvim_set_option_value("buftype", "nofile", { buf = self.buf })
vim._with({ buf = self.buf }, function() vim.fn.jobstart(self.cmd, { term = true, cwd = self.cwd, on_exit = function() self:delete() end, }) end)end
function Terminal:iswinvalid() return self.win and vim.api.nvim_win_is_valid(self.win)end
function Terminal:toggle() self:ensurebuf()
if not self:iswinvalid() then self:open() return end
local wcfg = vim.api.nvim_win_get_config(self.win) local hidden = wcfg.hide
if hidden then self:open() else self:close() endend
function Terminal:open() if not self:iswinvalid() then self:ensurebuf() self.win = vim.api.nvim_open_win(self.buf, true, vim.F.if_nil(self.winoptsfn, get_winopts)()) vim.api.nvim_set_option_value("signcolumn", "no", { win = self.win }) vim.api.nvim_set_option_value("foldcolumn", "0", { win = self.win }) self.on_open(self) else vim.api.nvim_win_set_config(self.win, { hide = false, }) vim.api.nvim_set_current_win(self.win) endend
function Terminal:close() if not self:iswinvalid() then return end
vim.api.nvim_win_set_config(self.win, { hide = true, })
if vim.api.nvim_get_current_win() == self.win then vim.cmd.wincmd("p") endend
function Terminal:quit() if not self:iswinvalid() then return end
vim.api.nvim_win_close(self.win, true) self.win = nilend
function Terminal:delete() self:quit()
if self:isbufvalid() then vim.bo[self.buf].buflisted = false vim.api.nvim_buf_delete(self.buf, { unload = true }) self.buf = nil endend
return Terminal