[Breaking] Refactor: switch to %{%expr%} from %!expr
Huge change to internal mechanics. - Now %{%expr%} blocks are used for evaluating statusline instead of %!expr . Pros for this is statusline is evaluated on current win and buf context instead of active win & bufs context. - Now all components branch & diff(These two are cached) including users function components updates on inactive status. - now components update status and function components receive an argument (is_focused) when called. It indicates whether it's running for active or inactive statusline. - Now lualine no longer aggrasively takes over 'statusline' option. instead it sets the global version of statusline option. So it's possible to unset it to hide lualine . Or set buffer local version of that option to have different statusline then lualine on thay buffer - Switch vim.o to vim.go or vim.opt. - BugFix autcommands being set everytime an instence of diff or branch component is created - Added new utils functions define_autocmd & is_focused - Remove utils function lualine_eval - Removed hacky require cache modification from component.lua
This commit is contained in:
parent
cb5c4c031e
commit
fac96d71cc
|
@ -5,14 +5,6 @@ local highlight = require 'lualine.highlight'
|
||||||
-- Used to provide a unique id for each component
|
-- Used to provide a unique id for each component
|
||||||
local component_no = 1
|
local component_no = 1
|
||||||
|
|
||||||
-- Here we're manupulation the require() cache so when we
|
|
||||||
-- require('lualine.component.components') it will return this table
|
|
||||||
-- It's hacky but package.loaded is documented in lua docs so from
|
|
||||||
-- standereds point of view we're good ]. I think it's better than
|
|
||||||
-- modifiying global state
|
|
||||||
package.loaded['lualine.component.components'] = {}
|
|
||||||
local components = package.loaded['lualine.component.components']
|
|
||||||
|
|
||||||
local Component = {
|
local Component = {
|
||||||
-- Creates a new component
|
-- Creates a new component
|
||||||
new = function(self, options, child)
|
new = function(self, options, child)
|
||||||
|
@ -27,7 +19,6 @@ local Component = {
|
||||||
new_component.options.component_name = tostring(component_no)
|
new_component.options.component_name = tostring(component_no)
|
||||||
end
|
end
|
||||||
new_component.component_no = component_no
|
new_component.component_no = component_no
|
||||||
components[component_no] = new_component
|
|
||||||
new_component:set_separator()
|
new_component:set_separator()
|
||||||
new_component:create_option_highlights()
|
new_component:create_option_highlights()
|
||||||
end
|
end
|
||||||
|
@ -157,22 +148,13 @@ local Component = {
|
||||||
-- luacheck: pop
|
-- luacheck: pop
|
||||||
|
|
||||||
-- Driver code of the class
|
-- Driver code of the class
|
||||||
draw = function(self, default_highlight, statusline_inactive)
|
draw = function(self, default_highlight, is_focused)
|
||||||
-- Check if we are in in inactive state and need to enable inactive_eval
|
|
||||||
-- for this compoennt
|
|
||||||
if self.inactive_eval and not statusline_inactive and vim.g.statusline_winid ~=
|
|
||||||
vim.fn.win_getid() then
|
|
||||||
-- In that case we'll return a evaluator
|
|
||||||
self.status = '%' .. string.format(
|
|
||||||
'{%%v:lua.require\'lualine.utils.utils\'.lualine_eval(%s,\'\',v:true)%%}',
|
|
||||||
tostring(self.component_no))
|
|
||||||
return self.status
|
|
||||||
end
|
|
||||||
self.status = ''
|
self.status = ''
|
||||||
|
|
||||||
if self.options.condition ~= nil and self.options.condition() ~= true then
|
if self.options.condition ~= nil and self.options.condition() ~= true then
|
||||||
return self.status
|
return self.status
|
||||||
end
|
end
|
||||||
local status = self:update_status()
|
local status = self:update_status(is_focused)
|
||||||
if self.options.format then status = self.options.format(status or '') end
|
if self.options.format then status = self.options.format(status or '') end
|
||||||
if type(status) == 'string' and #status > 0 then
|
if type(status) == 'string' and #status > 0 then
|
||||||
self.status = status
|
self.status = status
|
||||||
|
@ -181,10 +163,8 @@ local Component = {
|
||||||
self:apply_padding()
|
self:apply_padding()
|
||||||
self:apply_section_separators()
|
self:apply_section_separators()
|
||||||
self:apply_highlights(default_highlight)
|
self:apply_highlights(default_highlight)
|
||||||
if not (statusline_inactive and self.last_component) then
|
|
||||||
self:apply_separator()
|
self:apply_separator()
|
||||||
end
|
end
|
||||||
end
|
|
||||||
return self.status
|
return self.status
|
||||||
end
|
end
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,14 +1,14 @@
|
||||||
-- Copyright (c) 2020-2021 shadmansaleh
|
-- Copyright (c) 2020-2021 shadmansaleh
|
||||||
-- MIT license, see LICENSE for more details.
|
-- MIT license, see LICENSE for more details.
|
||||||
|
local utils = require('lualine.utils.utils')
|
||||||
local Branch = require('lualine.component'):new()
|
local Branch = require('lualine.component'):new()
|
||||||
|
|
||||||
-- vars
|
-- vars
|
||||||
Branch.git_branch = ''
|
Branch.git_branch = ''
|
||||||
-- os specific path separator
|
-- os specific path separator
|
||||||
Branch.sep = package.config:sub(1, 1)
|
Branch.sep = package.config:sub(1, 1)
|
||||||
-- event watcher to watch head file
|
-- event watcher to watch head file
|
||||||
Branch.file_changed = vim.loop.new_fs_event()
|
Branch.file_changed = vim.loop.new_fs_event()
|
||||||
|
local branch_cache = {} -- stores last known branch for a buffer
|
||||||
-- Initilizer
|
-- Initilizer
|
||||||
Branch.new = function(self, options, child)
|
Branch.new = function(self, options, child)
|
||||||
local new_branch = self._parent:new(options, child or Branch)
|
local new_branch = self._parent:new(options, child or Branch)
|
||||||
|
@ -18,11 +18,14 @@ Branch.new = function(self, options, child)
|
||||||
-- run watch head on load so branch is present when component is loaded
|
-- run watch head on load so branch is present when component is loaded
|
||||||
Branch.update_branch()
|
Branch.update_branch()
|
||||||
-- update branch state of BufEnter as different Buffer may be on different repos
|
-- update branch state of BufEnter as different Buffer may be on different repos
|
||||||
vim.cmd [[autocmd lualine BufEnter * lua require'lualine.components.branch'.update_branch()]]
|
utils.define_autocmd('BufEnter', "lua require'lualine.components.branch'.update_branch()")
|
||||||
return new_branch
|
return new_branch
|
||||||
end
|
end
|
||||||
|
|
||||||
Branch.update_status = function() return Branch.git_branch end
|
Branch.update_status = function(_, is_focused)
|
||||||
|
if not is_focused then return branch_cache[vim.fn.bufnr()] or '' end
|
||||||
|
return Branch.git_branch
|
||||||
|
end
|
||||||
|
|
||||||
-- returns full path to git directory for current directory
|
-- returns full path to git directory for current directory
|
||||||
function Branch.find_git_dir()
|
function Branch.find_git_dir()
|
||||||
|
@ -90,6 +93,7 @@ function Branch.update_branch()
|
||||||
-- set to '' when git dir was not found
|
-- set to '' when git dir was not found
|
||||||
Branch.git_branch = ''
|
Branch.git_branch = ''
|
||||||
end
|
end
|
||||||
|
branch_cache[vim.fn.bufnr()] = Branch.git_branch
|
||||||
end
|
end
|
||||||
|
|
||||||
return Branch
|
return Branch
|
||||||
|
|
|
@ -20,6 +20,8 @@ Diff.default_colors = {
|
||||||
modified = '#ff0038'
|
modified = '#ff0038'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
local diff_cache = {} -- Stores last known value of diff of a buffer
|
||||||
|
|
||||||
-- Initializer
|
-- Initializer
|
||||||
Diff.new = function(self, options, child)
|
Diff.new = function(self, options, child)
|
||||||
local new_instance = self._parent:new(options, child or Diff)
|
local new_instance = self._parent:new(options, child or Diff)
|
||||||
|
@ -64,22 +66,22 @@ Diff.new = function(self, options, child)
|
||||||
|
|
||||||
if type(new_instance.options.source) ~= 'function' then
|
if type(new_instance.options.source) ~= 'function' then
|
||||||
-- setup internal source
|
-- setup internal source
|
||||||
vim.cmd [[
|
utils.define_autocmd('BufEnter', "lua require'lualine.components.diff'.update_diff_args()")
|
||||||
autocmd lualine BufEnter * lua require'lualine.components.diff'.update_diff_args()
|
utils.define_autocmd('BufWritePost', "lua require'lualine.components.diff'.update_git_diff()")
|
||||||
autocmd lualine BufWritePost * lua require'lualine.components.diff'.update_git_diff()
|
|
||||||
]]
|
|
||||||
end
|
end
|
||||||
|
|
||||||
return new_instance
|
return new_instance
|
||||||
end
|
end
|
||||||
|
|
||||||
-- Function that runs everytime statusline is updated
|
-- Function that runs everytime statusline is updated
|
||||||
Diff.update_status = function(self)
|
Diff.update_status = function(self, is_focused)
|
||||||
|
local git_diff = Diff.git_diff
|
||||||
if self.options.source then
|
if self.options.source then
|
||||||
Diff.git_diff = self.options.source()
|
git_diff = self.options.source()
|
||||||
end
|
end
|
||||||
|
|
||||||
if Diff.git_diff == nil then return '' end
|
if not is_focused then git_diff = diff_cache[vim.fn.bufnr()] or {} end
|
||||||
|
if git_diff == nil then return '' end
|
||||||
|
|
||||||
local colors = {}
|
local colors = {}
|
||||||
if self.options.colored then
|
if self.options.colored then
|
||||||
|
@ -92,12 +94,12 @@ Diff.update_status = function(self)
|
||||||
local result = {}
|
local result = {}
|
||||||
-- loop though data and load available sections in result table
|
-- loop though data and load available sections in result table
|
||||||
for _, name in ipairs {'added', 'modified', 'removed'} do
|
for _, name in ipairs {'added', 'modified', 'removed'} do
|
||||||
if Diff.git_diff[name] and Diff.git_diff[name] > 0 then
|
if git_diff[name] and git_diff[name] > 0 then
|
||||||
if self.options.colored then
|
if self.options.colored then
|
||||||
table.insert(result, colors[name] .. self.options.symbols[name] ..
|
table.insert(result, colors[name] .. self.options.symbols[name] ..
|
||||||
Diff.git_diff[name])
|
git_diff[name])
|
||||||
else
|
else
|
||||||
table.insert(result, self.options.symbols[name] .. Diff.git_diff[name])
|
table.insert(result, self.options.symbols[name] .. git_diff[name])
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -180,6 +182,7 @@ function Diff.update_diff_args()
|
||||||
else
|
else
|
||||||
Diff.git_diff = {added = 0, modified = 0, removed = 0}
|
Diff.git_diff = {added = 0, modified = 0, removed = 0}
|
||||||
end
|
end
|
||||||
|
diff_cache[vim.fn.bufnr()] = Diff.git_diff
|
||||||
end
|
end
|
||||||
}
|
}
|
||||||
Diff.update_git_diff()
|
Diff.update_git_diff()
|
||||||
|
|
|
@ -2,8 +2,6 @@
|
||||||
-- MIT license, see LICENSE for more details.
|
-- MIT license, see LICENSE for more details.
|
||||||
local FileName = require('lualine.component'):new()
|
local FileName = require('lualine.component'):new()
|
||||||
|
|
||||||
FileName.inactive_eval = true
|
|
||||||
|
|
||||||
local function count(base, pattern)
|
local function count(base, pattern)
|
||||||
return select(2, string.gsub(base, pattern, ''))
|
return select(2, string.gsub(base, pattern, ''))
|
||||||
end
|
end
|
||||||
|
|
|
@ -30,7 +30,7 @@ function FileType:apply_icon()
|
||||||
if icon and self.options.colored then
|
if icon and self.options.colored then
|
||||||
local highlight_color = utils.extract_highlight_colors(
|
local highlight_color = utils.extract_highlight_colors(
|
||||||
icon_highlight_group, 'fg')
|
icon_highlight_group, 'fg')
|
||||||
local is_focused = vim.g.statusline_winid == vim.fn.win_getid()
|
local is_focused = utils.is_focused()
|
||||||
local default_highlight = highlight.format_highlight(is_focused,
|
local default_highlight = highlight.format_highlight(is_focused,
|
||||||
self.options.self
|
self.options.self
|
||||||
.section)
|
.section)
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
local FunctionComponent = require('lualine.component'):new()
|
local FunctionComponent = require('lualine.component'):new()
|
||||||
|
|
||||||
FunctionComponent.update_status = function(self)
|
FunctionComponent.update_status = function(self, is_focused)
|
||||||
-- 1st element in options table is the function provided by config
|
-- 1st element in options table is the function provided by config
|
||||||
return self.options[1]()
|
return self.options[1](is_focused)
|
||||||
end
|
end
|
||||||
|
|
||||||
return FunctionComponent
|
return FunctionComponent
|
||||||
|
|
|
@ -51,7 +51,7 @@ end
|
||||||
function M.create_highlight_groups(theme)
|
function M.create_highlight_groups(theme)
|
||||||
utils.clear_highlights()
|
utils.clear_highlights()
|
||||||
active_theme = theme
|
active_theme = theme
|
||||||
if not vim.o.termguicolors then
|
if not vim.opt.termguicolors:get() then
|
||||||
cterm_colors = require 'lualine.utils.cterm_colors'
|
cterm_colors = require 'lualine.utils.cterm_colors'
|
||||||
end
|
end
|
||||||
for mode, sections in pairs(theme) do
|
for mode, sections in pairs(theme) do
|
||||||
|
@ -154,7 +154,7 @@ function M.component_format_highlight(highlight_name)
|
||||||
if highlight_name:find('no_mode') == #highlight_name - #'no_mode' + 1 then
|
if highlight_name:find('no_mode') == #highlight_name - #'no_mode' + 1 then
|
||||||
return '%#' .. highlight_group .. '#'
|
return '%#' .. highlight_group .. '#'
|
||||||
end
|
end
|
||||||
if vim.g.statusline_winid == vim.fn.win_getid() then
|
if utils.is_focused() then
|
||||||
highlight_group = append_mode(highlight_group)
|
highlight_group = append_mode(highlight_group)
|
||||||
else
|
else
|
||||||
highlight_group = highlight_group .. '_inactive'
|
highlight_group = highlight_group .. '_inactive'
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
local highlight = require('lualine.highlight')
|
local highlight = require('lualine.highlight')
|
||||||
local loader = require('lualine.utils.loader')
|
local loader = require('lualine.utils.loader')
|
||||||
local utils_section = require('lualine.utils.section')
|
local utils_section = require('lualine.utils.section')
|
||||||
|
local utils = require('lualine.utils.utils')
|
||||||
local config_module = require('lualine.config')
|
local config_module = require('lualine.config')
|
||||||
|
|
||||||
local config = config_module.config
|
local config = config_module.config
|
||||||
|
@ -145,9 +146,8 @@ end
|
||||||
|
|
||||||
local function status_dispatch()
|
local function status_dispatch()
|
||||||
-- disable on specific filetypes
|
-- disable on specific filetypes
|
||||||
local current_ft = vim.api.nvim_buf_get_option(
|
local current_ft = vim.bo.filetype
|
||||||
vim.fn.winbufnr(vim.g.statusline_winid), 'filetype')
|
local is_focused = utils.is_focused()
|
||||||
local is_focused = vim.g.statusline_winid == vim.fn.win_getid()
|
|
||||||
for _, ft in pairs(config.options.disabled_filetypes) do
|
for _, ft in pairs(config.options.disabled_filetypes) do
|
||||||
if ft == current_ft then
|
if ft == current_ft then
|
||||||
vim.wo.statusline = ''
|
vim.wo.statusline = ''
|
||||||
|
@ -195,19 +195,17 @@ end
|
||||||
|
|
||||||
local function set_tabline()
|
local function set_tabline()
|
||||||
if next(config.tabline) ~= nil then
|
if next(config.tabline) ~= nil then
|
||||||
vim.o.tabline = '%!v:lua.require\'lualine\'.tabline()'
|
vim.go.tabline = "%{%v:lua.require'lualine'.tabline()%}"
|
||||||
vim.o.showtabline = 2
|
vim.go.showtabline = 2
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
local function set_statusline()
|
local function set_statusline()
|
||||||
if next(config.sections) ~= nil or next(config.inactive_sections) ~= nil then
|
if next(config.sections) ~= nil or next(config.inactive_sections) ~= nil then
|
||||||
vim.o.statusline = '%!v:lua.require\'lualine\'.statusline()'
|
vim.go.statusline = "%{%v:lua.require'lualine'.statusline()%}"
|
||||||
vim.api.nvim_exec([[
|
vim.cmd([[
|
||||||
autocmd lualine WinLeave,BufLeave * lua vim.wo.statusline=require'lualine'.statusline()
|
|
||||||
autocmd lualine BufWinEnter,WinEnter,BufEnter,SessionLoadPost * set statusline<
|
|
||||||
autocmd lualine VimResized * redrawstatus
|
autocmd lualine VimResized * redrawstatus
|
||||||
]], false)
|
]])
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
-- Copyright (c) 2020-2021 shadmansaleh
|
-- Copyright (c) 2020-2021 shadmansaleh
|
||||||
-- MIT license, see LICENSE for more details.
|
-- MIT license, see LICENSE for more details.
|
||||||
-- Credit: itchyny(lightline)
|
-- Credit: itchyny(lightline)
|
||||||
local background = vim.o.background
|
local background = vim.opt.background:get()
|
||||||
|
|
||||||
return require('lualine.themes.papercolor_' .. background)
|
return require('lualine.themes.papercolor_' .. background)
|
||||||
|
|
|
@ -2,6 +2,6 @@
|
||||||
-- MIT license, see LICENSE for more details.
|
-- MIT license, see LICENSE for more details.
|
||||||
-- Credit: itchyny(lightline)
|
-- Credit: itchyny(lightline)
|
||||||
-- License: MIT License
|
-- License: MIT License
|
||||||
local background = vim.o.background
|
local background = vim.opt.background:get()
|
||||||
|
|
||||||
return require('lualine.themes.solarized_' .. background)
|
return require('lualine.themes.solarized_' .. background)
|
||||||
|
|
|
@ -15,7 +15,7 @@ function M.draw_section(section, section_name, is_focused)
|
||||||
(type(component) == 'table' and not component.component_no) then
|
(type(component) == 'table' and not component.component_no) then
|
||||||
return '' -- unknown element in section. section posibly not yet loaded
|
return '' -- unknown element in section. section posibly not yet loaded
|
||||||
end
|
end
|
||||||
table.insert(status, component:draw(highlight_name))
|
table.insert(status, component:draw(highlight_name, is_focused))
|
||||||
end
|
end
|
||||||
|
|
||||||
-- Flags required for knowing when to remove component separator
|
-- Flags required for knowing when to remove component separator
|
||||||
|
@ -38,7 +38,6 @@ function M.draw_section(section, section_name, is_focused)
|
||||||
.options.section_separators[1])
|
.options.section_separators[1])
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
section[component_no].last_component = true
|
|
||||||
end
|
end
|
||||||
-- Remove component separator when color option is used in next component
|
-- Remove component separator when color option is used in next component
|
||||||
if strip_next_component then
|
if strip_next_component then
|
||||||
|
|
|
@ -56,14 +56,23 @@ function M.list_shrink(list)
|
||||||
return new_list
|
return new_list
|
||||||
end
|
end
|
||||||
|
|
||||||
-- Wvaluate a component
|
-- Check if a auto command is already defined
|
||||||
function M.lualine_eval(id, ...)
|
local function autocmd_is_defined(event, patern, command_str)
|
||||||
local ok, components = pcall(require, 'lualine.component.components')
|
return vim.api.nvim_exec(string.format("au lualine %s %s",
|
||||||
if ok and components then
|
event, patern), true):find(command_str) ~= nil
|
||||||
return components[id]:draw(...)
|
end
|
||||||
else
|
|
||||||
return ''
|
-- Define a auto command if it's not already defined
|
||||||
|
function M.define_autocmd(event, patern, cmd)
|
||||||
|
if not cmd then cmd = patern; patern = '*' end
|
||||||
|
if not autocmd_is_defined(event, patern, cmd) then
|
||||||
|
vim.cmd(string.format("autocmd lualine %s %s %s", event, patern, cmd))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- Check if statusline is on focused window or not
|
||||||
|
function M.is_focused()
|
||||||
|
return tonumber(vim.g.actual_curwin) == vim.fn.win_getid()
|
||||||
|
end
|
||||||
|
|
||||||
return M
|
return M
|
||||||
|
|
Loading…
Reference in New Issue