*nvim-cmp* *cmp* A completion plugin for neovim coded in Lua. ============================================================================== CONTENTS *cmp-contents* Abstract |cmp-abstract| Concept |cmp-concept| Usage |cmp-usage| Function |cmp-function| Mapping |cmp-mapping| Command |cmp-command| Highlight |cmp-highlight| Autocmd |cmp-autocmd| Config |cmp-config| Config Helper |cmp-config-helper| Develop |cmp-develop| FAQ |cmp-faq| ============================================================================== Abstract *cmp-abstract* This is nvim-cmp's document. 1. This help file uses the type definition notation like `{lsp,cmp,vim}.*` - You can find it in `../lua/cmp/types/init.lua`. 2. Advanced configuration is described on the wiki. - https://github.com/hrsh7th/nvim-cmp/wiki ============================================================================== Concept *cmp-concept* - Full support for LSP completion related capabilities - Powerful customization abilities via Lua functions - Smart handling of key mapping - No flicker ============================================================================== Usage *cmp-usage* Recommended configuration is written below. NOTE: 1. You must provide `snippet.expand` function. 2. `cmp.setup.cmdline` won't work if you use `native` completion menu. 3. You can disable the `default` options via specifying `cmp.config.disable` value. > call plug#begin(s:plug_dir) Plug 'neovim/nvim-lspconfig' Plug 'hrsh7th/cmp-nvim-lsp' Plug 'hrsh7th/cmp-buffer' Plug 'hrsh7th/cmp-path' Plug 'hrsh7th/cmp-cmdline' Plug 'hrsh7th/nvim-cmp' " For vsnip users. Plug 'hrsh7th/cmp-vsnip' Plug 'hrsh7th/vim-vsnip' " For luasnip users. " Plug 'L3MON4D3/LuaSnip' " Plug 'saadparwaiz1/cmp_luasnip' " For snippy users. " Plug 'dcampos/nvim-snippy' " Plug 'dcampos/cmp-snippy' " For ultisnips users. " Plug 'SirVer/ultisnips' " Plug 'quangnguyen30192/cmp-nvim-ultisnips' call plug#end() set completeopt=menu,menuone,noselect lua <'] = cmp.mapping.scroll_docs(-4), [''] = cmp.mapping.scroll_docs(4), [''] = cmp.mapping.complete(), [''] = cmp.mapping.confirm({ select = true }), }), sources = cmp.config.sources({ { name = 'nvim_lsp' }, { name = 'vsnip' }, -- For vsnip users. -- { name = 'luasnip' }, -- For luasnip users. -- { name = 'snippy' }, -- For snippy users. -- { name = 'ultisnips' }, -- For ultisnips users. }, { { name = 'buffer' }, }) }) -- `/` cmdline setup. cmp.setup.cmdline('/', { mapping = cmp.mapping.preset.cmdline(), sources = { { name = 'buffer' } } }) -- `:` cmdline setup. cmp.setup.cmdline(':', { mapping = cmp.mapping.preset.cmdline(), sources = cmp.config.sources({ { name = 'path' } }, { { name = 'cmdline' } }) }) -- Setup lspconfig. local capabilities = require('cmp_nvim_lsp').update_capabilities(vim.lsp.protocol.make_client_capabilities()) require('lspconfig')[%YOUR_LSP_SERVER%].setup { capabilities = capabilities } EOF < ============================================================================== Function *cmp-function* NOTE: `lua require('cmp').complete()` can be used to call these functions in mapping. *cmp.setup* (config: cmp.ConfigSchema) Setup global configuration. See configuration options. *cmp.setup.filetype* (filetype: string, config: cmp.ConfigSchema) Setup filetype-specific configuration. *cmp.setup.buffer* (config: cmp.ConfigSchema) Setup configuration for the current buffer. *cmp.setup.cmdline* (cmdtype: string, config: cmp.ConfigSchema) Setup cmdline configuration for the specific type of cmd. See |getcmdtype()| NOTE: nvim-cmp does not support the `=` cmd type. *cmp.visible* () Return boolean showing whether the completion menu is visible or not. *cmp.get_entries* () Return all current entries. *cmp.get_selected_entry* () Return current selected entry (contains preselected). *cmp.get_active_entry* () Return current selected entry (without preselected). *cmp.close* () Close the completion menu. *cmp.abort* () Closes the completion menu and restore the current line to the state when it was started current completion. *cmp.select_next_item* (option: { behavior = cmp.SelectBehavior }) Select next item. *cmp.select_prev_item* (option: { behavior = cmp.SelectBehavior })* Select previous item. *cmp.scroll_docs* (delta: number) Scroll docs if visible. *cmp.complete* (option: { reason = cmp.ContextReason, config = cmp.ConfigSchema }) Invoke completion. The following configurations defines the key mapping to show completion only for vsnip snippets. > cmp.setup { mapping = { [''] = cmp.mapping.complete({ config = { sources = { { name = 'vsnip' } } } }) } } < > inoremap lua require('cmp').complete({ config = { sources = { { name = 'vsnip' } } } }) < NOTE: `config` in that case means a temporary setting, but `config.mapping` remains permanent. *cmp.complete_common_string* () Complete common string (reminds shell completion behavior). > cmp.setup { mapping = { [''] = cmp.mapping(function(fallback) if cmp.visible() then return cmp.complete_common_string() end fallback() end, { 'i', 'c' }), } } < *cmp.confirm* (option: cmp.ConfirmOption, callback: function) Accepts current selected completion item. If you didn't select any item and `{ select = true }` is specified for this, nvim-cmp would automatically select the first item. *cmp.event:on* ('%EVENT_NAME%, callback) Subscribe to nvim-cmp's event. Events are listed below. - `complete_done`: emit after current completion is done. - `confirm_done`: emit after confirmation is done. ============================================================================== Mapping *cmp-mapping* Nvim-cmp's mapping mechanism is complex but flexible and user-friendly. You can specify the mapping function that receives the `fallback` function as argument. The `fallback` function can be used to call an existing mapping. For example, typical pair-wise plugin automatically defines the mappings for `` and `(`. Nvim-cmp might overwrite it via specified mapping. But you can use existing mapping via invoking the `fallback` function. > cmp.setup { mapping = { [''] = function(fallback) if cmp.visible() then cmp.confirm() else fallback() -- If you use vim-endwise, this fallback will behave as vim-endwise. end end } } < > cmp.setup { mapping = { [''] = function(fallback) if cmp.visible() then cmp.select_next_item() else fallback() end end } } < And you can specify the mapping modes. > cmp.setup { mapping = { [''] = cmp.mapping(your_mapping_function, { 'i', 'c' }) } } < And you can specify different mappings for different modes using the same key. > cmp.setup { mapping = { [''] = cmp.mapping({ i = your_mapping_function_a, c = your_mapping_function_b, }) } } < You can also use built-in mapping helpers. *cmp.mapping.close* () Same as |cmp.close|. *cmp.mapping.abort* () Same as |cmp.abort|. *cmp.mapping.select_next_item* (option: { behavior = cmp.SelectBehavior }) Same as |cmp.select_next_item|. *cmp.mapping.select_prev_item* (option: { behavior = cmp.SelectBehavior }) Same as |cmp.select_prev_item|. *cmp.mapping.scroll_docs* (delta: number) Same as |cmp.scroll_docs|. *cmp.mapping.complete* (option: cmp.CompleteParams) Same as |cmp.complete|. *cmp.mapping.complete_common_string* () Same as |cmp.complete_common_string|. *cmp.mapping.confirm* (option: cmp.ConfirmOption) Same as |cmp.confirm|. Built-in mapping helpers are only available as a configuration option. If you want to call nvim-cmp features directly, please use |cmp-function| instead. ============================================================================== Command *cmp-command* *CmpStatus* Describes statuses and states of sources. Sometimes `unknown` source will be printed but it isn't problem. For that reason `cmp-nvim-lsp` registered on the InsertEnter autocmd will have `unknown` status. ============================================================================== Highlight *cmp-highlight* *CmpItemAbbr* Highlights unmatched characters of each completion field. *CmpItemAbbrDeprecated* Highlights unmatched characters of each deprecated completion field. *CmpItemAbbrMatch* Highlights matched characters of each completion field. Matched characters must form a substring of a field which share a starting position. *CmpItemAbbrMatchFuzzy* Highlights fuzzy-matched characters of each completion field. *CmpItemKind* Highlights kind of the field. NOTE: `kind` is a symbol after each completion option. *CmpItemKind%KIND_NAME%* Highlights kind of the field for specific `lsp.CompletionItemKind`. If you only want to overwrite the `method` kind's highlight group, you can do this: > highlight CmpItemKindMethod guibg=NONE guifg=Orange < *CmpItemMenu* The menu field's highlight group. ============================================================================== Autocmd *cmp-autocmd* You can create custom autocommands for certain nvim-cmp events by defining autocommands for the User event with the following patterns: *CmpReady* Invoked when nvim-cmp gets sourced from `plugin/cmp.lua`. ============================================================================== Config *cmp-config* You can use the following options via `cmp.setup { ... }` . *cmp-config.enabled* enabled~ `boolean | fun(): boolean` Toggles the plugin on and off. *cmp-config.preselect* preselect~ `cmp.PreselectMode` 1. `cmp.PreselectMode.Item` nvim-cmp will pre-select the item that the source specified. 2. `cmp.PreselectMode.None` nvim-cmp wouldn't pre-select any items. *cmp-config.mapping* mapping~ `table final_score = orig_score + ((#sources - (source_index - 1)) * sorting.priority_weight) < *cmp-config.sorting.comparators* sorting.comparators~ `(fun(entry1: cmp.Entry, entry2: cmp.Entry): boolean | nil)[]` The function to customize the sorting behavior. You can use built-in comparators via `cmp.config.compare.*`. *cmp-config.sources* sources~ `cmp.SourceConfig[]` List of the sources and their configurations to use. Order of the sources matters for sorting order. *cmp-config.sources[n].name* sources[n].name~ `string` The source name. *cmp-config.sources[n].option* sources[n].option~ `table` The specific options defined by the source itself. *cmp-config.sources[n].keyword_length* sources[n].keyword_length~ `number` The source specific keyword length to trigger auto completion. *cmp-config.sources[n].keyword_pattern* sources[n].keyword_pattern~ `number` The source specific keyword pattern. *cmp-config.sources[n].trigger_characters* sources[n].trigger_characters~ `string[]` The source specific keyword pattern. *cmp-config.sources[n].priority* sources[n].priority~ `number` The source specific priority value. *cmp-config.sources[n].max_item_count* sources[n].max_item_count~ `number` The source specific item count. *cmp-config.sources[n].group_index* sources[n].group_index~ `number` The source group index. For instance, you can specify the `buffer`'s source `group_index` to bigger number if you don't want to see the buffer source items when nvim-lsp source is available. > cmp.setup { sources = { { name = 'nvim_lsp', group_index = 1 }, { name = 'buffer', group_index = 2 }, } } < You can specify this via the built-in configuration helper like this. > cmp.setup { sources = cmp.config.sources({ { name = 'nvim_lsp' }, }, { { name = 'buffer' }, }) } < *cmp-config.view* view~ `{ entries: cmp.EntriesConfig|string }` Specify the view class to customize appearance. Currently available configuration options are: *cmp-config.window.{completion,documentation}.border* window.{completion,documentation}.border~ `string | string[] | nil` Border characters used for the completion popup menu when |experimental.native_menu| is disabled. See |nvim_open_win|. *cmp-config.window.{completion,documentation}.winhighlight* window.{completion,documentation}.winhighlight~ `string | cmp.WinhighlightConfig` Specify the window's winhighlight option. See |nvim_open_win|. *cmp-config.window.{completion,documentation}.zindex* window.{completion,documentation}.zindex~ `number` The completion window's zindex. See |nvim_open_win|. *cmp-config.window.documentation.max_width* window.documentation.max_width~ `number` The documentation window's max width. *cmp-config.window.documentation.max_height* window.documentation.max_height~ `number` The documentation window's max height. *cmp-config.experimental.ghost_text* experimental.ghost_text~ `boolean | { hl_group = string }` Whether to enable the ghost_text feature. ============================================================================== Config Helper *cmp-config-helper* You can use the following configuration helpers: cmp.config.compare~ TBD cmp.config.context~ The `cmp.config.context` can be used for context-aware completion toggling. > cmp.setup { enabled = function() -- disable completion if the cursor is `Comment` syntax group. return not cmp.config.context.in_syntax_group('Comment') end } < *cmp.config.context.in_syntax_group* (group) You can specify the vim's built-in syntax group. If you use tree-sitter, you should use `cmp.config.context.in_treesitter_capture` instead. *cmp.config.context.in_treesitter_capture* (capture) You can specify the treesitter capture name. If you don't use `nvim-treesitter`, this helper doesn't work correctly. cmp.config.mapping~ See |cmp-mapping| cmp.config.sources~ *cmp.config.sources* (...sources) You can specify multiple source arrays. The sources are grouped in the order you specify, and the groups are displayed as a fallback, like chain completion. > cmp.setup { sources = cmp.config.sources({ { name = 'nvim_lsp' }, }, { { name = 'buffer' }, }) } < cmp.config.window~ *cmp.config.window.bordered* (option) Make window `bordered`. The option is described in `cmp.ConfigSchema`. > cmp.setup { window = { completion = cmp.config.window.bordered(), documentation = cmp.config.window.bordered(), } } < ============================================================================== Develop *cmp-develop* Create custom source~ NOTE: 1. The `complete` method is required. Others can be omitted. 2. The `callback` argument must always be called. 3. You can use only `require('cmp')` in custom source. 4. If LSP spec was changed, nvim-cmp would follow it without any announcement. 5. You should read ./lua/cmp/types and https://microsoft.github.io/language-server-protocol/specifications/specification-current. 6. Please add `nvim-cmp` topic for github repo. You can create custom source like the following example. > local source = {} ---Return this source is available in current context or not. (Optional) ---@return boolean function source:is_available() return true end ---Return the debug name of this source. (Optional) ---@return string function source:get_debug_name() return 'debug name' end ---Return keyword pattern for triggering completion. (Optional) ---If this is ommited, nvim-cmp will use default keyword pattern. See |cmp-config.completion.keyword_pattern| ---@return string function source:get_keyword_pattern() return [[\k\+]] end ---Return trigger characters for triggering completion. (Optional) function source:get_trigger_characters() return { '.' } end ---Invoke completion. (Required) ---@param params cmp.SourceCompletionApiParams ---@param callback fun(response: lsp.CompletionResponse|nil) function source:complete(params, callback) callback({ { label = 'January' }, { label = 'February' }, { label = 'March' }, { label = 'April' }, { label = 'May' }, { label = 'June' }, { label = 'July' }, { label = 'August' }, { label = 'September' }, { label = 'October' }, { label = 'November' }, { label = 'December' }, }) end ---Resolve completion item. (Optional) ---@param completion_item lsp.CompletionItem ---@param callback fun(completion_item: lsp.CompletionItem|nil) function source:resolve(completion_item, callback) callback(completion_item) end ---Execute command after item was accepted. ---@param completion_item lsp.CompletionItem ---@param callback fun(completion_item: lsp.CompletionItem|nil) function source:execute(completion_item, callback) callback(completion_item) end ---Register custom source to nvim-cmp. require('cmp').register_source('month', source.new()) < ============================================================================== FAQ *cmp-faq* Why does cmp automatically select a particular item? ~ How to disable the preselect feature? ~ Nvim-cmp respects LSP(Language Server Protocol) specification. The LSP spec defines the `preselect` feature for completion. You can disable the `preselect` feature like the following. > cmp.setup { preselect = cmp.PreselectMode.None } < Why nvim-cmp confirm item automatically?~ How to disable commitCharacters?~ You can disable commitCharacters feature (that defined in LSP spec). > cmp.setup { confirmation = { get_commit_characters = function(commit_characters) return {} end } } < How to disable auto-completion?~ How to use nvim-cmp as like omnifunc?~ You can disable auto-completion like this. > cmp.setup { ... completion = { autocomplete = false } ... } < And you can invoke completion manually. > inoremap lua require('cmp').complete() < How to disable nvim-cmp on the specific buffer?~ How to setup on the specific buffer?~ You can setup buffer specific configuration like this. > cmp.setup.filetype({ 'markdown', 'help' }, { sources = { { name = 'path' }, { name = 'buffer' }, } }) < How to disable documentation window?~ You can use the following config. > cmp.setup.filetype({ 'markdown', 'help' }, { window = { documentation = cmp.config.disable } }) < How to integrate with copilot.vim?~ Copilot.vim and nvim-cmp both have a `key-mapping fallback` mechanism. Therefore, you should manage those plugins by yourself. Fortunately, the copilot.vim has the feature that disables the fallback mechanism. > let g:copilot_no_tab_map = v:true imap (vimrc:copilot-dummy-map) copilot#Accept("\") < You can manage copilot.vim's accept feature with nvim-cmp' key-mapping configuration. > cmp.setup { mapping = { [''] = cmp.mapping(function(fallback) vim.api.nvim_feedkeys(vim.fn['copilot#Accept'](vim.api.nvim_replace_termcodes('', true, true, true)), 'n', true) end) }, experimental = { ghost_text = false -- this feature conflict with copilot.vim's preview. } } < How to customize menu appearance?~ You can see nvim-cmp wiki (https://github.com/hrsh7th/nvim-cmp/wiki). ============================================================================== vim:tw=78:ts=2:et:ft=help:norl: