Building a Better Window Manager This article Article I think this article has good comments on how to jump out of inertial thinking, understand and customize my WM.
Building a better window manager Eric Mangold
Teratorn (AT) World (DASH) Net (DOT) Net December 21,200 3
Contents1 Purpose
2 mindset
3 mice are slow
4 The keymap
5 choose a window manager
5.1 refreshing the Window Manager
5.2 launching programs
5.3 General bindings
5.4 other bindings
5.5 application specific key Translation
6 conclusion
7 links 1 Purpose
This paper deals with software user interfaces, and primarily with the user interface of window managers1, or WM's. it is the author's opinion that there is a lot of software with poor user interface capabilities. also, that software with good interface capabilities is almost always in need of fine-tuning.
Thus it is the purpose of this paper to describe a good window Manager interface. one that will minimize wasted time, and providing the user with a more streamlined interface experience. better concentration shoshould also be achievable while using your computer as opposed to the default Interface of most WM's.
This paper is aimed at people who havn't thought much about customizing their environment. However, it's the author's hope that even highly advanced users will find something useful.
2 mindset
When you're using your computer you shoshould always be awareWhatYou want to do, not justHowYou currently do it. for example, when you want to switch to a certain running application, you might reach for the moues to click it in a task bar, or hit Alt-tab to cycle through your windows. never automatically assume that your current tools are the best, and in this case they commonly are not. in this way you can identify faster ways of doing things.
3 mice are slow
Firstly, if you don't know touch-typing then this tutorial will be of little use. If you need to, go learn touch-typing first then come back here.
It shoshould be obvious that using the mouse to click a button, for example, is painfully slow compared to pushing a key or key-combination. all too often will software rely on the mouse where good key bindings2 wocould be better.
It wouldn't hurt to develop a healthy disdain for mouse-ware3 and the overuse of mice in general.
4 The keymap
This section describes how to change what your physical keys do. you might not want to do this since it will make your keyboard work differently than other into Les. this is more or less of an issue depending on how frequently you use other "uncustomizable" computers.
We are going to set up the modifier keys. A modifier is a key you press only in conjunction with other keys.4 C-C and C-V are common Bindings for "copy" and "Paste" and have strate the use of modifiers. please note that modifiers are slower that just pushing most keys. you shoshould always prefer to not use modifiers if just pushing a key will work for a given application. awkward keys such as home and end are an exception. these keys are too hard to push and shoshould never be used. use standard Emacs bindings instead.5
I'll describe two modifier layouts. The first is the one that I use. The 2nd is one that you might find more desireable.
The first thing we will do is setup the "control" and "Alt" keys as the two physical keys just to the left of the Space-bar. the two physical keys just to the right of the Space-bar will be our "super" and "hyper" keys. this will give names to the keys so we can use them in xfree86.
The physical layout will look like this.
[Control_l] [alt_l] [space] [super_r]
As you can see, all we care about are the two keys on either side of the space-bar, whichever keys they may be. in case you 've never thought about it, you press alt_l and super_r with your left and right-hand thumbs, respectively.
The reason we do this is to have a number of modifiers that are easy to push that we can use to control things. control and ALT (Meta) will have application-specific uses. super will manipulate windows and the Window Manager environment (mostly ). hyper will launch the programs we use (mostly ). I find that I can do everything I need with these four modifiers. if you find yourself wanting another modifier for something, the right-hand Shift key wowould probably be a good choice.
OK, to get xfree86 to do this you need to edit~ /. Xmodmap. You may also use the xkeycaps tool. Since I don't know your current keymap, I'll give you a procedure that shocould work regardless. It may be more detailed than necessary.
Step 1. Open a terminal and run the command"Xev". Now push the 2nd key to the left of the Space-bar (the one we want to make control_l ). write down the keycode. repeat for the 1st key to the left of the Space-bar, then the 1st on the right, then the 2nd on the right. you have the four keycodes now.
Step 2. make a backup copy~ /. Xmodmap, If it exists, then open~ /. XmodmapIn a text editor. copy and paste the follow block of lines:
Keycode A = control_l
Keycode B = alt_l
Keycode c = super_r
Keycode d = hyper_r
Clear Control
Add control = control_l
Clear mod1
Add mod1 = alt_l
Clear mod3
Add mod3 = super_r
Clear mod4
Add mod4 = hyper_r
Now, replace the "a" with the first keycode you wrote down, then Replace "B" with the 2nd, and so on.
Next, we will swap the escape and Caps Lock keys. since escape is pushed much more frequently than Caps Lock, it makes sense to have it in an easier to reach place. this is an even greater improvement if you use one of the Vi-style editors. if you're on a standard US keyboard, then add the following lines to your~ /. XmodmapFile, otherwise you're on your own :).
Keycode 66 = escape
Keycode 9 = caps_lock
Alternate #1-instead of the 2nd key left of the Space acting as the control key, have it act as the Escape key, and have the capslock key act as control. you will have to experiment to determine if your useage patterns make this a better layout.
Finally, you need to ensure that your system is loading your~ /. XmodmapFile when you start xfree86. the easiest way to check is to reboot and/or restart X. Then open a terminal and run"Xmodmap". You shoshould see output that matches what we have configured above. If not, you need to set xmodmap to load~ /. XmodmapManually. If you use~ /. XinitrcOr~ /. XsessionFiles, then you can add the line"Xmodmap ~ /. Xmodmap"Before your WM is launched. If you are using a graphical login, then you need to find it's startup file, and put the aforementioned line there.
5 choose a window manager
I recommend sawfish. other WM's may work, but I'm unware of any that have all the features that I will have strate. you may also use sawfish with Gnome (I do) If you want "visual representation of the desktop State", such as a task bar and those micro-windows for each virtual desktop. of course we won't be clicking on any of those things, but they are useful for keeping track of the stuff that's running on your system. gnome's also useful if you want a clock or panel applets or such.
5.1 refreshing the Window Manager
I'll detail my current sawfish config. you can adapt this to any window manager that supports the requisit features (if there are any ). if you do, I wocould be interested to know which Wm YOU CHOSE and what features made it a good choice.
There are several groups of tasks that your window manager will handle. I will talk about each individually.
5.2 launching programs
A major task of the window manager is to launch programs for you. another Overlapping Task is switching to programs that are already running. we are going to combine both tasks using the same key binding. this will not work for programs that you run more than once simultaniously. your terminal emulator will probably be one of those.
So, for example, lets say hyper-E is associated with your editor. if you press h-e while the editor is not running then it will be launched. if it is already running then it will be brought to focus (switching to the correct virtual desktop first ).
This is a powerful mechanic and will save you keeping track of what is running and what isn' t. We will use a sawfish extension called jump-or-exec to do this. Get it hereHttp://sawfish.uberstyle.net/index.php/SawfishWiki/JumpOrExecAnd install it.
We are going to use the hyper key to launch all the programs that we use. for each program that you want to use with jump-or-exec you need to add a block of code like the following to your~ /. Sawfish/RCFile.
(Bind-keys global-keymap
"H-e" '(jump-or-exec "gvim"
, (Lambda ()
(System
"Gvim &"))
, (Lambda (wind)
(Display-window wind ))))
There are three main parts. the first "H-e" is the key combination we are binding here. "gvim" is all or part of the window title of the program. "gvim &" is the command to run if a window matching the pattern "gvim" is not found. note the trailing ampersand. without it the program will run in the foreground and block sawfish into tively hanging your X session.
For programs that you run more than once you can use the sawfish keybinding editor.6 use the "run shell command" function.
The bindings you choose aren't that important. typically one will use the first letter of the programs name or it's function (such as "e" for "Editor "). if such a letter isn' t free to use, just pick one that's easy to press.
5.3 General bindings
I'll just give you the bindings I use. maybey a different configuration will suit you. the only rule of thumb is to make the most common bindings the ones that are easiest to press. please note these are just the basics, and there are a lot more possibilities. for example, you can use sawfish to control xmms.7
Super-a-activate Workspace: 1
Super-S-activate Workspace: 2
Super-D-activate Workspace: 3
Super-F-activate Workspace: 4
Super-m-maximize window toggle
Super-X-delete window safely
Super-J-cycle windows
Super-K-cycle windows backwards
Super-H-previous Workspace
Super-L-next Workspace
Super-o-send to next Workspace
Super-I-send to previous Workspace
Super-r-run shell command: gmrun
Super-Q-popup window menu
Super-T-popup Root menu
Super-p-iconify window
Super-e-show errors
Super-u-gnome logout
Super-w-move window interactively
Hyper-T-runs my terminal emulator
5.4 other bindings
Lookup. JL provides a mechanic to do some nifty things that I find myself doing every day. You can read all about it hereHttp://www.ewanmellor.org.uk/sawfish.html. Here's the lisp I use for these bindings, but you may want something different.
(Bind-keys global-keymap
; Prompt for Google search terms-focus browser window
"Super-G" '(lookup "google" t nil)
; Use X selection as Google search terms-focus browser window
; (If selection contains a URL, then that URL is visited instead
; Of searching Google)
"Super-G" '(lookup "google" t)
; The next two are the same as the previous two
; Should t that they don't focus the browser window
"H-G" '(lookup "google" Nil nil)
"H-G" '(lookup "google" Nil T)
; Dictionary searches
"Super-c" '(lookup "dict" t nil)
"Super-c" '(lookup "dict" t)
; Thesaurus searches
"Super-V" '(lookup "thes" t nil)
"Super-V" '(lookup "thes" t ))
5.5 application specific key Translation
This section deals with improving upon an applications keyboard interface where such application does not provide a way to do so "natively ". an example will make this clear. x-chat, an excellent IRC client, brings up the Search dialog box when you press the C-F binding. some folks may prefer this, But I wowould prefer C-F to move the cursor forward one space in keeping with the other Emacs bindings.8
With a bit of Lisp code, sawfish can pull some tricks to make the program interface the way we want it. in this case, we will catch the C-F event and synthesizing a right (arrow) event thus producing the desired effect.
To do this, we will first Add the following block of code to~ /. Sawfish/RCFile.9
(Define-match-window-setter 'keymap-Trans
(Lambda (W prop value)
(Declare (unused prop ))
(Let (keymap (or (window-Get W' keymap)
(Window-put w'keymap (copy-sequence window-keymap )))))
(Mapcar
(Lambda (pair); pair of from and to keys
(Bind-keys
Keymap (CAR pair)
(Lambda () (interactive)
(Synthesize-event (lookup-event (CADR pair) (input-Focus )))))
Value ))))
Now add a block like the following for each program you want to "fix ".
(Add-window-matcher 'wm _ class "xchat"
'(Keymap-Trans. ("C-F" "Right") ("C-s" "C-F "))))
There are three parts you shoshould understand. the first is the symbol wm_class, which indicates the following string will match against the class of the variable limit 10 if you wowould rather match the window's title, use wm_name instead.
Next is the string"Xchat". It selects the window (s) that our key translations will apply. we use this so that our translations will only affect the desired window (s ). you can get the class string by using the "matched windows" configurator.11 if you are matching the window title instead, then just pick a unique part of the title string (it doesn't have to be the whole thing ).
The third is the list of key events to translate. In the example above, that is the part of the Code which reads("C-F" "Right") ("C-s" "C-F ")). It is simply a list of one or more pairs. Each pair specifies the "from" and "to" events for each translation.
Here is another example for opera users.
(Add-window-matcher 'wm _ class "Opera"
'(Keymap-Trans. ("M-F" "C-Right") ("M-B" "C-left "))))
This overrides the hard-wired shortcuts for the file (m-F) and bookmark (m-B) menus. the bindings are then translated to C-right and C-left, respectively. this makes them move the cursor forwards and backwards by a word at a time. emacs users shoshould appreciate the added consistency.
6 conclusion
Sawfish has a ton more possible bindings. i'm sure you will want to review them and locate any that will make your work faster. also of note is the "library" at the sawfish wiki where you can find (and contribute !) Extensions that make it work in new and (hopefully !) Better ways.
Please email me with any suggestions, criticisms or other ideas.
7 links