summaryrefslogtreecommitdiff
path: root/pkgs/custom-neovim/config/lua/winbar.lua
blob: 62020654b4244eece65264a07f586fbd8d2b25e7 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
-- Custom Winbar

-- Wherher to use icons.
local use_icons = true

-- Utility functions for components.
local utils = {}

-- The width of the winbar.
utils.linewidth = function ()
  return vim.api.nvim_win_get_width(0)
end

utils.component_takes_percentage = function (comp_width, percentage)
  return comp_width > (percentage/100) * utils.linewidth()
end

-- Highlighting Shortcut
local hi_pattern = '%%#%s#%s%%*'

-- Define Components
local components = {}

-- Filename component
components.filename = function (args)
  args = args or {}
  local before = args.before or ""
  local after = args.after or ""

  -- Get filename
  local filename = vim.fn.expand("%t")

  -- Shorten if too large
  if utils.component_takes_percentage(#filename, 40) then
    filename = vim.fn.pathshorten(filename)
  end
  if utils.component_takes_percentage(#filename, 80) then
    return ""
  end

  -- Handle empty filenames
  if filename == "" then
    filename = "[No Name]"
  end

  -- Get modified status
  local modified_bool = vim.bo.modified
  local modifiable_bool = vim.bo.modifiable

  local modified = ""

  if modified_bool then modified = "[+]" end
  if not modifiable_bool then modified = "[-]" end

  -- append space if not empty
  if modified ~= "" then
    modified = " "..modified
  end

  -- Compose component
  return before..filename..modified..after
end

-- Git status component
components.git_status = function (args)
  args = args or {}
  local before = args.before or ""
  local after = args.after or ""

  if not vim.b.minidiff_summary then return "" end

  local summary = vim.b.minidiff_summary

  local status = {}

  local add_icon = use_icons and " " or "+"
  local change_icon = use_icons and " " or "~"
  local delete_icon = use_icons and " " or "-"

  if (summary.add or 0) > 0 then
    table.insert(status, hi_pattern:format("Added", ("%s%s"):format(add_icon, summary.add)))
  end
  if (summary.change or 0) > 0 then
    table.insert(status, hi_pattern:format("Changed", ("%s%s"):format(change_icon, summary.change)))
  end
  if (summary.delete or 0) > 0 then
    table.insert(status, hi_pattern:format("Removed", ("%s%s"):format(delete_icon, summary.delete)))
  end

  return before..table.concat(status, " ")..after
end

-- Diagnostics component
components.diagnostics = function (args)
  args = args or {}
  local before = args.before or ""
  local after = args.after or ""

  -- Define icons
  local error_icon = use_icons and " " or "E"
  local warning_icon = use_icons and " " or "W"
  local info_icon = use_icons and " " or "I"
  local hint_icon = use_icons and " " or "H"

  -- Create empty diagnostics table
  local diagnostics = {}

  -- Count diagnostics
  local errors = #vim.diagnostic.get(0, { severity = 1 })

  if errors > 0 then
    table.insert(diagnostics, hi_pattern:format("DiagnosticSignError", ("%s%s"):format(error_icon, errors)))
  end

  local warnings = #vim.diagnostic.get(0, { severity = 2 })

  if warnings > 0 then
    table.insert(diagnostics, hi_pattern:format("DiagnosticSignWarn", ("%s%s"):format(warning_icon, warnings)))
  end

  local infos = #vim.diagnostic.get(0, { severity = 3 })

  if infos > 0 then
    table.insert(diagnostics, hi_pattern:format("DiagnosticSignInfo", ("%s%s"):format(info_icon, infos)))
  end

  local hints = #vim.diagnostic.get(0, { severity = 4 })

  if hints > 0 then
    table.insert(diagnostics, hi_pattern:format("DiagnosticSignHint", ("%s%s"):format(hint_icon, hints)))
  end

  -- Don't show diagnostics in insert mode.
  if vim.api.nvim_get_mode().mode:find "i" then
    return ""
  end

  local icon = use_icons and '' or 'diag: '

  local status = hi_pattern:format("Statusline", table.concat(diagnostics, " "))

  return before..icon..status..after
end

-- Define winbar
local winbar = function ()
  return {
    components.filename({before = " "}),
    components.git_status(),
    components.diagnostics(),
  }
end

-- Gaps between components.
local gaps = " "

-- Process and apply statusline.
Winbar_builder = function ()
  --get a table of all the winbar strings
  local winbar_strings = winbar()

  -- Remove empty strings to prevent concat issues
  for i = #winbar_strings, 1, -1 do
    if winbar_strings[i] == "" then
      table.remove(winbar_strings, i)
    end
  end

  -- Concatentate strings with gaps
  return table.concat(winbar_strings, gaps)
end

vim.o.winbar = "%{%v:lua.Winbar_builder()%}"