luastatus is a universal status bar content generator. It allows you to configure the way the data from event sources is processed and shown, with Lua.
Its main feature is that the content can be updated immediately as some event occurs, be it a change of keyboard layout, active window title, volume or a song in your favorite music player (provided that there is a plugin for it) — a thing rather uncommon for tiling window managers.
Its motto is:
No more heavy-forking, second-lagging shell-script status bar generators!
Above is i3bar with luastatus with Bitcoin price, time, volume, and keyboard layout widgets.
In short:
- plugin is a thing that decides when to call the callback function
widget.cband what to pass to it; - barlib (bar library) is a thing that decides what to with values that
widget.cbfunction returns; - there are also derived plugins, which are plugins written in Lua that use regular plugins.
ALSA volume widget:
widget = {
plugin = 'alsa',
opts = {
channel = 'PCM'
},
cb = function(t)
if t.mute then
return {full_text = '[mute]', color = '#e03838'}
else
local percent = (t.vol.cur - t.vol.min)
/ (t.vol.max - t.vol.min)
* 100
return {full_text = string.format('[%3d%%]', math.floor(0.5 + percent)),
color = '#718ba6'}
end
end,
event = function(t)
if t.button == 1 then -- left mouse button
os.execute('urxvt -e alsamixer &')
end
end
}GMail widget (uses the derived plugin imap):
--[[
-- Expects 'credentials.lua' to be present in the current directory; it may contain, e.g.,
-- return {
-- gmail = {
-- login = 'john.smith',
-- password = 'qwerty'
-- }
-- }
--]]
credentials = require 'credentials'
widget = luastatus.require_plugin('imap').widget{
host = 'imap.gmail.com',
port = 993,
mailbox = 'Inbox',
use_ssl = true,
timeout = 2 * 60,
handshake_timeout = 10,
login = credentials.gmail.login,
password = credentials.gmail.password,
error_sleep_period = 60,
cb = function(unseen)
if unseen == nil then
return nil
elseif unseen == 0 then
return {full_text = '[-]', color = '#595959'}
else
return {full_text = string.format('[%d unseen]', unseen)}
end
end,
event = [[ -- separate-state event function
local t = ... -- obtain argument of this implicit function
if t.button == 1 then -- left mouse button
os.execute('xdg-open https://gmail.com &')
end
]]
}See more examples here.
cmake . && make && sudo make install
You can specify a Lua library to build with: cmake -DWITH_LUA_LIBRARY=luajit .
You can disable building certain barlibs and plugins, e.g. cmake -DBUILD_PLUGIN_XTITLE=OFF .
You can disable building man pages: cmake -DBUILD_DOCS=OFF .
ArchLinux users can use one of the following AUR packages:
There is also the luastatus-meta meta package which installs the dependencies of all of luastatus's plugins.
It is recommended to first have a look at the luastatus' man page.
Then, read the barlib's and plugins' documentation, either via directly viewing
barlibs/<name>/README.rst and plugins/<name>/README.rst files, or via installing the man pages
and reading luastatus-barlib-<name>(7) and luastatus-plugin-<name>(7).
Barlib-specific notes on usage follow.
luastatus-i3-wrapper should be specified as the i3bar's status command in the i3 config, e.g.:
bar {
status_command cd ~/.config/luastatus && exec luastatus-i3-wrapper -B no_separators time-battery-combined.lua alsa.lua xkb.lua
See also README for i3 and examples for i3.
luastatus should simply be launched with -b dwm, e.g.:
luastatus -b dwm -B separator=' • ' alsa.lua time-battery-combined.lua
See also README for dwm and examples for dwm.
lemonbar should be launched with luastatus-lemonbar-launcher, e.g.:
luastatus-lemonbar-launcher -p -B#111111 -p -f'Droid Sans Mono for Powerline:pixelsize=12:weight=Bold' -- -Bseparator=' ' alsa.lua time-date.lua
See also README for lemonbar and examples for lemonbar.
luastatus should be launched with luastatus-stdout-wrapper; or write your own wrapper, see e.g.
the wrapper for launching dvtm with luastatus.
See also README for stdout and and examples for stdout.
- 5.1
- LuaJIT, which is currently 5.1-compatible with "some language and library extensions from Lua 5.2"
- 5.2
- 5.3
- 5.4
- 5.5
Feel free to open an issue or a pull request. You can also chat on our Gitter chat room.
See the Migration Guide.
Here, at luastatus, we take code correctness and safety very seriously. We do the following things:
- We use best practices for C programming:
- All non-trivial string processing goes through libsafe
- We mark printf-like functions with appropriate attributes in order to get warnings on illegal format string or wrong argument types
- We handle every error possible (except for cases where we can't, and don't want to, do anything about an error)
- We pay attention to integer overflows/underflows, conversion of integers to/from floating-point types, and other possible cases of undefined behavior
- We use typedef'd enum types instead of "untyped" integers to represent enum's values so that we can get warnings when a switch does not account for some value
- We use macros for (re)allocations that make it impossible to get types wrong
- We compile with
-Wall -Wextra - We have a comprehensive test suite; it contains tests for luastatus, barlibs and plugins, and also includes "torture"-style tests (a.k.a. stress tests)
which bombard luastatus with a lot of events from a plugin and a barlib simultaneously:
- It passes under valgrind [memcheck tool]
- It passes under valgrind [helgrind tool]
- It passes under UBSAN (Undefined Behaviour Sanitizer)
- It passes under ASAN (Address Sanitizer)
- It passes under LSAN (Leak Sanitizer)
- It passes under TSAN (Thread Sanitizer)
We tried to use additional compiler warnings, -fanalyzer, and external linters/static analyzers, but
these tools only gave false positives, except for PVS-Studio, which found one actual bug, but with a lot of false positives.
So we don't use any of these on a regular basis.