diff --git a/docs/manual/configuring/dag-entries.md b/docs/manual/configuring/dag-entries.md index 402cde66..32dd4c6e 100644 --- a/docs/manual/configuring/dag-entries.md +++ b/docs/manual/configuring/dag-entries.md @@ -15,9 +15,11 @@ entries in nvf: 5. `theme` (this is simply placed before `pluginConfigs`, meaning that surrounding entries don't depend on it) - used to set up the theme, which has to be done before other plugins -6. `pluginConfigs` - the result of the nested `vim.pluginRC` (internal option, +6. `lazyConfigs` - `lz.n` and `lzn-auto-require` configs. If `vim.lazy.enable` + is false, this will contain each plugin's config instead. +7. `pluginConfigs` - the result of the nested `vim.pluginRC` (internal option, see the [Custom Plugins](/index.xhtml#ch-custom-plugins) page for adding your own plugins) DAG, used to set up internal plugins -7. `extraPluginConfigs` - the result of `vim.extraPlugins`, which is not a +8. `extraPluginConfigs` - the result of `vim.extraPlugins`, which is not a direct DAG, but is converted to, and resolved as one internally -8. `mappings` - the result of `vim.maps` +9. `mappings` - the result of `vim.maps` diff --git a/docs/manual/hacking/additional-plugins.md b/docs/manual/hacking/additional-plugins.md index bd2d7a64..8531aa98 100644 --- a/docs/manual/hacking/additional-plugins.md +++ b/docs/manual/hacking/additional-plugins.md @@ -162,7 +162,7 @@ in { } ``` -This results in the lua code: +This results in the following lua code: ```lua require('lz.n').load({ { diff --git a/modules/plugins/assistant/copilot/config.nix b/modules/plugins/assistant/copilot/config.nix index 9c337148..9f92d14a 100644 --- a/modules/plugins/assistant/copilot/config.nix +++ b/modules/plugins/assistant/copilot/config.nix @@ -56,21 +56,12 @@ in { (mkLuaKeymap ["i"] cfg.mappings.suggestion.prev "function() require('copilot.suggestion').prev() end" "[copilot] previous suggestion" {}) ]; }; - - copilot-cmp = mkIf cfg.cmp.enable { - package = "copilot-cmp"; - lazy = true; - after = optionalString config.vim.lazy.enable '' - local path = vim.fn.globpath(vim.o.packpath, 'pack/*/opt/copilot-cmp') - require("rtp_nvim").source_after_plugin_dir(path) - require("lz.n").trigger_load("copilot-lua") - ''; - }; - - nvim-cmp.after = mkIf cfg.cmp.enable "require('lz.n').trigger_load('copilot-cmp')"; }; - autocomplete.nvim-cmp.sources = {copilot = "[Copilot]";}; + autocomplete.nvim-cmp = { + sources = {copilot = "[Copilot]";}; + sourcePlugins = ["copilot-cmp"]; + }; # Disable plugin handled keymaps. # Setting it here so that it doesn't show up in user docs diff --git a/modules/plugins/completion/nvim-cmp/config.nix b/modules/plugins/completion/nvim-cmp/config.nix index 9140b05f..27d0bfb6 100644 --- a/modules/plugins/completion/nvim-cmp/config.nix +++ b/modules/plugins/completion/nvim-cmp/config.nix @@ -3,56 +3,57 @@ config, ... }: let - inherit (lib.modules) mkIf; + inherit (lib.modules) mkIf mkMerge; inherit (lib.strings) optionalString; inherit (lib.generators) mkLuaInline; inherit (lib.nvim.lua) toLuaObject; - inherit (builtins) attrNames; + inherit (lib.nvim.attrsets) mapListToAttrs; + inherit (builtins) attrNames typeOf tryEval concatStringsSep; cfg = config.vim.autocomplete.nvim-cmp; luasnipEnable = config.vim.snippets.luasnip.enable; + getPluginName = plugin: + if typeOf plugin == "string" + then plugin + else if (plugin ? pname && (tryEval plugin.pname).success) + then plugin.pname + else plugin.name; inherit (cfg) mappings; in { config = mkIf cfg.enable { vim = { startPlugins = ["rtp-nvim"]; - lazy.plugins = { - # cmp sources are loaded via lzn-auto-require as long as it is defined - # in cmp sources - cmp-buffer = { - package = "cmp-buffer"; - lazy = true; - after = '' - local path = vim.fn.globpath(vim.o.packpath, 'pack/*/opt/cmp-buffer') - require("rtp_nvim").source_after_plugin_dir(path) - ''; - }; - cmp-path = { - package = "cmp-path"; - lazy = true; - after = '' - local path = vim.fn.globpath(vim.o.packpath, 'pack/*/opt/cmp-path') - require("rtp_nvim").source_after_plugin_dir(path) - ''; - }; - nvim-cmp = { - package = "nvim-cmp"; - after = '' - ${optionalString luasnipEnable "local luasnip = require('luasnip')"} - require("lz.n").trigger_load("cmp-path") - local cmp = require("cmp") - cmp.setup(${toLuaObject cfg.setupOpts}) + lazy.plugins = mkMerge [ + (mapListToAttrs (package: { + name = getPluginName package; + value = { + inherit package; + lazy = true; + after = '' + local path = vim.fn.globpath(vim.o.packpath, 'pack/*/opt/${getPluginName package}') + require("rtp_nvim").source_after_plugin_dir(path) + ''; + }; + }) + cfg.sourcePlugins) + { + nvim-cmp = { + package = "nvim-cmp"; + after = '' + ${optionalString luasnipEnable "local luasnip = require('luasnip')"} + require("lz.n").trigger_load("cmp-path") + local cmp = require("cmp") + cmp.setup(${toLuaObject cfg.setupOpts}) - ${ - optionalString config.vim.lazy.enable '' - require("lz.n").trigger_load("cmp-buffer") - '' - } - ''; + ${concatStringsSep "\n" (map + (package: "require('lz.n').trigger_load(${toLuaObject (getPluginName package)})") + cfg.sourcePlugins)} + ''; - event = ["InsertEnter" "CmdlineEnter"]; - }; - }; + event = ["InsertEnter" "CmdlineEnter"]; + }; + } + ]; autocomplete.nvim-cmp = { sources = { @@ -61,6 +62,8 @@ in { path = "[Path]"; }; + sourcePlugins = ["cmp-buffer" "cmp-path"]; + setupOpts = { sources = map (s: {name = s;}) (attrNames cfg.sources); diff --git a/modules/plugins/completion/nvim-cmp/nvim-cmp.nix b/modules/plugins/completion/nvim-cmp/nvim-cmp.nix index 860a1c3f..8246e710 100644 --- a/modules/plugins/completion/nvim-cmp/nvim-cmp.nix +++ b/modules/plugins/completion/nvim-cmp/nvim-cmp.nix @@ -4,10 +4,10 @@ ... }: let inherit (lib.options) mkEnableOption mkOption literalExpression literalMD; - inherit (lib.types) str attrsOf nullOr either; + inherit (lib.types) str attrsOf nullOr either listOf; inherit (lib.generators) mkLuaInline; inherit (lib.nvim.binds) mkMappingOption; - inherit (lib.nvim.types) mkPluginSetupOption luaInline mergelessListOf; + inherit (lib.nvim.types) mkPluginSetupOption luaInline mergelessListOf pluginType; inherit (lib.nvim.lua) toLuaObject; inherit (builtins) isString; @@ -99,5 +99,11 @@ in { } ''; }; + + sourcePlugins = mkOption { + type = listOf pluginType; + default = []; + description = "List of source plugins used by nvim-cmp."; + }; }; } diff --git a/modules/plugins/debugger/nvim-dap/config.nix b/modules/plugins/debugger/nvim-dap/config.nix index 78e86a8c..7e9e8f76 100644 --- a/modules/plugins/debugger/nvim-dap/config.nix +++ b/modules/plugins/debugger/nvim-dap/config.nix @@ -57,7 +57,7 @@ in { lazy.plugins.nvim-dap-ui = { package = "nvim-dap-ui"; setupModule = "dapui"; - setupOpts = {}; + inherit (cfg.ui) setupOpts; keys = [ (mkSetLuaLznBinding mappings.toggleDapUI "function() require('dapui').toggle() end") diff --git a/modules/plugins/debugger/nvim-dap/nvim-dap.nix b/modules/plugins/debugger/nvim-dap/nvim-dap.nix index 3fab33ae..5a699491 100644 --- a/modules/plugins/debugger/nvim-dap/nvim-dap.nix +++ b/modules/plugins/debugger/nvim-dap/nvim-dap.nix @@ -2,12 +2,16 @@ inherit (lib.options) mkEnableOption mkOption; inherit (lib.types) bool attrsOf str; inherit (lib.nvim.binds) mkMappingOption; + inherit (lib.nvim.types) mkPluginSetupOption; in { options.vim.debugger.nvim-dap = { enable = mkEnableOption "debugging via nvim-dap"; ui = { enable = mkEnableOption "UI extension for nvim-dap"; + + setupOpts = mkPluginSetupOption "nvim-dap-ui" {}; + autoStart = mkOption { type = bool; default = true; diff --git a/modules/plugins/lsp/config.nix b/modules/plugins/lsp/config.nix index 63c21d5a..841e28bb 100644 --- a/modules/plugins/lsp/config.nix +++ b/modules/plugins/lsp/config.nix @@ -5,7 +5,6 @@ ... }: let inherit (lib.modules) mkIf; - inherit (lib.lists) optional; inherit (lib.strings) optionalString; inherit (lib.trivial) boolToString; inherit (lib.nvim.binds) addDescriptionsToMappings; @@ -23,20 +22,11 @@ in { config = mkIf cfg.enable { vim = { - lazy.plugins = { - cmp-nvim-lsp = { - package = "cmp-nvim-lsp"; - lazy = true; - after = '' - local path = vim.fn.globpath(vim.o.packpath, 'pack/*/opt/cmp-treesitter') - require("rtp_nvim").source_after_plugin_dir(path) - ''; - }; - nvim-cmp.after = mkIf usingNvimCmp "require('lz.n').trigger_load('cmp-nvim-lsp')"; + autocomplete.nvim-cmp = { + sources = {nvim_lsp = "[LSP]";}; + sourcePlugins = ["cmp-nvim-lsp"]; }; - autocomplete.nvim-cmp.sources = {nvim_lsp = "[LSP]";}; - pluginRC.lsp-setup = '' vim.g.formatsave = ${boolToString cfg.formatOnSave}; @@ -126,7 +116,7 @@ in { end local capabilities = vim.lsp.protocol.make_client_capabilities() - ${optionalString usingNvimCmp "capabilities = require('cmp_nvim_lsp').default_capabilities()"} + -- ${optionalString usingNvimCmp "capabilities = require('cmp_nvim_lsp').default_capabilities()"} ''; }; }; diff --git a/modules/plugins/lsp/trouble/config.nix b/modules/plugins/lsp/trouble/config.nix index e4b966a4..cae0c7ad 100644 --- a/modules/plugins/lsp/trouble/config.nix +++ b/modules/plugins/lsp/trouble/config.nix @@ -1,6 +1,7 @@ { config, lib, + options, ... }: let inherit (lib.modules) mkIf; @@ -8,8 +9,7 @@ cfg = config.vim.lsp; - self = import ./trouble.nix {inherit lib;}; - mappingDefinitions = self.options.vim.lsp.trouble.mappings; + mappingDefinitions = options.vim.lsp.trouble.mappings; mappings = addDescriptionsToMappings cfg.trouble.mappings mappingDefinitions; in { config = mkIf (cfg.enable && cfg.trouble.enable) { diff --git a/modules/plugins/snippets/luasnip/config.nix b/modules/plugins/snippets/luasnip/config.nix index 4fbbd2cd..927b21fd 100644 --- a/modules/plugins/snippets/luasnip/config.nix +++ b/modules/plugins/snippets/luasnip/config.nix @@ -4,7 +4,6 @@ ... }: let inherit (lib.modules) mkIf; - inherit (lib.strings) optionalString; cfg = config.vim.snippets.luasnip; in { @@ -16,20 +15,12 @@ in { lazy = true; after = cfg.loaders; }; - cmp-luasnip = mkIf config.vim.autocomplete.nvim-cmp.enable { - package = "cmp-luasnip"; - lazy = true; - after = '' - local path = vim.fn.globpath(vim.o.packpath, 'pack/*/opt/cmp-luasnip') - require("rtp_nvim").source_after_plugin_dir(path) - ''; - }; - nvim-cmp.after = optionalString config.vim.lazy.enable '' - require("lz.n").trigger_load("cmp-luasnip") - ''; }; startPlugins = cfg.providers; - autocomplete.nvim-cmp.sources = {luasnip = "[LuaSnip]";}; + autocomplete.nvim-cmp = { + sources = {luasnip = "[LuaSnip]";}; + sourcePlugins = ["cmp-luasnip"]; + }; }; }; } diff --git a/modules/plugins/treesitter/config.nix b/modules/plugins/treesitter/config.nix index e810d7e5..e863d048 100644 --- a/modules/plugins/treesitter/config.nix +++ b/modules/plugins/treesitter/config.nix @@ -5,7 +5,7 @@ ... }: let inherit (lib.modules) mkIf mkMerge; - inherit (lib.lists) optional optionals; + inherit (lib.lists) optionals; inherit (lib.nvim.binds) mkSetBinding addDescriptionsToMappings; inherit (lib.nvim.lua) toLuaObject; inherit (lib.nvim.dag) entryBefore entryAfter; @@ -32,7 +32,11 @@ in { nvim-cmp.after = mkIf usingNvimCmp "require('lz.n').trigger_load('cmp-treesitter')"; }; - autocomplete.nvim-cmp.sources = {treesitter = "[Treesitter]";}; + autocomplete.nvim-cmp = { + sources = {treesitter = "[Treesitter]";}; + sourcePlugins = ["cmp-treesitter"]; + }; + treesitter.grammars = optionals cfg.addDefaultGrammars cfg.defaultGrammars; maps = { diff --git a/modules/plugins/utility/telescope/config.nix b/modules/plugins/utility/telescope/config.nix index 37bdc0f9..d42e1bbc 100644 --- a/modules/plugins/utility/telescope/config.nix +++ b/modules/plugins/utility/telescope/config.nix @@ -1,6 +1,6 @@ { + options, config, - pkgs, lib, ... }: let @@ -11,8 +11,7 @@ inherit (lib.nvim.binds) pushDownDefault mkSetLznBinding; cfg = config.vim.telescope; - self = import ./telescope.nix {inherit pkgs lib;}; - mappingDefinitions = self.options.vim.telescope.mappings; + mappingDefinitions = options.vim.telescope.mappings; mappings = addDescriptionsToMappings cfg.mappings mappingDefinitions; in { diff --git a/modules/wrapper/lazy/config.nix b/modules/wrapper/lazy/config.nix index da5dd8c1..01deeb0f 100644 --- a/modules/wrapper/lazy/config.nix +++ b/modules/wrapper/lazy/config.nix @@ -58,6 +58,8 @@ }; lznSpecs = mapAttrsToList toLuaLznSpec cfg.plugins; + pluginPackages = mapAttrsToList (_: plugin: plugin.package) cfg.plugins; + specToNotLazyConfig = _: spec: '' do ${optionalString (spec.before != null) spec.before} @@ -74,25 +76,32 @@ then [] else [spec.keys]; - notLazyConfig = concatStringsSep "\n" (mapAttrsToList specToNotLazyConfig cfg.plugins); + notLazyConfig = + concatStringsSep "\n" + (mapAttrsToList specToNotLazyConfig cfg.plugins); + + beforeAllJoined = + concatStringsSep "\n" + (filter (x: x != null) (mapAttrsToList (_: spec: spec.beforeAll) cfg.plugins)); in { config.vim = mkMerge [ (mkIf cfg.enable { startPlugins = ["lz-n" "lzn-auto-require"]; - optPlugins = mapAttrsToList (_: plugin: plugin.package) cfg.plugins; + optPlugins = pluginPackages; - luaConfigRC.lzn-load = entryBefore ["pluginConfigs"] '' + lazy.builtLazyConfig = '' require('lz.n').load(${toLuaObject lznSpecs}) + ${optionalString cfg.enableLznAutoRequire "require('lzn-auto-require').enable()"} ''; }) (mkIf (!cfg.enable) { - startPlugins = mapAttrsToList (_: plugin: plugin.package) cfg.plugins; - luaConfigPre = - concatStringsSep "\n" - (filter (x: x != null) (mapAttrsToList (_: spec: spec.beforeAll) cfg.plugins)); - luaConfigRC.unlazy = entryAfter ["pluginConfigs"] notLazyConfig; + startPlugins = pluginPackages; + lazy.builtLazyConfig = '' + ${beforeAllJoined} + ${notLazyConfig} + ''; keymaps = concatLists (mapAttrsToList specToKeymaps cfg.plugins); }) ]; diff --git a/modules/wrapper/lazy/lazy.nix b/modules/wrapper/lazy/lazy.nix index e16a8aa2..5b2c53d1 100644 --- a/modules/wrapper/lazy/lazy.nix +++ b/modules/wrapper/lazy/lazy.nix @@ -35,7 +35,7 @@ mode = mkOption { description = "Modes to bind in"; - type = listOf str; + type = either str (listOf str); default = ["n" "x" "s" "o"]; }; @@ -181,7 +181,7 @@ }; in { options.vim.lazy = { - enable = mkEnableOption "plugin lazy-loading" // {default = true;}; + enable = mkEnableOption "plugin lazy-loading via lz.n and lzn-auto-require" // {default = true;}; loader = mkOption { description = "Lazy loader to use"; type = enum ["lz.n"]; @@ -215,5 +215,23 @@ in { } ''; }; + + enableLznAutoRequire = mkOption { + description = '' + Enable lzn-auto-require. Since builtin plugins rely on this, only turn + off for debugging. + ''; + type = bool; + default = true; + }; + + builtLazyConfig = mkOption { + internal = true; + type = lines; + description = '' + The built config for lz.n, or if `vim.lazy.enable` is false, the + individual plugin configs. + ''; + }; }; } diff --git a/modules/wrapper/rc/config.nix b/modules/wrapper/rc/config.nix index 25fc9bcf..627fd05b 100644 --- a/modules/wrapper/rc/config.nix +++ b/modules/wrapper/rc/config.nix @@ -52,11 +52,10 @@ in { optionsScript = entryAfter ["basic"] (concatLines optionsScript); # Basic - pluginConfigs = entryAfter ["optionsScript"] pluginConfigs; + lazyConfigs = entryAfter ["optionsScript"] cfg.lazy.builtLazyConfig; + pluginConfigs = entryAfter ["lazyConfigs"] pluginConfigs; extraPluginConfigs = entryAfter ["pluginConfigs"] extraPluginConfigs; mappings = entryAfter ["extraPluginConfigs"] keymaps; - # FIXME: put this somewhere less stupid - footer = entryAfter ["mappings"] (optionalString config.vim.lazy.enable "require('lzn-auto-require').enable()"); }; builtLuaConfigRC = let