From 6eeeb16ed49cac766280aa5388ffcd1982d9d062 Mon Sep 17 00:00:00 2001
From: Hubert Pelczarski <41551030+hoob3rt@users.noreply.github.com>
Date: Mon, 22 Feb 2021 01:59:35 +0100
Subject: [PATCH] feat: diagnostics support (#95)
---
README.md | 37 ++++---
lua/lualine/components/diagnostics.lua | 133 +++++++++++++++++++++++++
2 files changed, 157 insertions(+), 13 deletions(-)
create mode 100644 lua/lualine/components/diagnostics.lua
diff --git a/README.md b/README.md
index 5fadb07..f4364e1 100644
--- a/README.md
+++ b/README.md
@@ -132,16 +132,17 @@ lualine.inactive_sections = {
Available components
* general
- * branch
- * encoding
- * fileformat
+ * branch (git branch)
+ * diagnostics (diagnostics count from your prefered source)
+ * encoding (file encoding)
+ * fileformat (file format)
* filename
* filetype
- * location
- * mode
- * progress
+ * location (location in file in line:column format)
+ * mode (vim mode)
+ * progress (%progress in file)
* plugin
- * signify
+ * signify (signify status)
@@ -219,6 +220,16 @@ color | nil | Sets custom color for the component in this format
`color
In addition, some components have unique options.
+* `diagnostics` component options
+
+Option | Default | Behaviour | Format
+:------: | :------: | :----: | :---:
+sources | `nil` | displays diagnostic count from defined source | array containing one or many string from set `{'nvim_lsp', 'coc', 'ale'}`
+sections | `{'error', 'warn', 'info'}` | displays diagnostics of defined severity | array containing one or many string from set `{'error', 'warn', 'info'}`
+color_error | `DiffDelete` foreground color | changes diagnostic's error section foreground color | color in `#rrggbb` format
+color_warn | `DiffText` foreground color | changes diagnostic's warn section foreground color | color in `#rrggbb` format
+color_info | `Normal` foreground color | changes diagnostic's info section foreground color | color in `#rrggbb` format
+
* `filename` component options
Option | Default | Behaviour
@@ -229,12 +240,12 @@ shorten | true | if `full_path` is true and `shorten` is `false` it shortens abs
* `signify` component options
-Option | Default | Behaviour
-:------: | :------: | :----:
-colored | true | displays signify status in color if set to `true`
-color_added | `diffAdd` foreground color | changes signify's added section foreground color
-color_modified | `diffChange` foreground color | changes signify's changed section foreground color
-color_removed | `diffDelete` foreground color | changes signify's removed section foreground color
+Option | Default | Behaviour | Format
+:------: | :------: | :----: | :---:
+colored | true | displays signify status in color if set to `true` |
+color_added | `DiffAdd` foreground color | changes signify's added section foreground color | color in `#rrggbb` format
+color_modified | `DiffChange` foreground color | changes signify's changed section foreground color | color in `#rrggbb` format
+color_removed | `DiffDelete` foreground color | changes signify's removed section foreground color | color in `#rrggbb` format
##### Component options example
diff --git a/lua/lualine/components/diagnostics.lua b/lua/lualine/components/diagnostics.lua
new file mode 100644
index 0000000..d7f30d2
--- /dev/null
+++ b/lua/lualine/components/diagnostics.lua
@@ -0,0 +1,133 @@
+-- Copyright (c) 2020-2021 hoob3rt
+-- MIT license, see LICENSE for more details.
+local highlight = require('lualine.highlight')
+local utils = require('lualine.utils.utils')
+
+local default_color_error = '#e32636'
+local default_color_warn = '#ffdf00'
+local default_color_info = '#ffffff'
+
+local diagnostic_sources = {
+ nvim_lsp = function()
+ local error_count = vim.lsp.diagnostic.get_count(0, 'Error')
+ local warning_count = vim.lsp.diagnostic.get_count(0, 'Warning')
+ local info_count = vim.lsp.diagnostic.get_count(0, 'Information') +
+ vim.lsp.diagnostic.get_count(0, 'Hint')
+ return error_count, warning_count, info_count
+ end,
+ coc = function()
+ local data = vim.b.coc_diagnostic_info
+ if data then
+ return data.error, data.warning, data.information
+ else
+ return 0, 0, 0
+ end
+ end,
+ ale = function()
+ local ok, data = pcall(vim.fn['ale#statusline#Count'], vim.fn.bufnr())
+ if ok then
+ return data.error, data.warning, data.info
+ else
+ return 0, 0, 0
+ end
+ end,
+}
+
+local function get_diagnostics(sources)
+ local result = {}
+ for index, source in ipairs(sources) do
+ local error_count, warning_count, info_count = diagnostic_sources[source]()
+ result[index] = {error = error_count, warn = warning_count, info = info_count}
+ end
+ return result
+end
+
+local function diagnostics(options)
+ local symbols
+ if options.icons_enabled then
+ symbols = {
+ error = ' ', -- xf659
+ warn = ' ', -- xf529
+ info = ' ', -- xf7fc
+ }
+ else
+ symbols = {
+ error = 'E:',
+ warn = 'W:',
+ info = 'I:'
+ }
+ end
+ if options.sources == nil then
+ print('no sources for diagnostics configured')
+ return ''
+ end
+ if options.sections == nil then options.sections = {'error', 'warn', 'info'} end
+ if options.colored == nil then options.colored = true end
+ -- apply colors
+ if not options.color_error then
+ options.color_error = utils.extract_highlight_colors('DiffDelete', 'foreground') or default_color_error
+ end
+ if not options.color_warn then
+ options.color_warn = utils.extract_highlight_colors('DiffText', 'foreground') or default_color_warn
+ end
+ if not options.color_info then
+ options.color_info = utils.extract_highlight_colors('Normal', 'foreground') or default_color_info
+ end
+
+ local highlight_groups = {}
+ local function add_highlights()
+ highlight_groups = {
+ error = highlight.create_component_highlight_group({ fg = options.color_error }, 'diagnostics_error', options),
+ warn = highlight.create_component_highlight_group({ fg = options.color_warn }, 'diagnostics_warn', options),
+ info = highlight.create_component_highlight_group({ fg = options.color_info }, 'diagnostics_info', options),
+ }
+ end
+
+ if options.colored then
+ add_highlights()
+ utils.expand_set_theme(add_highlights)
+ end
+
+ return function()
+ local error_count, warning_count, info_count = 0,0,0
+ local diagnostic_data = get_diagnostics(options.sources)
+ for _, data in pairs(diagnostic_data) do
+ error_count = error_count + data.error
+ warning_count = warning_count + data.warn
+ info_count = info_count + data.info
+ end
+ local result = {}
+ local data = {
+ error = error_count,
+ warn = warning_count,
+ info = info_count,
+ }
+ if options.colored then
+ local colors = {}
+ for name, hl in pairs(highlight_groups) do
+ colors[name] = highlight.component_format_highlight(hl)
+ end
+ for _, section in ipairs(options.sections) do
+ if data[section] ~= nil and data[section] > 0 then
+ table.insert(result, colors[section]..symbols[section]..data[section])
+ end
+ end
+ else
+ for _, section in ipairs(options.sections) do
+ if data[section] ~= nil and data[section] > 0 then
+ table.insert(result,symbols[section]..data[section])
+ end
+ end
+ end
+ if result[1] ~= nil then
+ return table.concat(result, ' ')
+ else
+ return ''
+ end
+ end
+end
+
+return {
+ init = function(options) return diagnostics(options) end,
+ get_diagnostics = get_diagnostics,
+}