Implementing 'grow down' window placement in Fvwm on X11

February 17, 2023

In days long ago, I used Twm as my window manager. Twm uses manual window placement for new windows; when a program wants to create a new window and it doesn't explicitly specify where the window should be on the screen, you move your mouse around to wherever you want the window to be (well, usually the top left of the window). Then you can click the left mouse button to place it there, or the right mouse button to invoke a special twm window placement feature. To quote the manual page:

[...] Clicking pointer Button3 (usually the right pointer button) will give the window its current position but attempt to make it long enough to touch the bottom the screen.

I became addicted to this feature when I used twm, because it's so handy for making big (xterm) windows. You don't have to size or resize your default 80x24 xterm; instead you put the top wherever you want and then click the right button and bang, it automatically goes to the bottom of the screen. It can be used with other programs too, of course, although I don't usually want to resize them as much.

When I moved to FVWM as my window manager, I wanted to keep this feature despite Fvwm not natively supporting it. Over the years I've used a number of ways to get this in Fvwm, starting from patching the source code to much better, lower overhead ways. My current approach uses Fvwm's InitialMapCommand window style option, inspired by this Fvwm cookbook entry.

First we need a function that will do this 'grow down', with a conditional command

DestroyFunc GrownDownFunc
AddToFunc GrownDownFunc
+ I windowid $0 (PlacedByButton3)   Resize bottomright keep -0p

'Resize bottomright' says we're specifying the position of the bottom right of the window; 'keep' says we want to keep the x (horizontal) position the same, and '-0p' says we want the y (vertical) to be at the bottom of the screen, or as close to it as window size quantization allows.

Then we need to invoke this function, passing it the window ID of the new window so it can work on the right window:

Style * InitialMapCommand GrownDownFunc $[w.id]

Because this approach uses styles instead of something more broad (such as FvwmEvent), I could limit this to terminal windows if I wanted to, or specifically exempt some windows. For example, if I never wanted to yank around the size of new Firefox windows this way, I could add:

Style Firefox InitialMapCommand Nop

So far I haven't bothered to exclude certain programs or specifically limit this to terminal windows, although in practice I almost entirely use it on terminals and editors such as sam.

(I sometimes use it on Emacs windows, but usually I also want to widen them beyond 80 columns. Which is actually an argument that I should change my default Emacs window size. It feels a little bit depressing to widen things out that way, but modern coding is what it is and it's not like I'm short on the horizontal screen space.)

Written on 17 February 2023.
« Linux Ext4 directories have a maximum size (in entries)
The size of a window is complicated in X (or can be) »

Page tools: View Source, Add Comment.
Search:
Login: Password:
Atom Syndication: Recent Comments.

Last modified: Fri Feb 17 23:00:15 2023
This dinky wiki is brought to you by the Insane Hackers Guild, Python sub-branch.