feat(api): support for ask customization (#527)

Signed-off-by: Aaron Pham <contact@aarnphm.xyz>
This commit is contained in:
Aaron Pham 2024-09-04 09:15:32 -04:00 committed by GitHub
parent a4a037cec1
commit d10cca4265
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 71 additions and 31 deletions

View File

@ -84,11 +84,21 @@ M.build = function(opts)
return pid
end
---@param question? string
M.ask = function(question)
if not require("avante").toggle() then return false end
if question == nil or question == "" then return true end
vim.api.nvim_exec_autocmds("User", { pattern = "AvanteInputSubmitted", data = { request = question } })
---@class AskOptions
---@field question? string optional questions
---@field win? table<string, any> windows options similar to |nvim_open_win()|
---@param opts? AskOptions
M.ask = function(opts)
opts = opts or {}
if type(opts) == "string" then
Utils.warn("passing 'ask' as string is deprecated, do {question = '...'} instead", { once = true })
opts = { question = opts }
end
if not require("avante").toggle_sidebar(opts) then return false end
if opts.question == nil or opts.question == "" then return true end
vim.api.nvim_exec_autocmds("User", { pattern = "AvanteInputSubmitted", data = { request = opts.question } })
return true
end
@ -108,7 +118,8 @@ M.get_suggestion = function()
return suggestion
end
M.refresh = function()
---@param opts? AskOptions
M.refresh = function(opts)
local sidebar = require("avante").get()
if not sidebar then return end
if not sidebar:is_open() then return end
@ -125,7 +136,7 @@ M.refresh = function()
sidebar:close()
sidebar.code.winid = curwin
sidebar.code.bufnr = curbuf
sidebar:render()
sidebar:render(opts)
end
return setmetatable(M, {

View File

@ -32,11 +32,33 @@ H.commands = function()
api.nvim_create_user_command("Avante" .. n, c, o)
end
cmd(
"Ask",
function(opts) require("avante.api").ask(vim.trim(opts.args)) end,
{ desc = "avante: ask AI for code suggestions", nargs = "*" }
)
cmd("Ask", function(opts)
---@type AskOptions
local args = { question = nil, win = {} }
local q_parts = {}
for _, arg in ipairs(opts.fargs) do
local value = arg:match("position=(%w+)")
if value then
args.win.position = value
else
table.insert(q_parts, arg)
end
end
args.question = #q_parts > 0 and table.concat(q_parts, " ") or nil
require("avante.api").ask(args)
end, {
desc = "avante: ask AI for code suggestions",
nargs = "*",
complete = function(_, _, _)
local candidates = {} ---@type string[]
vim.list_extend(
candidates,
---@param x string
vim.tbl_map(function(x) return "position=" .. x end, { "left", "right", "top", "bottom" })
)
return candidates
end,
})
cmd("Toggle", function() M.toggle() end, { desc = "avante: toggle AI panel" })
cmd(
"Edit",
@ -258,6 +280,19 @@ end
M.toggle = { api = true }
---@param opts? AskOptions
M.toggle_sidebar = function(opts)
opts = opts or {}
local sidebar = M.get()
if not sidebar then
M._init(api.nvim_get_current_tabpage())
M.current.sidebar:open(opts)
return true
end
return sidebar:toggle(opts)
end
M.toggle.debug = H.api(Utils.toggle_wrap({
name = "debug",
get = function() return Config.debug end,
@ -272,16 +307,7 @@ M.toggle.hint = H.api(Utils.toggle_wrap({
setmetatable(M.toggle, {
__index = M.toggle,
__call = function()
local sidebar = M.get()
if not sidebar then
M._init(api.nvim_get_current_tabpage())
M.current.sidebar:open()
return true
end
return sidebar:toggle()
end,
__call = function() M.toggle_sidebar() end,
})
---@param opts? avante.Config

View File

@ -66,18 +66,19 @@ function Sidebar:reset()
self.input = nil
end
function Sidebar:open()
---@param opts? AskOptions
function Sidebar:open(opts)
local in_visual_mode = Utils.in_visual_mode() and self:in_code_win()
if not self:is_open() then
self:reset()
self:initialize()
self:render()
self:render(opts)
else
if in_visual_mode then
self:close()
self:reset()
self:initialize()
self:render()
self:render(opts)
return self
end
self:focus()
@ -121,13 +122,14 @@ end
function Sidebar:in_code_win() return self.code.winid == api.nvim_get_current_win() end
function Sidebar:toggle()
---@param opts? table<string, any>
function Sidebar:toggle(opts)
local in_visual_mode = Utils.in_visual_mode() and self:in_code_win()
if self:is_open() and not in_visual_mode then
self:close()
return false
else
self:open()
self:open(opts)
return true
end
end
@ -1002,8 +1004,7 @@ local function get_chat_record_prefix(timestamp, provider, model, request)
end
function Sidebar:get_layout()
if Config.windows.position == "left" or Config.windows.position == "right" then return "vertical" end
return "horizontal"
return vim.tbl_contains({ "left", "right" }, Config.windows.position) and "vertical" or "horizontal"
end
function Sidebar:update_content_with_history(history)
@ -1478,10 +1479,12 @@ function Sidebar:get_selected_code_size()
return selected_code_size
end
function Sidebar:render()
---@param opts? AskOptions
function Sidebar:render(opts)
opts = opts or {}
local chat_history = Path.history.load(self.code.bufnr)
local get_position = function() return Config.windows.position end
local get_position = function() return (opts and opts.win.position) and opts.win.position or Config.windows.position end
local get_height = function()
local selected_code_size = self:get_selected_code_size()