A lightweight yet feature-rich status bar for i3bar or swaybar.
It is written completely in C/C++ to make it as lightweight as possible and specifically, to avoid creating new processes every second as in bash script.
It uses libraries like libasound and glibc function getifaddrs to retrieve volume information as opposed to using amixer and ip addr.
For battery, backlight, load, and meminfo, it reads directly from /sys/class/power_supply,
/sys/class/backlight, /proc/loadavg and /proc/meminfo.
libasound.so.2libjson-c.so.5(also used by sway and swaybar)libsensors.so.5
Install clang (must have lto support), lld, make and pkg-config, then run
git clone --recurse-submodules https://github.com/NobodyXu/swaystatus
cd swaystatus/src
make -j $(nproc)
You can customize ou build via environment variable:
BUILD_DIR: affects where the built object will be put. Default is..TARGET_DIR: where the executable will be installed whenmake installis executed. Default is/usr/local/binPYTHON: whether to include embeded python interpreter support inswaystatus, can betrueorfalse. Default istrue.DEBUG: whether to have a debug build or release build.truefor debug build andfalsefor release build. Default isfalse.EXCEPTION: whether to enable C++ exception.falseto disable C++ exception.
To install, run sudo make install, which by default will install a single binary swaystatus to /usr/local/bin.
swaystatus: Usage: swaystatus [options] configuration_filename
--help Show help message and exit
--interval=unsigned_msec Specify update interval in milliseconds, must be an unsigner integer.
By default, the interval is set to 1000 ms.
To reload swaystatus, send SIGUSR1 to swaystatus process.
{
"order": ["network_interface", "time"],
"_comment": "element order specify the order of which blocks will appear.",
"_comment2": "If a block is not specified in order, it will not appear.",
"name": {
"format": "Hello, {variable_name}",
"short_format": "hello",
"update_interval": 20,
"color": "##RRGGBBA",
"background: "##RRGGBBA",
"border": "##RRGGBBA",
"border_top": 1,
"border_bottom": 1,
"border_left": 1,
"border_right": 1,
"min_width": 1,
"align": "center",
"separator": true,
"separator_block_width": 9,
"markup": "none",
"click_event_handler": {
"type": "python",
"module_name": "hello",
"function_name": "handler"
}
},
"_comment": "Any variable starts with '_' is a comment"
}
All property present for "name" above are optional.
For volume, you can also set property "mix_name" and "card".
The following values are valid name:
-
brightness
-
volume
-
battery
The configuration block of battery support
excluded_modelto exclude certain battery devices from the output ofswaystatus. -
network_interface
-
load
-
memory_usage
-
time
-
sensors
Any unrecognized parameters will be ignored.
It is used internally to generate the "full_text" that will be passed to swaybar.
Formatting for blocks other than time is done using fmt - Format String Syntax.
Formatting for block time is parsed by strftime.
In the format string, user is capable of taking advantage of format variables to customize the output.
It is used to generate "short_text", which is used by swaybar when it decided that the
"full_text" is too long.
TO enable click event handling for a block, add json object "click_event_handler" to the block that block.
The return value of it can be ored from the following values:
0do nothing1force the module to update2force the module to reload
Currently, the handler can be written in python or C/C++.
For loading python handler, add "type": "python" to your "click_event_handler", then specify
the "module_name" and "function_name" of the handler.
swaystatus will attempt to load the module from the same directory of your configuration file,
your current working dir, any path you specified with environment variable PYTHONPATH and your
system module paths.
If instead you want to embed the python code into your configuration file, add "code" to your "click_event_handler" and assign your code as value to it.
The python function is expected to have signature (Check here for more information):
(instance: str, click_pos: Tuple[int, int], button: int, event: int, relative_click_pos: Tuple[int, int], blocksize: Tuple[int, int]) -> int
Your function is expected to return 0 and any exception thrown in your function must be handled,
otherwise swaystatus will print that error and exit.
You C/C++ code has to be compiled with -fPIC -shared.
For loading python handler, add "type": "dynlib" to your "click_event_handler", then specify
the "module_name" and "function_name" of the handler.
Just like loading python, swaystatus will attemp to load the shared library from the same
directory of your configuration file, your current working dir.
It is loaded using dlopen, so LD_LIBRARY_PATH, /etc/ld.so.cache, /lib and /usr/lib is
also searched.
You can also specify the path instead of a name directly in the module_name, which is perfectly
valid.
The C/C++ function is expected to be exported in "C" and have signature:
#include <stdint.h>
struct Pos {
uint64_t x;
uint64_t y;
};
typedef struct Pos ClickPos;
typedef struct Pos BlockSize;
int f(
const char *instance,
const ClickPos *pos,
uint64_t button,
uint64_t event,
const ClickPos *relative_pos,
const BlockSize *size
)Your function is expected to return 0.
If you want to disable a certain feature, say brightness, then add the following to your configuration:
{
"brightness": false,
}
Or if you are using element "order" for specifing block order, then you can simply remove the name from "order".
Note that {"brightness": false} overrides "order":
If block specified in "order" is disabled by setting it to false, then the block
will not appear.
Using this block, you can import a python/c module and display whatever you want in this block.
You need to provide update_callback and do_print_callback, which need to have the
same fields as click event handler type, module_name, function_name,
(optional code for python).
Check example-config.json for example configuration of this
block.
If specified, then the block will update at update_interval * main_loop_interval ms,
where main_loop_interval is the value passed by cmdline arg --interval= or 1000 ms
by default.
The sensors on computer are so many that they cannot be fitted into one line, so swaystatus
instead, print one sensor each time and once update_interval is reached, next sensor is shown
at the swaybar.
When all sensors are shown, swaystatus will then update the sensors reading from the computer.
-
has_battery: check whether battery device exists -
per_battery_fmt_str, which is used to print every battery on this system.It contains the following variables:
namepresenttechnologymodel_namemanufacturerserial_numberstatuscycle_countvoltage_min_designvoltage_nowcharge_full_designcharge_fullcharge_nowcapacitycapacity_levelis_charging(Check section "Conditional Variable" for usage)is_dischargingis_not_chargingis_full
MemTotalMemFreeMemAvailableBuffersCachedSwapCachedActiveInactiveMlockedSwapTotalSwapFreeDirtyWritebackAnonPagesMappedShmem
The unit (supports 'BKMGTPEZY') of the variables printed can be specified.
For example, '{MemTotal:K}' will print MemTotal in KiloBytes.
volume
loadavg_1mloadavg_5mloadavg_15mrunning_kthreads_cnttotal_kthreads_cntlast_created_process_pid
NOTE that these variables are evaluated per backlight_device.
backlight_devicebrightnessmax_brightnesshas_multiple_backlight_devices(this is a Conditional Variable)
-
is_connected -
is_not_connected -
per_interface_fmt_str: The specification for this variable will be formatted once for each interface.It contains subvariables that can be used inside:
HAS_UAPI_DEF_IF_NET_DEVICE_FLAGS_LOWER_UP_DORMANT_ECHOhas_broadcast_supportis_pointopointhas_no_arp_supportis_in_promisc_modeis_in_notrailers_modeis_masteris_slavehas_multicast_supporthas_portsel_supportis_automedia_activeis_dhcprx_packetstx_packetsrx_bytes(Supports unit specification, checks Memry Usage Variables for more info)tx_bytes(Supports unit specification, checks Memry Usage Variables for more info)rx_errorstx_errorsrx_droppedtx_droppedmulticastcollisionsrx_length_errorsrx_over_errorsrx_crc_errorsrx_frame_errorsrx_fifo_errorsrx_missed_errorstx_aborted_errorstx_carrier_errorstx_fifo_errorstx_heartbeat_errorstx_window_errorsrx_compressedtx_compressedipv4_addrsipv6_addrs
Limit of number of ip address can be done via
{ipv4_addrs:1}and{ipv6_addrs:1}Optionally if
HAS_UAPI_DEF_IF_NET_DEVICE_FLAGS_LOWER_UP_DORMANT_ECHO, the following variables are also defined:is_lower_upis_dormantis_echo_device
To limit number of ip addresses in output, please use {ipv4_config:1}.
prefix: the name of the devicepath: the path to the device in/sysaddr: the internal address of the device inlibsensorsbus_type: the type of devicebus_nr: unclearreading_number: the internal index for the specific sensor readingreading_temp: the temperature reading from the sensor
Conditional variables are used to conditionally evaulate part of the format string.
For example, setting "format" in "battery" to "{is_charging:Charging}" will print "Charging" only when the battery is charging.
All variables start with "is" and "has" are conditional variables.
In additional to printing strings conditionally, conditional variables can also be used to print other variables conditionally.
For example, "{is_charging:{level}%}" will print "98%" when charging, where "98" is the actual level of battery.
Check example-config.json for the example configuration.
bar {
status_command swaystatus
}
