feat(picker): add new pickers with Snacks.picker.source.foo = {} and automatically add them to main picker

This commit is contained in:
Folke Lemaitre 2025-01-14 14:30:03 +01:00
parent 773e584d85
commit bba68a9631
No known key found for this signature in database
GPG key ID: 41F8B1FBACAE2040
3 changed files with 41 additions and 7 deletions

View file

@ -76,10 +76,33 @@ function M.setup()
did_setup = true
require("snacks.picker.config.highlights")
for source in pairs(Snacks.picker.config.get().sources) do
Snacks.picker[source] = function(opts)
return Snacks.picker.pick(source, opts)
M.wrap(source)
end
--- Automatically wrap new sources added after setup
setmetatable(require("snacks.picker.config.sources"), {
__newindex = function(t, k, v)
rawset(t, k, v)
M.wrap(k)
end,
})
end
---@param source string
---@param opts? {check?: boolean}
function M.wrap(source, opts)
if opts and opts.check then
local config = M.get()
if not config.sources[source] then
return
end
end
---@type fun(opts: snacks.picker.Config): snacks.Picker
local ret = function(_opts)
return Snacks.picker.pick(source, _opts)
end
---@diagnostic disable-next-line: no-unknown
Snacks.picker[source] = ret
return ret
end
return M

View file

@ -45,7 +45,7 @@ M.last = nil
---@type {pattern: string, search: string, live?: boolean}[]
M.history = {}
---@private
---@hide
---@param opts? snacks.picker.Config
function M.new(opts)
local self = setmetatable({}, M)

View file

@ -7,17 +7,29 @@
---@field preview snacks.picker.preview
---@field current? snacks.Picker
---@field highlight snacks.picker.highlight
---@field resume fun(opts?: snacks.picker.Config):snacks.Picker
---@field sources snacks.picker.sources.Config
---@overload fun(opts: snacks.picker.Config): snacks.Picker
---@overload fun(source: string, opts: snacks.picker.Config): snacks.Picker
local M = setmetatable({}, {
__call = function(M, ...)
return M.pick(...)
end,
---@param M snacks.picker
__index = function(M, k)
if k == "setup" then
if k == "setup" or type(k) ~= "string" then
return
end
local mods = { "actions", "config", "format", "preview", "util", "sorter", highlight = "util.highlight" }
local mods = {
"actions",
"config",
"format",
"preview",
"util",
"sorter",
highlight = "util.highlight",
sources = "config.sources",
}
for m, mod in pairs(mods) do
mod = mod == k and k or m == k and mod or nil
if mod then
@ -26,8 +38,7 @@ local M = setmetatable({}, {
return rawget(M, k)
end
end
M.config.setup()
return rawget(M, k)
return M.config.wrap(k, { check = true })
end,
})