Hyprland-dotfiles/nvim/lua/modules/configs/ui/lualine.lua
2024-07-21 02:51:17 -04:00

348 lines
9.1 KiB
Lua
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

return function()
local has_catppuccin = vim.g.colors_name:find("catppuccin") ~= nil
local colors = require("modules.utils").get_palette()
local icons = {
diagnostics = require("modules.utils.icons").get("diagnostics", true),
git = require("modules.utils.icons").get("git", true),
git_nosep = require("modules.utils.icons").get("git"),
misc = require("modules.utils.icons").get("misc", true),
ui = require("modules.utils.icons").get("ui", true),
}
local function custom_theme()
vim.api.nvim_create_autocmd("ColorScheme", {
group = vim.api.nvim_create_augroup("LualineColorScheme", { clear = true }),
pattern = "*",
callback = function()
has_catppuccin = vim.g.colors_name:find("catppuccin") ~= nil
require("lualine").setup({ options = { theme = custom_theme() } })
end,
})
if has_catppuccin then
colors = require("modules.utils").get_palette()
local universal_bg = require("core.settings").transparent_background and "NONE" or colors.mantle
return {
normal = {
a = { fg = colors.lavender, bg = colors.surface0, gui = "bold" },
b = { fg = colors.text, bg = universal_bg },
c = { fg = colors.text, bg = universal_bg },
},
command = {
a = { fg = colors.peach, bg = colors.surface0, gui = "bold" },
},
insert = {
a = { fg = colors.green, bg = colors.surface0, gui = "bold" },
},
visual = {
a = { fg = colors.flamingo, bg = colors.surface0, gui = "bold" },
},
terminal = {
a = { fg = colors.teal, bg = colors.surface0, gui = "bold" },
},
replace = {
a = { fg = colors.red, bg = colors.surface0, gui = "bold" },
},
inactive = {
a = { fg = colors.subtext0, bg = universal_bg, gui = "bold" },
b = { fg = colors.subtext0, bg = universal_bg },
c = { fg = colors.subtext0, bg = universal_bg },
},
}
else
return "auto"
end
end
local conditionals = {
has_enough_room = function()
return vim.o.columns > 100
end,
has_comp_before = function()
return vim.bo.filetype ~= ""
end,
has_git = function()
local gitdir = vim.fs.find(".git", {
limit = 1,
upward = true,
type = "directory",
path = vim.fn.expand("%:p:h"),
})
return #gitdir > 0
end,
}
---@class lualine_hlgrp
---@field fg string
---@field bg string
---@field gui string?
local utils = {
force_centering = function()
return "%="
end,
abbreviate_path = function(path)
local home = require("core.global").home
if path:find(home, 1, true) == 1 then
path = "~" .. path:sub(#home + 1)
end
return path
end,
---Generate <func>`color` for any component
---@param fg string @Foreground hl group
---@param gen_bg boolean @Generate guibg from hl group |StatusLine|?
---@param special_nobg boolean @Disable guibg for transparent backgrounds?
---@param bg string? @Background hl group
---@param gui string? @GUI highlight arguments
---@return nil|fun():lualine_hlgrp
gen_hl = function(fg, gen_bg, special_nobg, bg, gui)
if has_catppuccin then
return function()
local guifg = colors[fg]
local guibg = gen_bg and require("modules.utils").hl_to_rgb("StatusLine", true, colors.mantle)
or colors[bg]
local nobg = special_nobg and require("core.settings").transparent_background
return {
fg = guifg and guifg or colors.none,
bg = (guibg and not nobg) and guibg or colors.none,
gui = gui and gui or nil,
}
end
else
-- Return `nil` if the theme is user-defined
return nil
end
end,
}
local function diff_source()
local gitsigns = vim.b.gitsigns_status_dict
if gitsigns then
return {
added = gitsigns.added,
modified = gitsigns.changed,
removed = gitsigns.removed,
}
end
end
local components = {
separator = { -- use as section separators
function()
return ""
end,
padding = 0,
color = utils.gen_hl("surface1", true, true),
separator = { left = "", right = "" },
},
file_status = {
function()
local function is_new_file()
local filename = vim.fn.expand("%")
return filename ~= "" and vim.bo.buftype == "" and vim.fn.filereadable(filename) == 0
end
local symbols = {}
if vim.bo.modified then
table.insert(symbols, "[+]")
end
if vim.bo.modifiable == false then
table.insert(symbols, "[-]")
end
if vim.bo.readonly == true then
table.insert(symbols, "[RO]")
end
if is_new_file() then
table.insert(symbols, "[New]")
end
return #symbols > 0 and table.concat(symbols, "") or ""
end,
padding = { left = -1, right = 1 },
cond = conditionals.has_comp_before,
},
lsp = {
function()
local buf_ft = vim.bo.filetype
local clients = vim.lsp.get_clients({ buffer = vim.api.nvim_get_current_buf() })
local lsp_lists = {}
local available_servers = {}
if next(clients) == nil then
return icons.misc.NoActiveLsp -- No server available
end
for _, client in ipairs(clients) do
local filetypes = client.config.filetypes
local client_name = client.name
if filetypes and vim.fn.index(filetypes, buf_ft) ~= -1 then
-- Avoid adding servers that already exists.
if not lsp_lists[client_name] then
lsp_lists[client_name] = true
table.insert(available_servers, client_name)
end
end
end
return next(available_servers) == nil and icons.misc.NoActiveLsp
or string.format("%s[%s]", icons.misc.LspAvailable, table.concat(available_servers, ", "))
end,
color = utils.gen_hl("blue", true, true, nil, "bold"),
cond = conditionals.has_enough_room,
},
python_venv = {
function()
local function env_cleanup(venv)
if string.find(venv, "/") then
local final_venv = venv
for w in venv:gmatch("([^/]+)") do
final_venv = w
end
venv = final_venv
end
return venv
end
if vim.bo.filetype == "python" then
local venv = os.getenv("CONDA_DEFAULT_ENV")
if venv then
return icons.misc.PyEnv .. env_cleanup(venv)
end
venv = os.getenv("VIRTUAL_ENV")
if venv then
return icons.misc.PyEnv .. env_cleanup(venv)
end
end
return ""
end,
color = utils.gen_hl("green", true, true),
cond = conditionals.has_enough_room,
},
tabwidth = {
function()
return icons.ui.Tab .. vim.bo.tabstop
end,
padding = 1,
},
cwd = {
function()
return icons.ui.FolderWithHeart .. utils.abbreviate_path(vim.fs.normalize(vim.fn.getcwd()))
end,
color = utils.gen_hl("subtext0", true, true, nil, "bold"),
},
file_location = {
function()
local cursorline = vim.fn.line(".")
local cursorcol = vim.fn.virtcol(".")
local filelines = vim.fn.line("$")
local position
if cursorline == 1 then
position = "Top"
elseif cursorline == filelines then
position = "Bot"
else
position = string.format("%2d%%%%", math.floor(cursorline / filelines * 100))
end
return string.format("%s·%3d:%-2d", position, cursorline, cursorcol)
end,
},
}
require("modules.utils").load_plugin("lualine", {
options = {
icons_enabled = true,
theme = custom_theme(),
disabled_filetypes = { statusline = { "alpha" } },
component_separators = "",
section_separators = { left = "", right = "" },
},
sections = {
lualine_a = { "mode" },
lualine_b = {
{
"filetype",
colored = true,
icon_only = false,
icon = { align = "left" },
},
components.file_status,
vim.tbl_extend("force", components.separator, {
cond = function()
return conditionals.has_git() and conditionals.has_comp_before()
end,
}),
},
lualine_c = {
{
"branch",
icon = icons.git_nosep.Branch,
color = utils.gen_hl("subtext0", true, true, nil, "bold"),
cond = conditionals.has_git,
},
{
"diff",
symbols = {
added = icons.git.Add,
modified = icons.git.Mod_alt,
removed = icons.git.Remove,
},
source = diff_source,
colored = false,
color = utils.gen_hl("subtext0", true, true),
cond = conditionals.has_git,
padding = { right = 1 },
},
{ utils.force_centering },
{
"diagnostics",
sources = { "nvim_diagnostic" },
sections = { "error", "warn", "info", "hint" },
symbols = {
error = icons.diagnostics.Error,
warn = icons.diagnostics.Warning,
info = icons.diagnostics.Information,
hint = icons.diagnostics.Hint_alt,
},
},
components.lsp,
},
lualine_x = {
{
"encoding",
fmt = string.upper,
padding = { left = 1 },
cond = conditionals.has_enough_room,
},
{
"fileformat",
symbols = {
unix = "LF",
dos = "CRLF",
mac = "CR", -- Legacy macOS
},
padding = { left = 1 },
},
components.tabwidth,
},
lualine_y = {
components.separator,
components.python_venv,
components.cwd,
},
lualine_z = { components.file_location },
},
inactive_sections = {
lualine_a = {},
lualine_b = {},
lualine_c = { "filename" },
lualine_x = { "location" },
lualine_y = {},
lualine_z = {},
},
tabline = {},
extensions = {},
})
end