A customized Quickshell configuration for Niri with a full-width top bar, split popup system, themed control surfaces, and a simplified theme pipeline built around Quickshell QML + JS.
- Full-width top bar with shaped outer corners
- Per-screen
PanelWindowsetup viaVariants - Left section with:
- profile/avatar trigger
- CPU ring
- memory ring
- active workspace/window info
- Center section with a compact workspace strip
- Right section with:
- media chip
- notification indicator
- volume / Wi-Fi / Bluetooth controls
- volume pill
- Popup system for:
- profile menu
- system status
- media
- notification center
- Wi-Fi
- Bluetooth
- volume device switching
- power actions
- tray application menus
- Notification toast support
- Theme split into user-editable entrypoints + derived style layers
matugentemplate support for generatingmodules/Theme/colors.js
shell.qml— entry pointmodules/Bar/Bar.qml— global bar state + popup orchestrationcontrollers/— popup / notification coordination logiclayout/— screen windows and dismiss layerspopups/— popup host windows / toast windowssections/— left / center / right bar sectionswidgets/buttons/— compact right-side control buttonswidgets/chrome/— structural chrome such as outer cornerswidgets/panels/— actual popup panel componentswidgets/strips/— workspace / tray / notification strips
modules/Services/NiriService.qml— workspace / focused window state fromniri msgSystemStatsService.qml— CPU / memory samplingAudioService.qml— volume + sink/source switching viawpctlWifiService.qml— Wi-Fi / ethernet state vianmcliBrightnessService.qml— brightness helpers
modules/Theme/userTheme.js— main user-editable theme entrypointtheme.js— derived global theme helperscolors.js— semantic color tokensprofileMenuStyle.js— derived profile menu sizingbarPopupStyle.js— derived popup sizing accessprofileMenuConfig.js— profile content / greeting / image configmatugen/— templates and config for color generation
If you only want to tweak the shell, start here:
modules/Theme/userTheme.js
That file now contains the main knobs you are expected to edit:
typography— font family and base font sizelayout—barHeight,innerGap,uiRadius, top spacingbar— outer-corner curve behaviorprofile— avatar path and profile menu sizeprofileMenu— major profile-menu sizing groupspopup— widths / heights for popup panels
Everything else is mostly derived from those values.
- Global roundness:
modules/Theme/userTheme.jslayout.uiRadius
- Bar height and spacing:
modules/Theme/userTheme.jslayout.barHeightlayout.innerGap
- Outer-corner curve feel:
modules/Theme/userTheme.jsbar.outerCornerControlFactor
- Profile avatar image path:
modules/Theme/userTheme.jsprofile.avatarImagePath
- Popup sizes:
modules/Theme/userTheme.jspopup.*
Color tokens are kept in:
modules/Theme/colors.js
If you want automated color generation, use the included matugen template setup:
- Template:
modules/Theme/matugen/colors.template.js - Config:
modules/Theme/matugen/quickshell-colors.toml - Notes:
modules/Theme/matugen/README.md
Example:
matugen image /path/to/wallpaper -m dark -c modules/Theme/matugen/quickshell-colors.tomlThat command regenerates modules/Theme/colors.js while keeping the rest of the shell structure unchanged.
Required:
quickshellniriwpctl(PipeWire / WirePlumber)nmcli(NetworkManager)
Recommended:
- a Nerd Font for icon glyphs
From this repo:
quickshell -p ~/quickshell-past/shell.qmlOr if this repo is installed as your default Quickshell config:
quickshell- Popup placement and dismissal are coordinated centrally through the bar controllers.
- Tray menus depend on what the application exposes through the system tray menu interface.
- Notification behavior depends on whether this shell owns
org.freedesktop.Notifications. - Offscreen / sandboxed test runs may still fail due to missing Wayland / DBus access even when QML parsing is valid.
- Notifications not showing:
- make sure another notification daemon is not already active
- Audio devices not showing:
- check
wpctl status
- check
- Wi-Fi results empty:
- check
nmcli device wifi list
- check
- Niri workspaces missing:
- check
niri msg -j workspaces
- check