Skip to content

Commit 7f8edca

Browse files
committed
feat(recipes): add AI completion engine boilerplate
1 parent c8d95cd commit 7f8edca

File tree

2 files changed

+85
-0
lines changed

2 files changed

+85
-0
lines changed
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
# AI Completion Boilerplate
2+
3+
**Website:** <https://docs.astronvim.com/recipes/ai>
4+
5+
This plugin specification configures completion engines to make `<Tab>` function as only snippet navigation and AI suggestion acceptance. Navigating completion items would then be done with other mappings such as `<C-n>`/`<C-p>`. AI plugins can then interface with this by setting up the `vim.g.ai_accept` as a function to do their acceptance command.
Lines changed: 80 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,80 @@
1+
return {
2+
{
3+
"AstroNvim/astrocore",
4+
opts = {
5+
options = {
6+
g = {
7+
ai_inline = true,
8+
ai_accept = nil, -- set in AI plugins to connect to the completion engines.
9+
},
10+
},
11+
},
12+
},
13+
{
14+
"hrsh7th/nvim-cmp",
15+
optional = true,
16+
opts = function(_, opts)
17+
local cmp = require "cmp"
18+
if not opts.mapping then opts.mapping = {} end
19+
opts.mapping["<Tab>"] = cmp.mapping(function(fallback)
20+
-- Snippet jump next (with support for several popular snippet plugins)
21+
local mini_snippets_avail, mini_snippets = pcall(require, "mini.snippets")
22+
local luasnip_avail, luasnip = pcall(require, "luasnip")
23+
if mini_snippets_avail then
24+
if mini_snippets.session.get(false) then
25+
mini_snippets.session.jump "next"
26+
return
27+
end
28+
elseif luasnip_avail then
29+
if luasnip.locally_jumpable(1) then
30+
luasnip.jump(1)
31+
return
32+
end
33+
elseif vim.snippet and vim.snippet.active { direction = 1 } then
34+
vim.schedule(function() vim.snippet.jump(1) end)
35+
return
36+
end
37+
-- AI accept
38+
if vim.g.ai_accept and vim.g.ai_accept() then return end
39+
-- Fallback
40+
fallback()
41+
end, { "i", "s" })
42+
opts.mapping["<S-Tab>"] = cmp.mapping(function(fallback)
43+
-- Snippet jump previous
44+
local mini_snippets_avail, mini_snippets = pcall(require, "mini.snippets")
45+
local luasnip_avail, luasnip = pcall(require, "luasnip")
46+
if mini_snippets_avail then
47+
if mini_snippets.session.get(false) then
48+
mini_snippets.session.jump "prev"
49+
return
50+
end
51+
elseif luasnip_avail then
52+
if luasnip.locally_jumpable(-1) then
53+
luasnip.jump(-1)
54+
return
55+
end
56+
elseif vim.snippet and vim.snippet.active { direction = -1 } then
57+
vim.schedule(function() vim.snippet.jump(-1) end)
58+
return
59+
end
60+
-- Fallback
61+
fallback()
62+
end, { "i", "s" })
63+
end,
64+
},
65+
{
66+
"Saghen/blink.cmp",
67+
optional = true,
68+
opts = function(_, opts)
69+
if not opts.keymap then opts.keymap = {} end
70+
opts.keymap["<Tab>"] = {
71+
"snippet_forward",
72+
function()
73+
if vim.g.ai_accept then return vim.g.ai_accept() end
74+
end,
75+
"fallback",
76+
}
77+
opts.keymap["<S-Tab>"] = { "snippet_backward", "fallback" }
78+
end,
79+
},
80+
}

0 commit comments

Comments
 (0)