diff --git a/nvim/lua/jj-snacks.lua b/nvim/lua/jj-snacks.lua new file mode 100644 index 0000000..63cd0da --- /dev/null +++ b/nvim/lua/jj-snacks.lua @@ -0,0 +1,110 @@ +Snacks.picker.jj_log = function() + Snacks.picker.pick({ + title = 'jj log', + supports_live = false, + finder = function(opts, ctx) + local cwd + cwd = opts and opts.cwd or vim.uv.cwd() or '.' + cwd = svim.fs.normalize(cwd) + cwd = vim.fs.root(cwd or 0, '.jj') + if not cwd then + Snacks.notify.error 'Cannot find `.jj` folder. To initialize a repository use `jj git init .`' + ctx.picker.closed = true + return {} + end + local template = [[ + separate("\0", + self.change_id().shortest(), + self.change_id().shortest(8), + commit_timestamp(self).format("%Y-%m-%d %H:%M"), + commit_id.shortest(), + commit_id.shortest(8), + empty, + if(description, + description.first_line(), + if(root, "root()", description_placeholder) + ), + self.author().name(), + current_working_copy, + immutable + ) ++ "\n" + ]] + local args = { + 'log', + '-r', + '::@', + '--color=never', + '--no-graph', + '--template=' .. template, + } + if opts.reversed then + table.insert(args, '--reversed') + end + vim.list_extend(args, opts.args or {}) + return require('snacks.picker.source.proc').proc( + ctx:opts({ + cmd = "jj", + args = args, + cwd = cwd, + ---@param item snacks.picker.finder.Item + transform = function(item) + local data = vim.split(item.text, '\0') + item.cwd = cwd + item.change_id_prefix = data[1] + item.change_id = data[2] + item.date = data[3] + item.commit_prefix = data[4] + item.commit = data[5] + item.empty = data[6] == "true" + item.msg = data[7] + item.author = data[8] + item.working_copy = data[9] == "true" + item.immutable = data[10] == "true" + end, + }), + ctx + ) + end, + format = function(item, picker) + local ret = {} ---@type snacks.picker.Highlight[] + if item.working_copy then + table.insert(ret, { "@", "SnacksPickerGitCommit" }) + elseif item.immutable then + table.insert(ret, { "◆", "SnacksPickerGitCommit" }) + else + table.insert(ret, { "○", "SnacksPickerGitCommit" }) + end + table.insert(ret, { ' ' }) + table.insert(ret, { item.change_id_prefix, 'SnacksPickerGitCommit' }) + table.insert(ret, { item.change_id:sub(#item.change_id_prefix + 1), 'SnacksPickerDimmed' }) + table.insert(ret, { ' ' }) + table.insert(ret, { item.date, 'SnacksPickerGitDate' }) + table.insert(ret, { ' ' }) + table.insert(ret, { picker.opts.icons.git.commit, "SnacksPickerGitStatusModified" }) + table.insert(ret, { item.commit_prefix, 'SnacksPickerGitStatusModified' }) + table.insert(ret, { item.commit:sub(#item.commit_prefix + 1), 'SnacksPickerDimmed' }) + table.insert(ret, { ' ' }) + if item.empty then + table.insert(ret, { '(empty) ', 'SnacksPickerDimmed' }) + end + if item.msg == '(no description set)' then + table.insert(ret, { item.msg, 'SnacksPickerDimmed' }) + else + Snacks.picker.highlight.extend(ret, Snacks.picker.format.commit_message(item, picker)) + end + table.insert(ret, { ' ' }) + table.insert(ret, { item.author, "SnacksPickerGitAuthor" }) + return ret + end, + preview = function(ctx) + local M = require 'snacks.picker.preview' + -- local cmd = { 'jj', 'log', '-r=' .. ctx.item.change_id, "--git" } + local cmd = { "git", "show", ctx.item.commit } + M.cmd(cmd, ctx, { ft = "git" }) + end, + confirm = function(picker, item) + picker:close() + end, + sort = { fields = { 'score:desc', 'idx' } }, + }) +end diff --git a/nvim/lua/plugins/git.lua b/nvim/lua/plugins/git.lua index ee60774..60124e8 100644 --- a/nvim/lua/plugins/git.lua +++ b/nvim/lua/plugins/git.lua @@ -94,7 +94,6 @@ return { local cmd = require("jj.cmd") vim.keymap.set("n", "jd", cmd.describe, { desc = "JJ describe" }) vim.keymap.set("n", "jc", cmd.commit, { desc = "JJ commit" }) - vim.keymap.set("n", "jl", cmd.log, { desc = "JJ log" }) vim.keymap.set("n", "jL", function() cmd.log({ revisions = "'all()'" }) end, { desc = "JJ log all" }) diff --git a/nvim/lua/plugins/snacks.lua b/nvim/lua/plugins/snacks.lua index d1bdfaa..9e732c4 100644 --- a/nvim/lua/plugins/snacks.lua +++ b/nvim/lua/plugins/snacks.lua @@ -98,8 +98,10 @@ return { [""] = { "close", mode = { "n", "i" } }, [""] = { "preview_scroll_up", mode = { "i", "n" } }, [""] = { "preview_scroll_down", mode = { "i", "n" } }, - [""] = function() vim.cmd "normal! I" end, - [""] = function() vim.cmd "startinsert!" end, + [""] = { function() vim.cmd "normal! I" end, mode = { "i" } }, + [""] = { function() vim.cmd "startinsert!" end, mode = { "i" } }, + [""] = { "toggle_help_input", mode = { "i" } }, + [""] = { "toggle_help_input", mode = { "i" } }, }, }, }, @@ -250,7 +252,7 @@ return { }, after = function(plug) require("snacks").setup(plug.opts) - + require(".jj-snacks") Snacks.picker.git_show = git_show vim.keymap.set("n", "zz", function() Snacks.zen() end, { desc = "Toggle zen mode" }) @@ -278,6 +280,9 @@ return { vim.keymap.set("n", "gs", function() Snacks.picker.git_status({ cwd = Snacks.git.get_root() }) end, { desc = "Git status" }) + + + vim.keymap.set("n", "jl", Snacks.picker.jj_log, { desc = "jj log" }) end, }, }