diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index df9f020..43762d5 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -12,6 +12,11 @@ please use lua-format before creating a pr :smile: * refer to example below to see how themes are defined * take 4 screenshots showing a different vim modes (normal, insert, visual, replace) * add your theme with screenshots attached to [THEMES.md](./THEMES.md) while maintaining alphabetical order +* If the colorscheme you're trying to add already support lightline. You can use +[lightline2lualine theme converter](https://gist.github.com/shadmansaleh/000871c9a608a012721c6acc6d7a19b9) to easily port the theme to lualine. + +**Note to colorscheme authors** : If you want to support lualine. You can put your +lualine theme at lua/lualine/themes/{your_colorscheme}.lua in you repo.
theme example diff --git a/README.md b/README.md index 8f97511..f0db0ee 100644 --- a/README.md +++ b/README.md @@ -24,6 +24,13 @@ Here is a preview of how lualine can look like. Screenshots of all available themes are listed in [THEMES.md](./THEMES.md) +For those who want to break the norms. You can create custom looks in lualine . + +**Example** : + +- [evil_lualine](https://gist.github.com/shadmansaleh/cd526bc166237a5cbd51429cc1f6291b) +![evil_lualine_image](https://user-images.githubusercontent.com/13149513/113875129-4453ba00-97d8-11eb-8f21-94a9ef565db3.png) + ## Performance compared to other plugins Unlike other statusline plugins lualine loads only defined components, nothing else. @@ -81,6 +88,28 @@ All available themes are listed in [THEMES.md](./THEMES.md) Please create a pr if you managed to port a popular theme before me, [here is how to do it](./CONTRIBUTING.md). +
+Tweeking themes + +You like a theme but would like to tweek some colors. +You can do that in your config easily. + +Example: +```lua +local custom_gruvbox = require'lualine.themes.gruvbox' + +-- Chnage the background of lualine_c section for normal mode +custom_gruvbox.normal.c.bg = '#112233' -- rgb colors are supported + +require'lualine'.setup{ + options = { theme = custom_gruvbox }, + ... +} +``` +You can checkout structure of a lualine theme [here](https://github.com/hoob3rt/lualine.nvim/blob/master/CONTRIBUTING.md#adding-a-theme) + +
+ ### Changing separators Lualine defines two kinds of seperators. One is for sections and other is for components. Default section seperators are '', '' and component separators are '', ''. They require powerline patched fonts. But you can easily change yours to something else like below @@ -170,7 +199,7 @@ sections = {lualine_a = {'FugitiveHead'}}
Using variables as lualine component -You can use variables from vim and lua globals as a lualine component +You can use variables from vim a lualine component Variables from g:, v:, t:, w:, b:, o, go:, vo:, to:, wo:, bo: scopes can be used. Scopes ending with o are options usualy accessed with `&` in vimscript @@ -180,39 +209,79 @@ sections = {lualine_a = {'g:coc_status', 'bo:filetype'}}
+
+Using lua expressions as lualine component + +You can use any valid lua expression as a component . This allows global +variables to be used as a component too. Even require statements can be used to access values returned by specific scripts. +One liner functions can be inlined by utilizeing this . + +For exmaple this will show day of the week. +And 2nd one will display current value of global variabke data. + +```lua +sections = {lualine_c = {"os.data('%a')", 'data'}} +``` + +
+
Options for components ### Available options: +Options can change the way a component behave. +There are two kinds of options some that work on every kind of component. +Even the ones you create like custom function component . And some that only +work on specific component. +Detailed list of available options are given below. + #### Global options +These options are available for all components. -Global options change behaviour of all suported components. -All of these options can also be specifically set to all supported components, full example below. - -##### Available global options -Option | Default | Behaviour | Supported components -:------: | :------: | :----------: | :-----: +Option | Default | Behaviour | Supported components +:------: | :------: | :------: | :--------: icons_enabled | true | Displays icons on components You should have nerd-fonts supported fonts to see icons properly. | branch, fileformat, filetype, location, diagnostics -padding | 1 | Adds padding to the left and right of components | all -left_padding | 1 | Adds padding to the left of components | all -right_padding | 1 | Adds padding to the right of components | all -upper | false | Changes components to be uppercase | all -lower | false | Changes components to be lowercase | all -format | nil | Takes a function . The funtion gets the result of component as argument and it's return value is displayed. So this function can parse and format the output as user wants. | all -##### Global options example +icon | Differs for each component | Displays an icon in front of the component | All +padding | 1 | Adds padding to the left and right of components | All +left_padding | 1 | Adds padding to the left of components | All +right_padding | 1 | Adds padding to the right of components | All +separator | (component_separators) | which separator to use at end of component | all +upper | false | Changes components to be uppercase | All +lower | false | Changes components to be lowercase | All +format | nil | Takes a function . The funtion gets the result of component as argument and it's return value is displayed. So this function can parse and format the output as user wants. | All +condition | nil | Takes a function. The component is loaded if the function returns true otherwise not. It can be used to load some comoonents on specific cases. | All +color | nil | Sets custom color for the component in this format

`color = {fg = '#rrggbb', bg= '#rrggbb', gui='style'}`

The fields of color table are optional and default to theme

Color option can also be a string containing highlight group name `color = "WarningMsg"`. One neat trick set the color to highlight group name then change that highlight with :hi command to change color of that component at runtime. | All + +#### Using global options +Global options can be set in two ways. One is as part of options table in setup. + ```lua -options = {icons_enabled = true} +require'lualine'.setup{ + options = { + icons_enabled = true, + padding = 2, + } +} +``` +When set this way these values work as default for all component. +These defaults can be overwritten by setting option as part of component +configuration like following. + +```lua +lualine_a = { + -- Displays only first char of mode name + {'mode', format=function(mode_name) return mode_name:sub(1,1) end}, + -- Disables icon for branch component + {'branch', icons_enabled=false}, +}, +lualine_c = { + -- Displays filename only when window is wider then 80 + {'filename', condition=function() return vim.fn.winwidth(0) > 80 end}, +} ``` #### Component specific options -As mentioned above, all global options can be applied to specific components. -However there are some options which are component-only (you cannot set them as globals) -Option | Default | Behaviour -:------: | :------: | :----: -icon | Differs for each component | Displays an icon in front of the component -color | nil | Sets custom color for the component in this format

`color = {fg = '#rrggbb', bg= '#rrggbb', gui='style'}`

The fields of color table are optional and default to theme - In addition, some components have unique options. * `diagnostics` component options @@ -245,6 +314,8 @@ color_removed | `DiffDelete` foreground color | changes diff's removed section f symbols | `{added = '+', modified = '~', removed = '-'}` | changes diff's symbols | table containing on or more symbols | +Component specific options can only be set with component configs. + ##### Component options example ```lua sections = { diff --git a/doc/lualine.txt b/doc/lualine.txt index 8271887..81a626f 100644 --- a/doc/lualine.txt +++ b/doc/lualine.txt @@ -111,6 +111,25 @@ All available themes are listed in THEMES.md (./THEMES.md) Please create a pr if you managed to port a popular theme before me, here is how to do it (./CONTRIBUTING.md). +Tweeking themes~ + +You like a theme but would like to tweek some colors. +You can do that in your config easily. + +Example: +> + local custom_gruvbox = require'lualine.themes.gruvbox' + + -- Chnage the background of lualine_c section for normal mode + custom_gruvbox.normal.c.bg = '#112233' -- rgb colors are supported + + require'lualine'.setup{ + options = { theme = custom_gruvbox }, + ... + } +< +You can checkout structure of a lualine theme [here](https://github.com/hoob3rt/lualine.nvim/blob/master/CONTRIBUTING.md#adding-a-theme) + CHANGING SEPARATOR IN SECTION *lualine_changing_separator* Lualine defines two kinds of seperators. One is for sections and other is @@ -163,7 +182,7 @@ Available components~ * fileformat (file format) * filename * filetype - * hostname + * hostname * location (location in file in line:column format) * mode (vim mode) * progress (%progress in file) @@ -193,13 +212,27 @@ You can use vim functions as a lualine component Using variables as lualine component~ -You can use variables from vim and lua globals as a lualine component -Variables from g:, v:, t:, w:, b:, o, go:, vo:, to:, wo:, bo: scopes -can be used. Scopes ending with o are options usualy accessed with `&` in vimscript +You can use variables from vim. Variables from g:, v:, t:, +w:, b:, o, go:, vo:, to:, wo:, bo: scopes can be used. +Scopes ending with o are options usualy accessed with `&` in +vimscript > sections = {lualine_a = {'g:coc_status', 'bo:filetype'}} < +Using lua expressions as lualine component~ + +You can use any valid lua expression as a component . This +allows global variables to be used as a component too. Even +require statements can be used to access values returned by +specific scripts. One liner functions can be inlined by +utilizeing this . + +For exmaple this will show day of the week. And 2nd one +will display current value of global variabke data. +> + sections = {lualine_c = {"os.data('%a')", 'data'}} +< -------------------------------------------------------------------------------- CUSTOM OPTIONS FOR COMPONENTS *lualine_custom_options* @@ -208,11 +241,17 @@ CUSTOM OPTIONS FOR COMPONENTS *lualine_custom_options* Options for components~ ====================== -Global options~ ----------------------- +Available options:~ -Global options change behaviour of all suported components. -All of these options can also be specifically set to all supported components. +Options can change the way a component behave. +There are two kinds of options some that work on every kind of component. +Even the ones you create like custom function component . And some that only +work on specific component. +Detailed list of available options are given below. + +Global options~ + +These options are available for all components. option (default_value) ------ --------------- @@ -222,6 +261,10 @@ option (default_value) You should have nerd-fonts supported fonts to see icons properly. Supported components: branch, fileformat, filetype, location, diagnostics + • icon (depends on component) + displays an icon infront of a component + Supported components: all + • padding (1) spaces on left and right Supported components: all @@ -234,6 +277,10 @@ option (default_value) spaces on right Supported components: all + • separator (component_separators) + which separator to use at end of component + Supported components: all + • upper (false) Displayed in upper case Supported components: all @@ -263,12 +310,53 @@ option (default_value) • icon (differs for each component) displays an icon infront of a component - • color (nil) + • condition (nil) + Takes a function. The component is loaded if the function + returns true otherwise not. It can be used to load some + comoonents on specific cases. + + • color (Theme colors) color option can be used to set custom color to a component Color format: `lua color = {fg = '#rrggbb', bg= '#rrggbb', gui='style'}` the members of color table are optional and default to theme + Color option can also be a string containing highlight group name > + color = "WarningMsg"` +< One neat trick set the color to highlight group name then change + that highlight with :hi command to change color of that component + at runtime. +Using global options~ + +Global options can be set in two ways. One is as part of options table in setup. + +> + require'lualine'.setup{ + options = { + icons_enabled = true, + padding = 2, + } + } +< +When set this way these values work as default for all component. +These defaults can be overwritten by setting option as part of component +configuration like following. + +> + lualine_a = { + -- Displays only first char of mode name + {'mode', format=function(mode_name) return mode_name:sub(1,1) end}, + -- Disables icon for branch component + {'branch', icons_enabled=false}, + }, + lualine_c = { + -- Displays filename only when window is wider then 80 + {'filename', condition=function() return vim.fn.winwidth(0) > 80 end}, + } +< + + +Component specific options~ In addition, some components have unique options. @@ -347,25 +435,26 @@ In addition, some components have unique options. changes diff's symbols Color in `#rrggbb` format < +Component specific options can only be set with component configs. Example:~ > sections = { lualine_b = { - {'branch', icon = '', upper = true, color = {fg = '#00aa22'}}, { - 'filename', - full_name = true, - shorten = true, - format = function(name) - -- Capitalize first charecter of filename to capital. - local path, fname = name:match('(.*/)(.*)') - if not path then - path = ''; - fname = name - end - return path .. fname:sub(1, 1):upper() .. fname:sub(2, #fname) - end - } + {'branch', icon = '', upper = true, color = {fg = '#00aa22'}}, { + 'filename', + full_name = true, + shorten = true, + format = function(name) + -- Capitalize first charecter of filename to capital. + local path, fname = name:match('(.*/)(.*)') + if not path then + path = ''; + fname = name + end + return path .. fname:sub(1, 1):upper() .. fname:sub(2, #fname) + end + } } } ------------------------------------------------------------------------------- @@ -426,29 +515,29 @@ Lua config example requires = {'kyazdani42/nvim-web-devicons', opt = true}, config = function() require('lualine').setup{ - options = { - theme = 'gruvbox', - section_separators = {'', ''}, - component_separators = {'', ''}, - icons_enabled = true, - }, - sections = { - lualine_a = { {'mode', upper = true} }, - lualine_b = { {'branch', icon = ''} }, - lualine_c = { {'filename', file_status = true} }, - lualine_x = { 'encoding', 'fileformat', 'filetype' }, - lualine_y = { 'progress' }, - lualine_z = { 'location' }, - }, - inactive_sections = { - lualine_a = { }, - lualine_b = { }, - lualine_c = { 'filename' }, - lualine_x = { 'location' }, - lualine_y = { }, - lualine_z = { } - }, - extensions = { 'fzf' } + options = { + theme = 'gruvbox', + section_separators = {'', ''}, + component_separators = {'', ''}, + icons_enabled = true, + }, + sections = { + lualine_a = { {'mode', upper = true} }, + lualine_b = { {'branch', icon = ''} }, + lualine_c = { {'filename', file_status = true} }, + lualine_x = { 'encoding', 'fileformat', 'filetype' }, + lualine_y = { 'progress' }, + lualine_z = { 'location' }, + }, + inactive_sections = { + lualine_a = { }, + lualine_b = { }, + lualine_c = { 'filename' }, + lualine_x = { 'location' }, + lualine_y = { }, + lualine_z = { } + }, + extensions = { 'fzf' } } end } @@ -457,31 +546,31 @@ Lua config example Vimscript config example > let g:lualine = { - \'options' : { - \ 'theme' : 'gruvbox', - \ 'section_separators' : ['', ''], - \ 'component_separators' : ['', ''], - \ 'icons_enabled' : v:true, - \}, - \'sections' : { - \ 'lualine_a' : [ ['mode', {'upper': v:true,},], ], - \ 'lualine_b' : [ ['branch', {'icon': '',}, ], ], - \ 'lualine_c' : [ ['filename', {'file_status': v:true,},], ], - \ 'lualine_x' : [ 'encoding', 'fileformat', 'filetype' ], - \ 'lualine_y' : [ 'progress' ], - \ 'lualine_z' : [ 'location' ], - \}, - \'inactive_sections' : { - \ 'lualine_a' : [ ], - \ 'lualine_b' : [ ], - \ 'lualine_c' : [ 'filename' ], - \ 'lualine_x' : [ 'location' ], - \ 'lualine_y' : [ ], - \ 'lualine_z' : [ ], - \}, - \'extensions' : [ 'fzf' ], - \} + \'options' : { + \ 'theme' : 'gruvbox', + \ 'section_separators' : ['', ''], + \ 'component_separators' : ['', ''], + \ 'icons_enabled' : v:true, + \}, + \'sections' : { + \ 'lualine_a' : [ ['mode', {'upper': v:true,},], ], + \ 'lualine_b' : [ ['branch', {'icon': '',}, ], ], + \ 'lualine_c' : [ ['filename', {'file_status': v:true,},], ], + \ 'lualine_x' : [ 'encoding', 'fileformat', 'filetype' ], + \ 'lualine_y' : [ 'progress' ], + \ 'lualine_z' : [ 'location' ], + \}, + \'inactive_sections' : { + \ 'lualine_a' : [ ], + \ 'lualine_b' : [ ], + \ 'lualine_c' : [ 'filename' ], + \ 'lualine_x' : [ 'location' ], + \ 'lualine_y' : [ ], + \ 'lualine_z' : [ ], + \}, + \'extensions' : [ 'fzf' ], + \} lua require("lualine").setup() < ------------------------------------------------------------------------------- -vim:tw=80:sw=4:ts=8:noet:ft=help:norl:noet: +vim:tw=80:sw=4:ts=8:noet:ft=help:norl:et: diff --git a/doc/tags b/doc/tags index b37c93a..b852ebf 100644 --- a/doc/tags +++ b/doc/tags @@ -14,7 +14,7 @@ lualine_loading_plugin_extensions lualine.txt /*lualine_loading_plugin_extension lualine_lualine.nvim lualine.txt /*lualine_lualine.nvim* lualine_nvim lualine.txt /*lualine_nvim* lualine_packer.nvim lualine.txt /*lualine_packer.nvim* -lualine_performance_comparism lualine.txt /*lualine_performance_comparism* +lualine_performance_comparison lualine.txt /*lualine_performance_comparison* lualine_screenshots lualine.txt /*lualine_screenshots* lualine_setting_theme lualine.txt /*lualine_setting_theme* lualine_starting_lualine lualine.txt /*lualine_starting_lualine* diff --git a/lua/lualine/component.lua b/lua/lualine/component.lua index 4ea5b54..47c236c 100644 --- a/lua/lualine/component.lua +++ b/lua/lualine/component.lua @@ -37,11 +37,13 @@ local Component = { create_option_highlights = function(self) -- set custom highlights - if self.options.color then + if type(self.options.color) == 'table' then self.options.color_highlight = highlight.create_component_highlight_group( self.options.color, self.options.component_name, self.options) + elseif type(self.options.color) == 'string' then + self.options.color_highlight_link = self.options.color end end, @@ -80,6 +82,8 @@ local Component = { if self.options.color_highlight then self.status = highlight.component_format_highlight( self.options.color_highlight) .. self.status + elseif self.options.color_highlight_link then + self.status = '%#' .. self.options.color_highlight_link ..'#'.. self.status end self.status = self.status .. default_highlight end, @@ -118,6 +122,9 @@ local Component = { -- Driver code of the class draw = function(self, default_highlight) self.status = '' + if self.options.condition ~= nil and self.options.condition() ~= true then + return self.status + end local status = self:update_status() if self.options.format then status = self.options.format(status or '') end if type(status) == 'string' and #status > 0 then diff --git a/lua/lualine/components/special/eval_func_component.lua b/lua/lualine/components/special/eval_func_component.lua index 93e1234..0cae2c4 100644 --- a/lua/lualine/components/special/eval_func_component.lua +++ b/lua/lualine/components/special/eval_func_component.lua @@ -2,22 +2,13 @@ local EvalFuncComponent = require('lualine.component'):new() EvalFuncComponent.update_status = function(self) local component = self.options[1] - local ok, status = EvalFuncComponent.evallua(component) + local ok, status = pcall(EvalFuncComponent.eval_lua, component) if not ok then status = EvalFuncComponent.vim_function(component) end return status end -EvalFuncComponent.evallua = function(code) - if loadstring(string.format('return %s ~= nil', code)) and - loadstring(string.format([[return %s ~= nil]], code))() then - -- lua veriable component - return true, loadstring(string.format( - [[ - local ok, return_val = pcall(tostring, %s) - if ok then return return_val end - return '']], code))() - end - return false, '' +EvalFuncComponent.eval_lua = function(code) + return tostring(loadstring('return '..code)()) end EvalFuncComponent.vim_function = function(name) diff --git a/lua/lualine/highlight.lua b/lua/lualine/highlight.lua index 80f5290..9ae4982 100644 --- a/lua/lualine/highlight.lua +++ b/lua/lualine/highlight.lua @@ -5,16 +5,21 @@ local utils_colors = require 'lualine.utils.cterm_colors' local utils = require 'lualine.utils.utils' local section_highlight_map = {x = 'c', y = 'b', z = 'a'} local active_theme = nil +local cterm_colors = false function M.highlight(name, foreground, background, gui, reload) local command = {'highlight', name} if foreground and foreground ~= 'none' then - table.insert(command, 'ctermfg=' .. utils_colors.get_cterm_color(foreground)) table.insert(command, 'guifg=' .. foreground) + if cterm_colors then + table.insert(command, 'ctermfg=' .. utils_colors.get_cterm_color(foreground)) + end end if background and background ~= 'none' then - table.insert(command, 'ctermbg=' .. utils_colors.get_cterm_color(background)) table.insert(command, 'guibg=' .. background) + if cterm_colors then + table.insert(command, 'ctermbg=' .. utils_colors.get_cterm_color(background)) + end end if gui then table.insert(command, 'cterm=' .. gui) @@ -29,6 +34,7 @@ end function M.create_highlight_groups(theme) utils.clear_highlights() active_theme = theme + cterm_colors = not vim.o.termguicolors for mode, sections in pairs(theme) do for section, colorscheme in pairs(sections) do local highlight_group_name = {'lualine', section, mode} diff --git a/lua/lualine/init.lua b/lua/lualine/init.lua index 13d30b1..d60df74 100644 --- a/lua/lualine/init.lua +++ b/lua/lualine/init.lua @@ -251,19 +251,17 @@ end local function set_tabline() if next(config.tabline) ~= nil then - _G.lualine_tabline = tabline - vim.o.tabline = '%!v:lua.lualine_tabline()' + vim.o.tabline = "%!v:lua.require'lualine'.tabline()" vim.o.showtabline = 2 end end local function set_statusline() if next(config.sections) ~= nil or next(config.inactive_sections) ~= nil then - _G.lualine_statusline = status_dispatch - vim.o.statusline = '%!v:lua.lualine_statusline()' + vim.o.statusline = "%!v:lua.require'lualine'.statusline()" vim.api.nvim_exec([[ - autocmd lualine WinLeave,BufLeave * lua vim.wo.statusline=lualine_statusline() - autocmd lualine WinEnter,BufEnter * setlocal statusline=%!v:lua.lualine_statusline() + autocmd lualine WinLeave,BufLeave * lua vim.wo.statusline=require'lualine'.statusline() + autocmd lualine WinEnter,BufEnter * set statusline< ]], false) end end @@ -279,4 +277,8 @@ local function setup(user_config) set_tabline() end -return {setup = setup} +return { + setup = setup, + statusline = status_dispatch, + tabline = tabline, +}