From 21961967ffef6d49512b83a23b6c93bb8b80389a Mon Sep 17 00:00:00 2001 From: Jeremy Fleischman Date: Wed, 11 Dec 2024 17:29:54 -0800 Subject: [PATCH] feat(diagnostic): update quickfix list by title #31486 Previously, there was a singleton diagnostics quickfix list. Now there's effectively one per title (up to vim's internal limit on quickfix lists). Suggested by mfussenegger https://github.com/neovim/neovim/pull/30868#pullrequestreview-2385761374. --- runtime/doc/diagnostic.txt | 3 ++- runtime/doc/news.txt | 4 ++-- runtime/lua/vim/diagnostic.lua | 31 ++++++++++++++++++------------- 3 files changed, 22 insertions(+), 16 deletions(-) diff --git a/runtime/doc/diagnostic.txt b/runtime/doc/diagnostic.txt index eaa3681caa..3437717467 100644 --- a/runtime/doc/diagnostic.txt +++ b/runtime/doc/diagnostic.txt @@ -874,7 +874,8 @@ setqflist({opts}) *vim.diagnostic.setqflist()* • {open}? (`boolean`, default: `true`) Open quickfix list after setting. • {title}? (`string`) Title of quickfix list. Defaults to - "Diagnostics". + "Diagnostics". If there's already a quickfix list with this + title, it's updated. If not, a new quickfix list is created. • {severity}? (`vim.diagnostic.SeverityFilter`) See |diagnostic-severity|. diff --git a/runtime/doc/news.txt b/runtime/doc/news.txt index 07b1b8646a..e7d4b92f7e 100644 --- a/runtime/doc/news.txt +++ b/runtime/doc/news.txt @@ -315,8 +315,8 @@ UI |hl-PmenuSel| and |hl-PmenuMatch| both inherit from |hl-Pmenu|, and |hl-PmenuMatchSel| inherits highlights from both |hl-PmenuSel| and |hl-PmenuMatch|. -• |vim.diagnostic.setqflist()| updates existing diagnostics quickfix list if one - exists. +• |vim.diagnostic.setqflist()| updates an existing quickfix list with the + given title if found • |ui-messages| content chunks now also contain the highlight group ID. diff --git a/runtime/lua/vim/diagnostic.lua b/runtime/lua/vim/diagnostic.lua index 340bca4f6b..1b61cf8f71 100644 --- a/runtime/lua/vim/diagnostic.lua +++ b/runtime/lua/vim/diagnostic.lua @@ -2,7 +2,19 @@ local api, if_nil = vim.api, vim.F.if_nil local M = {} -local _qf_id = nil +--- @param title string +--- @return integer? +local function get_qf_id_for_title(title) + local lastqflist = vim.fn.getqflist({ nr = '$' }) + for i = 1, lastqflist.nr do + local qflist = vim.fn.getqflist({ nr = i, id = 0, title = 0 }) + if qflist.title == title then + return qflist.id + end + end + + return nil +end --- [diagnostic-structure]() --- @@ -845,24 +857,16 @@ local function set_list(loclist, opts) if loclist then vim.fn.setloclist(winnr, {}, 'u', { title = title, items = items }) else - -- Check if the diagnostics quickfix list no longer exists. - if _qf_id and vim.fn.getqflist({ id = _qf_id }).id == 0 then - _qf_id = nil - end + local qf_id = get_qf_id_for_title(title) -- If we already have a diagnostics quickfix, update it rather than creating a new one. -- This avoids polluting the finite set of quickfix lists, and preserves the currently selected -- entry. - vim.fn.setqflist({}, _qf_id and 'u' or ' ', { + vim.fn.setqflist({}, qf_id and 'u' or ' ', { title = title, items = items, - id = _qf_id, + id = qf_id, }) - - -- Get the id of the newly created quickfix list. - if _qf_id == nil then - _qf_id = vim.fn.getqflist({ id = 0 }).id - end end if open then api.nvim_command(loclist and 'lwindow' or 'botright cwindow') @@ -2037,7 +2041,8 @@ end --- (default: `true`) --- @field open? boolean --- ---- Title of quickfix list. Defaults to "Diagnostics". +--- Title of quickfix list. Defaults to "Diagnostics". If there's already a quickfix list with this +--- title, it's updated. If not, a new quickfix list is created. --- @field title? string --- --- See |diagnostic-severity|.