window tags
Thoughts after 5 years
I used to be a multi-screen maximalist. Everyone knows the more monitors you have the more powerful you are, right? I ran a triple-head setup turned in various ways, and it came with it’s own challenges for my wm management and window wants. One day I saw someone talking about their single monitor workflow and they said it helped them focus. After some reflection I came to the conclusion they were right - even if I’m referencing docs, having windows side by side rather than splatted helps me hone in on what matters. I would have to be a little more intentional with what is on the single screen in front of me instead of just splatting things into whatever space is available.
And so (initially as an experiment) I went from 3 mid monitors to one really nice monitor. Many edge cases left my dotfiles. I didn’t have to worry about lemonbar’s -g flag behaving oddly anymore. When the border of the monitor is the edge of the total display, you don’t have to worry about pseudo-borders for things like window movement scripts. All in all it was a great success! The result was a calmer, more focused desktop experience.
Around 2020 I saw a talk about the hikari wayland compositor and it mentioned
taking great inspo from cwm, a window group wm in the openbsd world. I did some
further digging and thought that window groups might be a fine thing to have,
and it might stack further into the single-monitor feels described above - after
all, you go from N virtual desktops to just 1, with tags for summoning or
dismissing things at will. Thus the latter half of 2020 saw a lot of tag/group
experiments for me, jamming the concept into bspwm with a script, currently
called btags
. bspc
can hide windows by toggling a hidden flag on them -
After ~6 months of messing with the concept, things largely stabilized, though I
did come back to tweak the flow once or twice in the 5 years since.
So.. What worked? What didn’t?
Overview:#
- I have 4 tags
- Tags have their own associated border color
- Toggling a tag just means flipping the hidden flag with bspc
- I still tile my windows, am not interested in a floating experience
Ideas that worked#
The hole, and dismissal#
The 4th tag is my “hole” tag. It’s where I banish windows I don’t want to see, but still keep them open - things like a torrent client, spare emacs window, or steam. After a few years, I realized I needed a “dismiss” notion in all this. Something to say “idc where this window goes, but not here”. Adding it made my experience much smoother pretty much right away.
Subscription#
Subscribing to bspwm events allows me to automatically assign tags to windows
based on their WM_CLASS
, or inherit the value from the currently focused tag.
This means I don’t have to assign window tags often, things go where they
should (ready to be summoned without thought)
Showing how I get the info to make those decisions:
bspc subscribe node_add | while read -r event m d i wid; do current_class=$(xprop WM_CLASS -id $wid) current_name=$(xprop WM_NAME -id $wid) last_class=$(xprop WM_CLASS -id $(bspc query -N last -n)) # ... done
Window border colors from tag#
Using distinct colors, I can tell assigned tags at a glance (drawn with chwbn):

From the top left clockwise: net, code, code, hole
# tag, visible, border color, wids $ btags state-plain code true e9a4d1 0x01ACB110 0x01AD21ED net true 7bcc7b 0x01E00013 chat false 98bde1 hole true b9b9b9 0x01AE254F none true 000000 0x0340003B
Fishing#
I have a script called find_class
that finds and shows a WM_CLASS
,
unhiding it if it is hidden - it does not touch the tag toggle state, which
allows me to view a window in a hidden tag. Thus, I can summon steam from the
hole without conjuring all the other windows I’ve thrown in there, and it
returns on the next action that triggers a tag render.
Ideas that didn’t pan out#
Status lines#
I gave btags
an option to match the output format of bspc subscribe
initially,
thinking it would be nice to plug and play into existing status bar helpers, but
ultimately ended up implementing a more plain status reporter and using it in my panel
$ btags state : WMDP-0:Fa:Ob:Fc:ohole:fd:LT:TT:G
$ btags state-plain a true e9a4d1 b true 7bcc7b 0x01A25F85 0x01E00013 0x01E00013 0x01A219FF c true 98bde1 hole false b9b9b9 0x0340003B 0x01A042CE none true 000000
Resize-averse applications#
In bspwm, showing/hiding a tiled node means re-inserting it into the tree, which can result in many resize events in nearby windows. Some programs (terminals, emacs, most websites) take this in stride, but occasionally you run into programs that don’t. The runelite runescape client was causing my entire wm to freeze when being resized so often for the show/hide action.
What might a return to virtual desktops look like for me?#
I’m writing this post because occasionally I feel like I should scrape this whole notion and return to a more traditional setup. Let’s think about it:
- I’d miss the “summon browser” key via tag focus - would probably make it a search-for-browser instead?
- The “hole” concept can still exist in an nth desktop, along with a dismissal notion
- cycling between current window class could be a thing
- I could get rid of btags and tag state most likely, simplify border handling (would only have to worry about one focused window, no multi-color drawing)
- Would be a feeling of “going to” windows rather than summoning/dismissing them
in one space
- benefit: could leave some workspace in-progress with an idea alone for awhile and pick it right back up
- Is it possible to have summon/dismiss notions with keybinds for desktop flicking and not have it be keybind hell? right now these things are conflated because it’s done via tags, so I don’t have to think about it, which is very nice.
- Flicking through window class is more limited than a tagging notion because you get to tag windows in an adhoc fashion. Is there some world where I mix tags and desktops? I would want a way to show details of the current tab group next to the desktop status - perhaps in the panel.
- One thing that would be missing/have to implement if I wanted it: per desktop layouts