Skip to content
noturbobPublic

About

A bar that isn't there until you ask for it. Keyboard-summoned status bar for niri & Wayland: windows glide aside, every panel is one key away, and one config file restyles it live. Vala + GTK4.

Topics

Resources

Stars

0 stars

Watchers

0 watching

Forks

Latest commit

 

History

49 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

flowbar: Super+/ slides a full-width bar down while the windows slide down to make room; c, v and s open the calendar, volume and system panels under their chips; saving config.ini restyles the bar live through four themes; Esc sends it away.

flowbar

A bar that isn't there, until you ask for it.

Your windows get the whole screen. Press Super + / and a bar slides down from the top,
your windows step down to make room, and every panel is a single key away.
Press it again and the screen is yours.

niri Wayland Vala

Install · Keys · Configure · Themes · Custom modules · How it works · Hacking


Why

Most bars rent a strip of your screen forever to show you the time. flowbar only shows up when you want something, and it's built to be driven without the mouse.

  • Out of the way. Hidden, it takes no pixels and polls nothing.
  • One key, then one letter. Super+/ to summon, a letter for each panel, Esc to back out.
  • Moves like niri. The bar slides down on niri's own spring and back up the same way when it leaves, and your windows step down to make room.
  • One file. Theme, layout, keys, icons and commands all live in one config.ini, and saving it restyles the open bar on the spot.
  • Mouse welcome. Every chip, row and toggle is clickable too, and clicking outside closes it.
  • Made to be riced. Six themes, every color overridable, CSS variables for your own stylesheet, and any shell command can become a module.

Install

flowbar targets Arch Linux with niri. Any Wayland compositor with layer-shell should work, but niri is where it's at home.

sudo pacman -S --needed vala gtk4 gtk4-layer-shell json-glib wayland wayland-protocols
git clone https://github.com/noturbob/Flowbar && cd Flowbar
make install

That puts flowbar in ~/.local/bin and an annotated config.ini in ~/.config/flowbar/ (it never overwrites one you already have).

Then add two lines to ~/.config/niri/config.kdl:

spawn-at-startup "flowbar" "--daemon"

binds {
    Mod+Slash hotkey-overlay-title="Toggle flowbar" { spawn "flowbar"; }
}

--daemon starts flowbar hidden at login and warms up its renderer, so the very first summon is instant. Every later flowbar just tells the running one to show or hide.

Peek on media keys

flowbar --peek <module> flashes just that module in a small pill at the top, with its level, then lets it fade. Hold a key and it stays up. Chain it after the command your media keys already run:

XF86AudioRaiseVolume  allow-when-locked=true { spawn-sh "wpctl set-volume @DEFAULT_AUDIO_SINK@ 0.1+ && flowbar --peek volume"; }
XF86AudioLowerVolume  allow-when-locked=true { spawn-sh "wpctl set-volume @DEFAULT_AUDIO_SINK@ 0.1- && flowbar --peek volume"; }
XF86AudioMute         allow-when-locked=true { spawn-sh "wpctl set-mute @DEFAULT_AUDIO_SINK@ toggle && flowbar --peek volume"; }
XF86MonBrightnessUp   allow-when-locked=true { spawn-sh "brightnessctl --class=backlight set +10% && flowbar --peek display"; }
XF86MonBrightnessDown allow-when-locked=true { spawn-sh "brightnessctl --class=backlight set 10%- && flowbar --peek display"; }

Any module can be peeked. If the bar is already open, the chip itself updates instead.

Straight to a panel

flowbar --open <module> summons the bar with that panel already open. It makes the launcher a drop-in for your app launcher bind:

