diff --git a/configuration.nix b/configuration.nix index b21b26aa..b08479aa 100644 --- a/configuration.nix +++ b/configuration.nix @@ -105,12 +105,10 @@ isMaximal: { transparent = false; }; - autopairs.enable = true; + autopairs.nvim-autopairs.enable = true; - autocomplete = { - enable = true; - type = "nvim-cmp"; - }; + autocomplete.nvim-cmp.enable = true; + snippets.vsnip.enable = true; filetree = { nvimTree = { diff --git a/lib/attrsets.nix b/lib/attrsets.nix new file mode 100644 index 00000000..59275af9 --- /dev/null +++ b/lib/attrsets.nix @@ -0,0 +1,5 @@ +{lib}: let + inherit (builtins) listToAttrs; +in { + mapListToAttrs = f: list: listToAttrs (map f list); +} diff --git a/lib/default.nix b/lib/default.nix index a418cff8..e6ccd2a7 100644 --- a/lib/default.nix +++ b/lib/default.nix @@ -10,6 +10,7 @@ dag = import ./dag.nix {inherit lib;}; languages = import ./languages.nix {inherit lib;}; lists = import ./lists.nix {inherit lib;}; + attrsets = import ./attrsets.nix {inherit lib;}; lua = import ./lua.nix {inherit lib;}; neovimConfiguration = import ../modules {inherit inputs lib;}; } diff --git a/lib/languages.nix b/lib/languages.nix index e47202ee..52f1b5b8 100644 --- a/lib/languages.nix +++ b/lib/languages.nix @@ -2,8 +2,8 @@ {lib}: let inherit (builtins) isString getAttr; inherit (lib.options) mkOption; - inherit (lib.attrsets) listToAttrs; inherit (lib.types) bool; + inherit (lib.nvim.attrsets) mapListToAttrs; in { # Converts a boolean to a yes/no string. This is used in lots of # configuration formats. @@ -12,21 +12,21 @@ in { config, diagnosticsProviders, }: - listToAttrs - (map (v: let - type = - if isString v - then v - else getAttr v.type; - package = - if isString v - then diagnosticsProviders.${type}.package - else v.package; - in { - name = "${lang}-diagnostics-${type}"; - value = diagnosticsProviders.${type}.nullConfig package; - }) - config); + mapListToAttrs + (v: let + type = + if isString v + then v + else getAttr v.type; + package = + if isString v + then diagnosticsProviders.${type}.package + else v.package; + in { + name = "${lang}-diagnostics-${type}"; + value = diagnosticsProviders.${type}.nullConfig package; + }) + config; mkEnable = desc: mkOption { diff --git a/modules/plugins/assistant/copilot/config.nix b/modules/plugins/assistant/copilot/config.nix index c9e6f830..923a0c6d 100644 --- a/modules/plugins/assistant/copilot/config.nix +++ b/modules/plugins/assistant/copilot/config.nix @@ -34,6 +34,8 @@ in { "copilot-cmp" ]; + vim.autocomplete.nvim-cmp.sources = {copilot = "[Copilot]";}; + vim.pluginRC.copilot = entryAnywhere '' require("copilot").setup(${toLuaObject cfg.setupOpts}) diff --git a/modules/plugins/autopairs/nvim-autopairs/config.nix b/modules/plugins/autopairs/nvim-autopairs/config.nix index 6ef7cbfb..fcf8c71a 100644 --- a/modules/plugins/autopairs/nvim-autopairs/config.nix +++ b/modules/plugins/autopairs/nvim-autopairs/config.nix @@ -4,16 +4,15 @@ ... }: let inherit (lib.modules) mkIf; - inherit (lib.trivial) boolToString; inherit (lib.nvim.dag) entryAnywhere; + inherit (lib.nvim.lua) toLuaObject; - cfg = config.vim.autopairs; + cfg = config.vim.autopairs.nvim-autopairs; in { config = mkIf cfg.enable { - vim.startPlugins = ["nvim-autopairs"]; - - vim.pluginRC.autopairs = entryAnywhere '' - require("nvim-autopairs").setup({ map_cr = ${boolToString (!config.vim.autocomplete.enable)} }) - ''; + vim = { + startPlugins = ["nvim-autopairs"]; + pluginRC.autopairs = entryAnywhere "require('nvim-autopairs').setup(${toLuaObject cfg.setupOpts})"; + }; }; } diff --git a/modules/plugins/autopairs/nvim-autopairs/nvim-autopairs.nix b/modules/plugins/autopairs/nvim-autopairs/nvim-autopairs.nix index 7e456063..4bfa9998 100644 --- a/modules/plugins/autopairs/nvim-autopairs/nvim-autopairs.nix +++ b/modules/plugins/autopairs/nvim-autopairs/nvim-autopairs.nix @@ -1,21 +1,14 @@ {lib, ...}: let inherit (lib) mkRemovedOptionModule; - inherit (lib.options) mkEnableOption mkOption; - inherit (lib.types) enum; + inherit (lib.options) mkEnableOption; + inherit (lib.nvim.types) mkPluginSetupOption; in { imports = [ (mkRemovedOptionModule ["vim" "autopairs" "nvim-compe"] "nvim-compe is deprecated and no longer suported.") ]; - options.vim = { - autopairs = { - enable = mkEnableOption "autopairs" // {default = false;}; - - type = mkOption { - type = enum ["nvim-autopairs"]; - default = "nvim-autopairs"; - description = "Set the autopairs type. Options: nvim-autopairs [nvim-autopairs]"; - }; - }; + options.vim.autopairs.nvim-autopairs = { + enable = mkEnableOption "autopairs" // {default = false;}; + setupOpts = mkPluginSetupOption "nvim-autopairs" {}; }; } diff --git a/modules/plugins/completion/nvim-cmp/config.nix b/modules/plugins/completion/nvim-cmp/config.nix index a28db3ed..97415ae1 100644 --- a/modules/plugins/completion/nvim-cmp/config.nix +++ b/modules/plugins/completion/nvim-cmp/config.nix @@ -3,246 +3,176 @@ config, ... }: let - inherit (builtins) toJSON; - inherit (lib.modules) mkIf mkMerge; - inherit (lib.attrsets) attrNames mapAttrsToList; - inherit (lib.strings) concatMapStringsSep concatStringsSep optionalString; - inherit (lib.nvim.binds) addDescriptionsToMappings mkSetLuaBinding; - inherit (lib.nvim.dag) entryAnywhere entryAfter; + inherit (lib.modules) mkIf; + inherit (lib.strings) optionalString; + inherit (lib.generators) mkLuaInline; + inherit (lib.nvim.binds) addDescriptionsToMappings; + inherit (lib.nvim.dag) entryAnywhere; + inherit (lib.nvim.lua) toLuaObject; + inherit (builtins) attrNames; - cfg = config.vim.autocomplete; - lspkindEnabled = config.vim.lsp.enable && config.vim.lsp.lspkind.enable; - - self = import ./nvim-cmp.nix {inherit lib;}; - mappingDefinitions = self.options.vim.autocomplete.mappings; + cfg = config.vim.autocomplete.nvim-cmp; + vsnipEnable = config.vim.snippets.vsnip.enable; + self = import ./nvim-cmp.nix {inherit lib config;}; + mappingDefinitions = self.options.vim.autocomplete.nvim-cmp.mappings; mappings = addDescriptionsToMappings cfg.mappings mappingDefinitions; - - builtSources = - concatMapStringsSep - "\n" - (n: "{ name = '${n}'},") - (attrNames cfg.sources); - - builtMaps = - concatStringsSep - "\n" - (mapAttrsToList - (n: v: - if v == null - then "" - else "${n} = '${v}',") - cfg.sources); - - dagPlacement = - if lspkindEnabled - then entryAfter ["lspkind"] - else entryAnywhere; in { config = mkIf cfg.enable { - vim.startPlugins = [ - "nvim-cmp" - "cmp-buffer" - "cmp-vsnip" - "cmp-path" - "vim-vsnip" - ]; + vim = { + startPlugins = [ + "nvim-cmp" + "cmp-buffer" + "cmp-path" + ]; - vim.autocomplete.sources = { - "nvim-cmp" = null; - "vsnip" = "[VSnip]"; - "buffer" = "[Buffer]"; - "crates" = "[Crates]"; - "path" = "[Path]"; - "copilot" = "[Copilot]"; - }; + autocomplete.nvim-cmp.sources = { + nvim-cmp = null; + buffer = "[Buffer]"; + path = "[Path]"; + }; - vim.maps.insert = mkMerge [ - (mkSetLuaBinding mappings.complete '' - require('cmp').complete - '') - (let - defaultKeys = - if config.vim.autopairs.enable - then "require('nvim-autopairs').autopairs_cr()" - else "vim.api.nvim_replace_termcodes(${toJSON mappings.confirm.value}, true, false, true)"; - in - mkSetLuaBinding mappings.confirm '' - function() - if not require('cmp').confirm({ select = true }) then - vim.fn.feedkeys(${defaultKeys}, 'n') - end - end - '') - (mkSetLuaBinding mappings.next '' - function() - local has_words_before = function() - local line, col = unpack(vim.api.nvim_win_get_cursor(0)) - return col ~= 0 and vim.api.nvim_buf_get_lines(0, line - 1, line, true)[1]:sub(col, col):match("%s") == nil - end + autopairs.nvim-autopairs.setupOpts.map_cr = false; - local cmp = require('cmp') + autocomplete.nvim-cmp.setupOpts = { + sources = map (s: {name = s;}) (attrNames cfg.sources); - local feedkey = function(key, mode) - vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes(key, true, true, true), mode, true) - end + # TODO: try to get nvim-cmp to follow global border style + window = mkIf config.vim.ui.borders.enable { + completion = mkLuaInline "cmp.config.window.bordered()"; + documentation = mkLuaInline "cmp.config.window.bordered()"; + }; - if cmp.visible() then - cmp.select_next_item() - elseif vim.fn['vsnip#available'](1) == 1 then - feedkey("(vsnip-expand-or-jump)", "") - elseif has_words_before() then - cmp.complete() - else - local termcode = vim.api.nvim_replace_termcodes(${toJSON mappings.next.value}, true, false, true) + formatting.format = cfg.format; + }; - vim.fn.feedkeys(termcode, 'n') - end - end - '') - (mkSetLuaBinding mappings.previous '' - function() - local cmp = require('cmp') + pluginRC.nvim-cmp = mkIf cfg.enable (entryAnywhere '' + local cmp = require("cmp") + cmp.setup(${toLuaObject cfg.setupOpts}) - local feedkey = function(key, mode) - vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes(key, true, true, true), mode, true) - end - - if cmp.visible() then - cmp.select_prev_item() - elseif vim.fn['vsnip#available'](-1) == 1 then - feedkeys("(vsnip-jump-prev)", "") - end - end - '') - (mkSetLuaBinding mappings.close '' - require('cmp').mapping.abort() - '') - (mkSetLuaBinding mappings.scrollDocsUp '' - require('cmp').mapping.scroll_docs(-4) - '') - (mkSetLuaBinding mappings.scrollDocsDown '' - require('cmp').mapping.scroll_docs(4) - '') - ]; - - vim.maps.command = mkMerge [ - (mkSetLuaBinding mappings.complete '' - require('cmp').complete - '') - (mkSetLuaBinding mappings.close '' - require('cmp').mapping.close() - '') - (mkSetLuaBinding mappings.scrollDocsUp '' - require('cmp').mapping.scroll_docs(-4) - '') - (mkSetLuaBinding mappings.scrollDocsDown '' - require('cmp').mapping.scroll_docs(4) - '') - ]; - - vim.maps.select = mkMerge [ - (mkSetLuaBinding mappings.next '' - function() - local cmp = require('cmp') - local has_words_before = function() - local line, col = unpack(vim.api.nvim_win_get_cursor(0)) - return col ~= 0 and vim.api.nvim_buf_get_lines(0, line - 1, line, true)[1]:sub(col, col):match("%s") == nil - end - - local feedkey = function(key, mode) - vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes(key, true, true, true), mode, true) - end - - if cmp.visible() then - cmp.select_next_item() - elseif vim.fn['vsnip#available'](1) == 1 then - feedkey("(vsnip-expand-or-jump)", "") - elseif has_words_before() then - cmp.complete() - else - local termcode = vim.api.nvim_replace_termcodes(${toJSON mappings.next.value}, true, false, true) - - vim.fn.feedkeys(termcode, 'n') - end - end - '') - (mkSetLuaBinding mappings.previous '' - function() - local cmp = require('cmp') - - local feedkey = function(key, mode) - vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes(key, true, true, true), mode, true) - end - - if cmp.visible() then - cmp.select_prev_item() - elseif vim.fn['vsnip#available'](-1) == 1 then - feedkeys("(vsnip-jump-prev)", "") - end - end - '') - ]; - - # TODO: alternative snippet engines to vsnip - # https://github.com/hrsh7th/nvim-cmp/blob/main/doc/cmp.txt#L82 - vim.pluginRC.completion = mkIf (cfg.type == "nvim-cmp") (dagPlacement '' - local nvim_cmp_menu_map = function(entry, vim_item) - -- name for each source - vim_item.menu = ({ - ${builtMaps} - })[entry.source.name] - return vim_item - end - - ${optionalString lspkindEnabled '' - lspkind_opts.before = ${cfg.formatting.format} - ''} - - local cmp = require'cmp' - cmp.setup({ - ${optionalString config.vim.ui.borders.enable '' - -- explicitly enabled by setting ui.borders.enable = true - -- TODO: try to get nvim-cmp to follow global border style - window = { - completion = cmp.config.window.bordered(), - documentation = cmp.config.window.bordered(), - }, - ''} - - snippet = { - expand = function(args) - vim.fn["vsnip#anonymous"](args.body) - end, - }, - - sources = { - ${builtSources} - }, - - completion = { - completeopt = 'menu,menuone,noinsert', - ${optionalString (!cfg.alwaysComplete) "autocomplete = false"} - }, - - formatting = { - format = - ${ - if lspkindEnabled - then "lspkind.cmp_format(lspkind_opts)" - else cfg.formatting.format - }, + ${ + optionalString config.vim.autopairs.nvim-autopairs.enable + '' + cmp.event:on('confirm_done', require("nvim-autopairs.completion.cmp").on_confirm_done({ map_char = { text = "" } })) + '' } - }) - ${optionalString (config.vim.autopairs.enable && config.vim.autopairs.type == "nvim-autopairs") '' - local cmp_autopairs = require('nvim-autopairs.completion.cmp') - cmp.event:on('confirm_done', cmp_autopairs.on_confirm_done({ map_char = { text = ""} })) - ''} - ''); + ''); - vim.snippets.vsnip.enable = - if (cfg.type == "nvim-cmp") - then true - else config.vim.snippets.vsnip.enable; + keymaps = [ + { + mode = ["i" "c"]; + key = mappings.complete.value; + lua = true; + action = "require('cmp').complete"; + desc = mappings.complete.description; + } + + { + mode = "i"; + key = mappings.confirm.value; + lua = true; + action = let + defaultKeys = + if config.vim.autopairs.nvim-autopairs.enable + then "require('nvim-autopairs').autopairs_cr()" + else "vim.api.nvim_replace_termcodes(${toLuaObject mappings.confirm.value}, true, false, true)"; + in '' + function() + if not require('cmp').confirm({ select = true }) then + vim.fn.feedkeys(${defaultKeys}, 'n') + end + end + ''; + desc = mappings.confirm.description; + } + + { + mode = ["i" "s"]; + key = mappings.next.value; + lua = true; + action = '' + function() + local has_words_before = function() + local line, col = unpack(vim.api.nvim_win_get_cursor(0)) + return col ~= 0 and vim.api.nvim_buf_get_lines(0, line - 1, line, true)[1]:sub(col, col):match("%s") == nil + end + + local cmp = require('cmp') + + local feedkey = function(key, mode) + vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes(key, true, true, true), mode, true) + end + + if cmp.visible() then + cmp.select_next_item() + ${ + optionalString vsnipEnable + '' + elseif vim.fn['vsnip#available'](1) == 1 then + feedkey("(vsnip-expand-or-jump)", "") + '' + } + elseif has_words_before() then + cmp.complete() + else + vim.fn.feedkeys(vim.api.nvim_replace_termcodes(${toLuaObject mappings.next.value}, true, false, true), 'n') + end + end + ''; + desc = mappings.next.description; + } + + { + mode = ["i" "s"]; + key = mappings.previous.value; + lua = true; + action = '' + function() + local cmp = require('cmp') + + local feedkey = function(key, mode) + vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes(key, true, true, true), mode, true) + end + + if cmp.visible() then + cmp.select_prev_item() + ${ + optionalString vsnipEnable + '' + elseif vim.fn['vsnip#available'](-1) == 1 then + feedkeys("(vsnip-jump-prev)", "") + '' + } + end + end + ''; + desc = mappings.previous.description; + } + + { + mode = ["i" "c"]; + key = mappings.close.value; + lua = true; + action = "require('cmp').mapping.abort()"; + desc = mappings.close.description; + } + + { + mode = ["i" "c"]; + key = mappings.scrollDocsUp.value; + lua = true; + action = "require('cmp').mapping.scroll_docs(-4)"; + desc = mappings.scrollDocsUp.description; + } + + { + mode = ["i" "c"]; + key = mappings.scrollDocsDown.value; + lua = true; + action = "require('cmp').mapping.scroll_docs(4)"; + desc = mappings.scrollDocsDown.description; + } + ]; + }; }; } diff --git a/modules/plugins/completion/nvim-cmp/default.nix b/modules/plugins/completion/nvim-cmp/default.nix index 603347f4..65578c38 100644 --- a/modules/plugins/completion/nvim-cmp/default.nix +++ b/modules/plugins/completion/nvim-cmp/default.nix @@ -1,4 +1,4 @@ -_: { +{ imports = [ ./config.nix ./nvim-cmp.nix diff --git a/modules/plugins/completion/nvim-cmp/nvim-cmp.nix b/modules/plugins/completion/nvim-cmp/nvim-cmp.nix index 8efa649f..1f74fbb7 100644 --- a/modules/plugins/completion/nvim-cmp/nvim-cmp.nix +++ b/modules/plugins/completion/nvim-cmp/nvim-cmp.nix @@ -1,72 +1,75 @@ -{lib, ...}: let - inherit (lib.options) mkEnableOption mkOption literalMD; +{ + lib, + config, + ... +}: let + inherit (lib.options) mkEnableOption mkOption literalExpression literalMD; + inherit (lib.types) str attrsOf nullOr; + inherit (lib.generators) mkLuaInline; inherit (lib.nvim.binds) mkMappingOption; - inherit (lib.types) enum attrsOf nullOr str bool; + inherit (lib.nvim.types) mkPluginSetupOption luaInline; + inherit (lib.nvim.lua) toLuaObject; + + cfg = config.vim.autocomplete.nvim-cmp; in { - options.vim = { - autocomplete = { - enable = mkEnableOption "autocomplete" // {default = false;}; - - alwaysComplete = mkOption { - type = bool; - description = "Automatically show completion."; - default = true; - }; - - mappings = { - complete = mkMappingOption "Complete [nvim-cmp]" ""; - confirm = mkMappingOption "Confirm [nvim-cmp]" ""; - next = mkMappingOption "Next item [nvim-cmp]" ""; - previous = mkMappingOption "Previous item [nvim-cmp]" ""; - close = mkMappingOption "Close [nvim-cmp]" ""; - scrollDocsUp = mkMappingOption "Scroll docs up [nvim-cmp]" ""; - scrollDocsDown = mkMappingOption "Scroll docs down [nvim-cmp]" ""; - }; - - type = mkOption { - type = enum ["nvim-cmp"]; - default = "nvim-cmp"; - description = "Set the autocomplete plugin. Options: [nvim-cmp]"; - }; - - sources = mkOption { + options.vim.autocomplete.nvim-cmp = { + enable = mkEnableOption "nvim-cmp" // {default = false;}; + setupOpts = mkPluginSetupOption "the autocomplete plugin" { + completion.completeopt = mkOption { + type = str; + default = "menu,menuone,noinsert"; description = '' - Attribute set of source names for nvim-cmp. + A comma-separated list of options for completion. - If an attribute set is provided, then the menu value of - `vim_item` in the format will be set to the value (if - utilizing the `nvim_cmp_menu_map` function). - - Note: only use a single attribute name per attribute set - ''; - type = attrsOf (nullOr str); - default = {}; - example = '' - {nvim-cmp = null; buffer = "[Buffer]";} + See `:help completeopt` for the complete list. ''; }; + }; - formatting = { - format = mkOption { - description = '' - The function used to customize the appearance of the completion menu. + mappings = { + complete = mkMappingOption "Complete [nvim-cmp]" ""; + confirm = mkMappingOption "Confirm [nvim-cmp]" ""; + next = mkMappingOption "Next item [nvim-cmp]" ""; + previous = mkMappingOption "Previous item [nvim-cmp]" ""; + close = mkMappingOption "Close [nvim-cmp]" ""; + scrollDocsUp = mkMappingOption "Scroll docs up [nvim-cmp]" ""; + scrollDocsDown = mkMappingOption "Scroll docs down [nvim-cmp]" ""; + }; - If [](#opt-vim.lsp.lspkind.enable) is true, then the function - will be called before modifications from lspkind. + format = mkOption { + type = luaInline; + default = mkLuaInline '' + function(entry, vim_item) + vim_item.menu = (${toLuaObject cfg.sources})[entry.source.name] + return vim_item + end + ''; + defaultText = literalMD '' + ```lua + function(entry, vim_item) + vim_item.menu = (''${toLuaObject config.vim.autocomplete.nvim-cmp.sources})[entry.source.name] + return vim_item + end + ``` + ''; + description = '' + The function used to customize the completion menu entires. + This is outside of `setupOpts` because of internal reasons. - Default is to call the menu mapping function. - ''; - type = str; - default = "nvim_cmp_menu_map"; - example = literalMD '' - ```lua - function(entry, vim_item) - return vim_item - end - ``` - ''; - }; - }; + See `:help cmp-config.formatting.format`. + ''; + }; + + sources = mkOption { + type = attrsOf (nullOr str); + default = {}; + description = "The list of sources used by nvim-cmp"; + example = literalExpression '' + { + nvim-cmp = null; + buffer = "[Buffer]"; + } + ''; }; }; } diff --git a/modules/plugins/languages/rust.nix b/modules/plugins/languages/rust.nix index 0f595761..b78ef74a 100644 --- a/modules/plugins/languages/rust.nix +++ b/modules/plugins/languages/rust.nix @@ -3,13 +3,12 @@ pkgs, lib, ... -}: let - inherit (builtins) attrNames; +}: let inherit (builtins) attrNames; inherit (lib.modules) mkIf mkMerge; inherit (lib.options) mkOption mkEnableOption; inherit (lib.strings) optionalString; inherit (lib.trivial) boolToString; - inherit (lib.lists) isList optionals; + inherit (lib.lists) isList; inherit (lib.types) bool package str listOf either enum; inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.lua) expToLua; @@ -101,7 +100,7 @@ in { vim = { startPlugins = ["crates-nvim"]; lsp.null-ls.enable = mkIf cfg.crates.codeActions true; - autocomplete.sources = {"crates" = "[Crates]";}; + autocomplete.nvim-cmp.sources = {crates = "[Crates]";}; pluginRC.rust-crates = entryAnywhere '' require('crates').setup { null_ls = { diff --git a/modules/plugins/lsp/config.nix b/modules/plugins/lsp/config.nix index a0aa7fee..52dc15b4 100644 --- a/modules/plugins/lsp/config.nix +++ b/modules/plugins/lsp/config.nix @@ -11,7 +11,7 @@ inherit (lib.nvim.binds) addDescriptionsToMappings; cfg = config.vim.lsp; - usingNvimCmp = config.vim.autocomplete.enable && config.vim.autocomplete.type == "nvim-cmp"; + usingNvimCmp = config.vim.autocomplete.nvim-cmp.enable; self = import ./module.nix {inherit config lib pkgs;}; mappingDefinitions = self.options.vim.lsp.mappings; @@ -25,7 +25,7 @@ in { vim = { startPlugins = optional usingNvimCmp "cmp-nvim-lsp"; - autocomplete.sources = {"nvim_lsp" = "[LSP]";}; + autocomplete.nvim-cmp.sources = {nvim_lsp = "[LSP]";}; pluginRC.lsp-setup = '' vim.g.formatsave = ${boolToString cfg.formatOnSave}; diff --git a/modules/plugins/lsp/lspkind/config.nix b/modules/plugins/lsp/lspkind/config.nix index 93426e0c..2ef20ff8 100644 --- a/modules/plugins/lsp/lspkind/config.nix +++ b/modules/plugins/lsp/lspkind/config.nix @@ -3,18 +3,32 @@ lib, ... }: let - inherit (lib.modules) mkIf; - inherit (lib.nvim.dag) entryAnywhere; + inherit (lib.modules) mkIf mkForce; + inherit (lib.generators) mkLuaInline; + inherit (lib.nvim.lua) toLuaObject; - cfg = config.vim.lsp; + cfg = config.vim.lsp.lspkind; in { - config = mkIf (cfg.enable && cfg.lspkind.enable) { - vim.startPlugins = ["lspkind"]; - vim.pluginRC.lspkind = entryAnywhere '' - local lspkind = require'lspkind' - local lspkind_opts = { - mode = '${cfg.lspkind.mode}' + config = mkIf cfg.enable { + assertions = [ + { + assertion = config.vim.autocomplete.nvim-cmp.enable; + message = '' + While lspkind supports Neovim's native lsp upstream, using that over + nvim-cmp isn't recommended, nor supported by nvf. + + Please migrate to nvim-cmp if you want to use lspkind. + ''; } - ''; + ]; + + vim = { + startPlugins = ["lspkind"]; + + lsp.lspkind.setupOpts.before = config.vim.autocomplete.nvim-cmp.format; + autocomplete.nvim-cmp.setupOpts.formatting.format = mkForce (mkLuaInline '' + require("lspkind").cmp_format(${toLuaObject cfg.setupOpts}) + ''); + }; }; } diff --git a/modules/plugins/lsp/lspkind/lspkind.nix b/modules/plugins/lsp/lspkind/lspkind.nix index 8ae9f39a..595decd7 100644 --- a/modules/plugins/lsp/lspkind/lspkind.nix +++ b/modules/plugins/lsp/lspkind/lspkind.nix @@ -1,16 +1,22 @@ {lib, ...}: let inherit (lib.options) mkEnableOption mkOption; - inherit (lib.types) enum; + inherit (lib.types) enum nullOr; + inherit (lib.nvim.types) mkPluginSetupOption luaInline; in { - options.vim.lsp = { - lspkind = { - enable = mkEnableOption "vscode-like pictograms for lsp [lspkind]"; - + options.vim.lsp.lspkind = { + enable = mkEnableOption "vscode-like pictograms for lsp [lspkind]"; + setupOpts = mkPluginSetupOption "lspkind.nvim" { mode = mkOption { description = "Defines how annotations are shown"; type = enum ["text" "text_symbol" "symbol_text" "symbol"]; default = "symbol_text"; }; + + before = mkOption { + description = "The function that will be called before lspkind's modifications are applied"; + type = nullOr luaInline; + default = null; + }; }; }; } diff --git a/modules/plugins/notes/obsidian/obsidian.nix b/modules/plugins/notes/obsidian/obsidian.nix index 6727430a..2dae5a9c 100644 --- a/modules/plugins/notes/obsidian/obsidian.nix +++ b/modules/plugins/notes/obsidian/obsidian.nix @@ -45,10 +45,10 @@ in { completion = { nvim_cmp = mkOption { - # if using nvim-cmp, otherwise set to false + # If using nvim-cmp, otherwise set to false type = bool; description = "If using nvim-cmp, otherwise set to false"; - default = config.vim.autocomplete.type == "nvim-cmp"; + default = config.vim.autocomplete.nvim-cmp.enable; }; }; }; diff --git a/modules/plugins/snippets/vsnip/config.nix b/modules/plugins/snippets/vsnip/config.nix index 5c6ba75f..3d58bbca 100644 --- a/modules/plugins/snippets/vsnip/config.nix +++ b/modules/plugins/snippets/vsnip/config.nix @@ -3,11 +3,28 @@ lib, ... }: let - inherit (lib.modules) mkIf; + inherit (lib.modules) mkIf mkMerge; + inherit (lib.generators) mkLuaInline; cfg = config.vim.snippets.vsnip; in { - config = mkIf cfg.enable { - vim.startPlugins = ["vim-vsnip"]; - }; + config = mkIf cfg.enable (mkMerge [ + { + vim.startPlugins = ["vim-vsnip"]; + } + + (mkIf config.vim.autocomplete.nvim-cmp.enable { + vim = { + startPlugins = ["cmp-vsnip"]; + autocomplete.nvim-cmp = { + sources = {"vsnip" = "[VSnip]";}; + setupOpts.snippet.expand = mkLuaInline '' + function(args) + vim.fn["vsnip#anonymous"](args.body) + end + ''; + }; + }; + }) + ]); } diff --git a/modules/plugins/theme/theme.nix b/modules/plugins/theme/theme.nix index 95d15d40..0422c027 100644 --- a/modules/plugins/theme/theme.nix +++ b/modules/plugins/theme/theme.nix @@ -4,10 +4,11 @@ ... }: let inherit (lib.options) mkOption; - inherit (lib.attrsets) attrNames listToAttrs; + inherit (lib.attrsets) attrNames; inherit (lib.strings) hasPrefix; inherit (lib.types) bool lines enum; inherit (lib.modules) mkIf; + inherit (lib.nvim.attrsets) mapListToAttrs; inherit (lib.nvim.dag) entryBefore; inherit (lib.nvim.types) hexColor; @@ -17,7 +18,8 @@ }; numbers = ["0" "1" "2" "3" "4" "5" "6" "7" "8" "9" "A" "B" "C" "D" "E" "F"]; - base16Options = listToAttrs (map (n: { + base16Options = + mapListToAttrs (n: { name = "base0${n}"; value = mkOption { description = "The base0${n} color to use"; @@ -28,7 +30,7 @@ else "#${v}"; }; }) - numbers); + numbers; in { options.vim.theme = { enable = mkOption { diff --git a/modules/plugins/treesitter/config.nix b/modules/plugins/treesitter/config.nix index 618da88e..ae093862 100644 --- a/modules/plugins/treesitter/config.nix +++ b/modules/plugins/treesitter/config.nix @@ -11,7 +11,7 @@ inherit (lib.nvim.dag) entryBefore entryAfter; cfg = config.vim.treesitter; - usingNvimCmp = config.vim.autocomplete.enable && config.vim.autocomplete.type == "nvim-cmp"; + usingNvimCmp = config.vim.autocomplete.nvim-cmp.enable; self = import ./treesitter.nix {inherit pkgs lib;}; mappingDefinitions = self.options.vim.treesitter.mappings; @@ -21,7 +21,7 @@ in { vim = { startPlugins = ["nvim-treesitter"] ++ optional usingNvimCmp "cmp-treesitter"; - autocomplete.sources = {"treesitter" = "[Treesitter]";}; + autocomplete.nvim-cmp.sources = {treesitter = "[Treesitter]";}; treesitter.grammars = optionals cfg.addDefaultGrammars cfg.defaultGrammars; maps = { diff --git a/modules/plugins/ui/noice/noice.nix b/modules/plugins/ui/noice/noice.nix index bf16e3f1..edd80ee1 100644 --- a/modules/plugins/ui/noice/noice.nix +++ b/modules/plugins/ui/noice/noice.nix @@ -21,7 +21,7 @@ in { mkBool true "override the lsp markdown formatter with Noice"; "cmp.entry.get_documentation" = - mkBool (config.vim.autocomplete.type == "nvim-cmp") "override cmp documentation with Noice"; + mkBool config.vim.autocomplete.nvim-cmp.enable "override cmp documentation with Noice"; }; signature = { diff --git a/modules/wrapper/rc/config.nix b/modules/wrapper/rc/config.nix index 6f9ed1ce..6cc1e4e9 100644 --- a/modules/wrapper/rc/config.nix +++ b/modules/wrapper/rc/config.nix @@ -4,7 +4,7 @@ ... }: let inherit (builtins) map mapAttrs filter; - inherit (lib.attrsets) mapAttrsToList filterAttrs; + inherit (lib.attrsets) mapAttrsToList; inherit (lib.strings) concatLines concatMapStringsSep; inherit (lib.trivial) showWarnings; inherit (lib.generators) mkLuaInline;