Mod+D hotkey-overlay-title="Launch an app" { spawn "flowbar" "--open" "launcher"; }
Tools flowbar talks to
Module Uses
workspaces niri msg (niri's IPC)
wifi nmcli (NetworkManager)
bluetooth bluetoothctl (bluez-utils)
volume wpctl, pactl (PipeWire)
display brightnessctl
media playerctl
clipboard wl-paste, wl-copy (wl-clipboard)
screenshot niri's built-in screenshot actions
notifications makoctl (mako)
night wlsunset (optional), makoctl
updates checkupdates (pacman-contrib), yay or paru for the AUR
power swaylock, systemctl, niri msg

Commands that need a terminal (Wi‑Fi passwords, upgrades) open in whatever [commands] terminal says, kitty -e by default.


Keys

Summon with Super+/. Every chip on the bar shows its key: press it to drop that module's panel down right under the chip. Esc closes the panel (so does the same key again, in most panels), and Esc once more sends the whole bar away. Arrow keys work anywhere hjkl do.

Key Module Inside the panel
left
o workspaces every window by workspace · j/k + Enter focus · 1–9 go to workspace
t time clock, date, week, uptime
c calendar h/l day · j/k week · H/L month · g today
m media space play/pause · h/l previous/next
center
␣ launcher type to search apps · ↑/↓ pick · Enter launch
y clipboard j/k pick · Enter copy · x delete · X clear
g screenshot a area · s screen · w window · o open folder
a notifications cards with icon, title and body: on screen, then history (dimmed) · Enter act · x remove (history too) · X clear all · r bring back last · f do not disturb
n night n night light · f do not disturb
u updates Enter upgrade · r check now
right
w wifi j/k pick · Enter connect or disconnect · space radio · r rescan
b bluetooth j/k pick · Enter connect or disconnect · space power
v volume h/l −/+ · m mute · j/k + Enter default device · i inputs/outputs
d display h/l brightness −/+
s system CPU, memory, temperature, battery
p power l lock · s suspend · e log out · r reboot · o power off, each pressed twice

With a mouse

Everything also works by pointer. Click a chip to open its panel (click it again to close), click any row to act on it, and click a toggle (Wi‑Fi, Bluetooth, mute, night light, do not disturb, play/pause) to flip it. Click along the volume or brightness meter to jump to that level, or scroll on their chips. Scroll on the workspaces chip to move between workspaces. Clicking anywhere outside the bar closes it. Power actions still take two clicks. Set [bar] mouse = false for keyboard only.

An open panel gets first pick of the keyboard, so letters can mean something local there (s is suspend inside power, not system). The launcher takes that furthest: while it's open, everything you type goes into the search.


Configure

Everything lives in ~/.config/flowbar/config.ini. flowbar watches it: save, and the bar rebuilds itself in place, even while it's open. Every setting has a default, so any line (or the whole file) is optional. The file make install gives you documents every option; the highlights:

[theme]
preset = azure            # azure · catppuccin · tokyo-night · gruvbox · nord · rose-pine
accent = #00A2E8          # override any single color of the preset
font = CommitMono Nerd Font
radius = 22

[bar]
left   = workspaces time calendar media
center = launcher clipboard screenshot notifications night updates
right  = wifi bluetooth volume display system power
margin = auto             # niri's layout `gaps`: the bar sits as far from the edges as your windows do
mouse = true              # clicks and scrolling; false for keyboard only
height = 24               # the size of a stock waybar

[motion]
speed = auto              # scales every animation; auto follows niri's `slowdown`, 0 turns it off

[keys]
power = q                 # rebind any module: a letter, or a key name like F1

[icons]
wifi = 󰖩                  # swap any chip's icon

[commands]
terminal = foot           # anything that runs a command: kitty -e · alacritty -e · wezterm start --
update = paru
lock = hyprlock

Module settings sit in their own sections: [volume] step, [display] step, [night] temperature, [clipboard] keep, [updates] interval, [screenshot] dir.

Mistakes don't fail silently. Run make run (or flowbar from a terminal) and bad config or CSS is reported with the file and line.


Themes

Six presets ship in the box. Each is one line: preset = <name>.

azure · the default azure theme
catppuccin catppuccin theme
tokyo-night tokyo-night theme
gruvbox gruvbox theme
nord nord theme
rose-pine rose-pine theme

Any preset color can be overridden in [theme]: accent, accent-2 (the active chip, today in the calendar), background, foreground, good ("on" states). Plus opacity, font, font-size and radius. On compositors with the ext-background-effect protocol (niri 26.04+), what shows through the bar and its panels is blurred.

Going further with style.css

For anything past colors, drop a style.css next to your config. It's GTK CSS, layered over flowbar's own, reloaded on save, and it can use the same variables the built-in theme uses:

/* square, flat, loud */
.bar, .card  { border-radius: 0; box-shadow: none; }
.chip.active { background: var(--accent); }
.chip.active .icon, .chip.active label { color: var(--background); }
Variables
colors --accent --accent-2 --background --foreground --good
shape --opacity --radius --bar-height --gap --font --font-size
motion --t-drop --t-fade --t-chip --t-leave --t-quick (already scaled by [motion] speed)
Classes
.flow the root; .flow.hidden while it's away
.peek · .osd the --peek window and its pill
.bar · .chip · .chip.active the bar and its chips
.key · .icon a chip's key badge and icon
.card the panel under a chip
.row · .row.cursor list rows and the selected one
.big · .sub · .dim · .status · .accent panel text

Custom modules

Any shell command can become a module, no code needed. Define it, then list its name in a [bar] line:

[bar]
right = weather wifi bluetooth volume display system power

[custom.weather]
key = e
icon = 
title = Weather
exec = curl -s 'wttr.in/?format=%c+%t'
interval = 900              # seconds between runs while the bar is up
on-enter = xdg-open https://wttr.in

[custom.vpn]
key = x
icon = 󰖂
exec = nmcli -t -f TYPE connection show --active | grep -q vpn && echo on || echo off
on-enter = nmcli connection up id my-vpn
close-on-enter = false      # keep the bar open after Enter

The chip shows the first line of the command's output and the panel shows all of it. Enter runs on-enter.


How it works

A few details, for the curious:

  • A layer-shell overlay. flowbar is a GTK 4 window on the overlay layer, anchored to the top and both sides. While it's up it takes the keyboard, so a single letter can mean something.
  • Windows that make room. When the bar appears it reserves a strip at the top edge, and niri moves your windows out of it. The strip is claimed in one step the moment you press the key, not grown with the bar: every change to it resizes every window, and apps re-flow their text a beat after the last resize, so a strip that grew frame by frame left terminals visibly settling after the bar had landed. In one step they finish re-flowing while the bar is still sliding in on niri's default spring.
  • Your spacing, not ours. The gap around the bar comes from niri's own gaps, so it lines up exactly with your window edges.
  • One instance. flowbar is a single-instance GTK application: running flowbar again just toggles the one that's already there, which is why a bind can be a plain spawn "flowbar".
  • Text that fits. A chip is at most fourteen characters wide. A longer window title, song or clipboard entry scrolls to show its end and back, and only while the bar is on screen.
  • Quiet when hidden. Modules only poll while the bar is on screen, and slow checks (package updates) are cached.
  • Clipboard without a daemon. History comes from wl-paste --watch and stays in memory. Copies a password manager marks as sensitive are never recorded.

Hacking

flowbar is written in Vala, which compiles to C against GTK 4: a small native binary, GObject underneath, and GTK's CSS engine doing the animation.

make run      # build, stop any running flowbar, run in the foreground with warnings visible
File What's in it
src/flowbar.vala the app: window, summon and dismiss, keys, panel placement, the Module base class and helpers
src/config.vala config.ini reading, theme presets, the CSS variables
src/style.vala the stylesheet
src/custom.vala [custom.NAME] modules
src/<module>.vala one file per built-in module
config.ini the annotated default config

A module is a chip plus a panel. Here's a complete one:

using Gtk;

class Uptime : Module {
    Label since = label ("", "sub");

    public Uptime () {
        base ("z", "");          // its key and icon
        every = 30;                    // refresh every 30 seconds while the bar is up
        panel.append (label ("Uptime", "status"));
        panel.append (since);
    }

    public override async void refresh () {
        value.label = yield sh ("uptime -p");   // the chip's text
        since.label = yield sh ("uptime -s");
    }

    public override bool on_key (string k) {   // keys while its panel is open
        if (k != "Return") return false;
        in_terminal ("btop");
        return true;
    }
}

Register it by name in make_module () in src/flowbar.vala, and it can be placed from [bar] like any other. Helpers to build with: sh () runs a command and returns its output, launch () fires one off, in_terminal () runs one in the user's terminal, act () runs a command and then refreshes, dismiss () hides the bar, Picker is a keyboard-driven list, key_row () makes a key-menu row, and Config.str / num / flag () read settings.


Troubleshooting

  • Nothing happens on Super+/. Check that ~/.local/bin is on niri's PATH, or bind the full path.
  • Night light does nothing. It needs wlsunset (sudo pacman -S wlsunset). The panel tells you when it's missing.
  • Do not disturb does nothing. mako needs the mode defined. Add this to ~/.config/mako/config:
    [mode=do-not-disturb]
    invisible=1
  • A theme change didn't apply. Run make run and look for a line number: flowbar reports config and CSS mistakes instead of skipping them.

The demo is real footage of flowbar on niri, composed with HyperFrames · a GIF version lives at docs/demo.gif

About

A bar that isn't there until you ask for it. Keyboard-summoned status bar for niri & Wayland: windows glide aside, every panel is one key away, and one config file restyles it live. Vala + GTK4.

Topics

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages