2009-09-19

wanderlust tips and tricks

Earlier, I spoke of the wonderful Wanderlust e-mail client. After years of using mutt, I am a quite happy Wanderlust-user now. Now, it's few months since my conversion, time to discuss some of the customizations I did. Not all the defaults are so well-chosen (in my opinion), but fortunately, the package is very configurable.

If you are interested in Wanderlust, this entry might save you some time in figuring out such customizations and some other tricks. If you haven't done so before, I'd recommend you to read the older entry first. Also, the entry about BBDB may be useful.

Before going into the customizations, let me first answer a question I got asked a couple of times: why I am using Wanderlust and not, say, VM, gnus, Mew or even mutt or some other client?

To start with the last part, an emacs-based client fits in very well with my workflow, which is (duh) revolves around emacs. Doing my email there as well makes a lot of sense - a little return-on-investment for the time spent taming emacs and its bag of tricks.

The reason I particularly like Wanderlust, is that it works very well with mail stored in maildirs - as you may know, maildir is a one-file-per-message way of storing your mail on disk. That's great for backing up things, and sync'ing different machines.

Unlike VM and gnus, Wanderlust keeps the mail in the maildir as-is, and does not use a separate spoolfile – thus, all changes are reflected in the maildir itself, making it possible to use different clients (ie., use mutt when needed). Even more important, the wonderful tool offlineimap does two-way synchronization with IMAP-servers, and downloads everything into a maildir. So, I can download all the mail on my laptop machine, go offline and work on the messages (delete, move, reply etc.) during a flight, and when I'm back online, I can synchronize things. All this 'cloud'-stuff is nice, but I like to have my mails on my side of the intertubes.

Ok, now let's take a look at some of the customizations and tricks. All of these are little snippets to add to your ~/.wl-file.

Forwarded mails should use 'Fwd:', not 'Forward:'

I wonder why this is not the default.

(setq
  wl-forward-subject-prefix "Fwd: " )    ;; use "Fwd: " not "Forward: "

Reply-to-all should not be the default

By default, Wanderlust uses Reply-to-All; that is usually not what we (well, I) want. The code below makes Reply-to-Sender the default, with Reply-to-All behind C-u; ie. A or a will reply to sender, C-u A and C-u a reply to all.

(Note, the uppercase A is for replying with quoting the original message, while the lowercase version starts the reply with an empty message)

;; from a WL-mailinglist post by David Bremner

;; Invert behaviour of with and without argument replies.
;; just the author
(setq wl-draft-reply-without-argument-list
  '(("Reply-To" ("Reply-To") nil nil)
     ("Mail-Reply-To" ("Mail-Reply-To") nil nil)
     ("From" ("From") nil nil)))


;; bombard the world
(setq wl-draft-reply-with-argument-list
  '(("Followup-To" nil nil ("Followup-To"))
     ("Mail-Followup-To" ("Mail-Followup-To") nil ("Newsgroups"))
     ("Reply-To" ("Reply-To") ("To" "Cc" "From") ("Newsgroups"))
     ("From" ("From") ("To" "Cc") ("Newsgroups"))))

Setting up spam-handling

If you're using spamassassin for spamfiltering, you can quite easily integrate it with Wanderlust:

(require 'wl-spam)
(wl-spam-setup)
(setq elmo-spam-scheme 'sa)   ;; sa for spamassassin, see the elmo-spam-scheme
                              ;; docs for alternatives
(setq wl-spam-folder ".spam") ;; maildir to store spam

After this, you quite easily handle spam in the 'Summary' with some keybindings:

  • k C : check whether spamassassin considers this message 'spam'
  • k m : mark message(s) as spam (move to spam folder)
  • k n : learn this message is 'ham'
  • k s : learn this message is 'spam'

Note, there are some hooks for other spamfiltering solutions as well.

How to easily refile messages

I receive all my messages in only two mailboxes: one for personal mail, and one for mailing lists. If, after reading, I want to keep the message, I'll refile it to some other folder (after all, it's good to empty your mailboxes quite often. Wanderlust makes this refiling quite easy; the first way is to do it semi-automatic, i.e., let Wanderlust 'guess' the folder for you, based on the contents of the message. Then, when pressing 'o' in the summary, it will suggest this folder, and you can refile (move) the message. You can set up this 'guessing' something like this:

(setq
  ;; refile rules determine the default where mails are put

  ;; when you mark them for refiling ('o'); cfg. save-hooks in mutt
   wl-refile-rule-alist  
  '(
     ("Subject" ;; put more specific rules before more general ones.
       ("emacs"   . ".emacs")   ;; emacs-related mail

       ("running" . ".running") ;; running-related mail
       )
     
     (("To" "Cc" "Delivered-To") 
       ("myself@company.com"      . ".workmail") 
       ("myself@home.com"         . ".privatemail"))
     
     (("Precedence" "Priority")
       ("bulk\|1\|2\|list"       . ".bulkmail"))))

Explicit refiling

Semi-automatic refiling works fairly well, but you might also want to have some explicit shortcuts to move messages to specific folders. For example, to move message from your inbox to your Project X-folder, or your Project Y-folder.

(defun djcb-wl-summary-refile (&optional folder)
  "refile the current message to FOLDER; if FOLDER is nil, use the default"
  (interactive)
  (wl-summary-refile (wl-summary-message-number) folder)
  (wl-summary-next)
  (message (concat "refiled to " folder)))

(define-key wl-summary-mode-map (kbd "b x") ;; => Project X

  '(lambda()(interactive)(djcb-wl-summary-refile ".project-x"))) 
(define-key wl-summary-mode-map (kbd "b y") ;; => Project Y
  '(lambda()(interactive)(djcb-wl-summary-refile ".project-y")))

Assuming you have (Maildir) folders project-x and project-y.

Check outgoing mail

It's not uncommon to forget to add a subject or an attachment when you send a mail (or at least, when I send a mail…). However, using wl-mail-send-pre-hook we can let Wanderlust warn us when something like that happens.

;; suggested by Masaru Nomiya on the WL mailing list

(defun djcb-wl-draft-subject-check ()
  "check whether the message has a subject before sending"
  (if (and (< (length (std11-field-body "Subject")) 1)
        (null (y-or-n-p "No subject! Send current draft?")))
      (error "Abort.")))


;; note, this check could cause some false positives; anyway, better
;; safe than sorry...
(defun djcb-wl-draft-attachment-check ()
  "if attachment is mention but none included, warn the the user"
  (save-excursion
    (goto-char 0)
    (unless ;; don't we have an attachment?

      (re-search-forward "^Content-Disposition: attachment" nil t) 
     (when ;; no attachment; did we mention an attachment?
        (re-search-forward "attach" nil t)
        (unless (y-or-n-p "Possibly missing an attachment. Send current draft?")
          (error "Abort."))))))

(add-hook 'wl-mail-send-pre-hook 'djcb-wl-draft-subject-check)
(add-hook 'wl-mail-send-pre-hook 'djcb-wl-draft-attachment-check)

Ok, that's all for now… I'll get back to Wanderlust in the future; of course, feel free to add your own tricks in the comments-section.

2009-08-16

managing e-mail addresses with bbdb

BBDB, the Insidious Big Brother Database is an Emacs addressbook application that works particularly well with e-mail. It's one of the classic emacs packages, written in 1991 by Jamie Zawinski.

Personally, I do not use BBDB as a general address book. Instead, I use it to harvest the e-mail addresses of the people that send me mail, so that the next time I'd like to send e-mail, I can auto-complete the names / e-mail addresses. If you're not using some emacs-based email client, BBDB might not be that useful in practice.

Note that other people are using BBDB for much more, see the Emacswiki-entry for some examples of that. Here, I just give some basics to get you started; please refer to the fine manual for all the details.

configuration

So, after you've installed bbdb (just follow the instructions; alternatively Ubuntu/Debian users can simply install the bbdb package), we can add the following to .emacs to set it up:

(setq bbdb-file "~/.emacs.d/bbdb")           ;; keep ~/ clean; set before loading
(require 'bbdb) 
(bbdb-initialize)
(setq 
    bbdb-offer-save 1                        ;; 1 means save-without-asking

    
    bbdb-use-pop-up t                        ;; allow popups for addresses
    bbdb-electric-p t                        ;; be disposable with SPC
    bbdb-popup-target-lines  1               ;; very small
    
    bbdb-dwim-net-address-allow-redundancy t ;; always use full name
    bbdb-quiet-about-name-mismatches 2       ;; show name-mismatches 2 secs

    bbdb-always-add-address t                ;; add new addresses to existing...
                                             ;; ...contacts automatically
    bbdb-canonicalize-redundant-nets-p t     ;; x@foo.bar.cx => x@bar.cx

    bbdb-completion-type nil                 ;; complete on anything

    bbdb-complete-name-allow-cycling t       ;; cycle through matches
                                             ;; this only works partially

    bbbd-message-caching-enabled t           ;; be fast
    bbdb-use-alternate-names t               ;; use AKA


    bbdb-elided-display t                    ;; single-line addresses

    ;; auto-create addresses from mail
    bbdb/mail-auto-create-p 'bbdb-ignore-some-messages-hook   
    bbdb-ignore-some-messages-alist ;; don't ask about fake addresses
    ;; NOTE: there can be only one entry per header (such as To, From)
    ;; http://flex.ee.uec.ac.jp/texi/bbdb/bbdb_11.html

    '(( "From" . "no.?reply\\|DAEMON\\|daemon\\|facebookmail\\|twitter")))
)

This will set up BBDB for you. I have commented the various settings; you can of course get more information for each of them by putting your cursor on them (in emacs) and issuing C-h v.

integration with e-mail clients

Another important part is the integration with e-mail - which is why I am using BBDB in the first place.

As I mentioned before, I am using the wonderful Wanderlust e-mail client for emacs, and you can easily integrate it with BBDB by putting the following in your .wl-file:

(require 'bbdb-wl)
(bbdb-wl-setup)

;; i don't want to store addresses from my mailing folders
(setq 
  bbdb-wl-folder-regexp    ;; get addresses only from these folders
  "^\.inbox$\\|^.sent")    ;; 


(define-key wl-draft-mode-map (kbd "<C-tab>") 'bbdb-complete-name)

For gnus, you'd use something like:

(add-hook 'gnus-startup-hook 'bbdb-insinuate-gnus)

(I am not using gnus myself, feel free to add you setup in the comments)

The BBDB-manual has the details for some other mail clients as well.

Use

So, we have everything set up now – but how does it work? Well, whenever you read e-mails, BBDB stores the various e-mail addresses. Whenever you write an e-mail, you can complete the names with M-x bbdb-complete-name, by default bound to M-TAB. This keybinding conflicts with many window managers, which already use M-TAB (Alt-TAB) for window switching. So, it's useful to rebind it to something else, for example C-TAB (I already did that for Wanderlust, in the example above).

I don't use BBDB too much directly, but you can manipulate the address; first display one with M-x bbdb-display-address, they you can edit a field by pressing 'e', 'd' for deleting the field or record, C-o for adding a new field and so on – see the whole list.

2009-08-03

interview with Chong Yidong and Stefan Monnier

Earlier this year, Chong Yidong and Stefan Monnier took over Emacs maintainership from Richard Stallman, and they successfully completed the Emacs 23.1 release. I asked them a couple of questions about the process, Emacs-development and some of the plans for the future.

I'd like to thank Chong (CYD) and Stefan (SM) to take the time to answer my (djcb) questions and even more so for doing an excellent job bringing us Emacs 23!


djcb: First of all, could you tell us a bit about yourself? For example, what you do when not hacking on Emacs?

CYD: I'm a postdoc in theoretical physics, specializing in photonic crystals and other optical phenomena.

SM: I'm a professor at the University of Montréal, teaching and researching theory of computer languages. More specifically, I design new type systems and try and abuse existing type systems for "type based formal methods" purposes.

djcb: Earlier this year, the two of you took over the maintainership of Emacs from Richard Stallman. How did you get involved in hacking on Emacs? How has the transition gone?

CYD: My first involvement in Emacs-related development was around 2004 or 2005—very recent by Emacs hacker standards—when I found myself with some free time on my hands after college. At that time, I wrote wikipedia-mode, a major mode for editing Wikipedia articles, plus some word-wrapping code that eventually became longlines-mode, and patches to emacs-devel fixing a few minor bugs. My level of involvement gradually grew, until eventually I was helping Richard to roll the pretest tarballs for the Emacs 22 release.

Because I was quite active in the Emacs 22 release process, I've been pretty comfortable with my role in Emacs 23. It helps, of course, that many parts of Emacs have their own dedicated and experienced maintainers, e.g. the major Lisp packages such as CC-mode, Gnus, and Org-mode.

SM: I started hacking on Emacs a fairly long time ago when I was waiting to start my PhD, but it only got more serious during my PhD when I decided that PCL-CVS was a neat idea but unusable as it stood (for lack of maintainership). It all went downhill from there.

The transition to maintainership happened very smoothly. I had already considered maintaining Emacs when Gerd [ Gerd Moellmann ] left (i.e. when 21.1 was released; at which point Richard ended up regaining maintainership for lack of any other volunteer), but it was a pretty busy time for me, so I decided not to. This time Richard kept a very active role, which coupled with the help of Chong made it very pleasant.

There's a fair bit of pressure, of course, because it's a very old package, so people have a lot invested in it, making some changes terribly delicate. As a maintainer, I did get to steer the direction of Emacs development, tho mostly by my own contributions and by imposing some contentious new defaults. The role of a maintainer as I see it is mostly to make sure the package keeps its integrity.

But I have to say, that while Chong started maybe a bit more of a "rookie maintainer" than I, he quickly took over and he deserves much of the credit for 23.1, while I was too busy with my work to do much good.

djcb: Talking about Emacs development: there are of course many people involved. Can you give a estimate of how many?

CYD: There are about 120 people who have commit access to the code repository; of these, I think around 20 contribute regularly. This does not count the packages that are maintained separately from Emacs.

Additionally, we do of course receive a steady stream of small patches from various users.

Emacs 23 has just been released (on July 29 2009), congratulations, a great accomplishment indeed! From your perspective, what are the most important improvements in Emacs 23 for end-users? And what about the internals? Are there any big changes in the way Emacs operates?

CYD: I'd describe the Emacs 23 release cycle as dominated by internals changes, in contrast with Emacs 22, where most of the major improvements occurred at the Lisp level. There are two fundamental changes. First, the internal character representation is now Unicode-based, which simplifies various aspects of multilingual editing. Second, the font engine has been revamped, and, among other things, we now support anti-aliasing on X. Both these changes are due largely to Kenichi Handa, who deserves a huge amount of credit for patiently developing the code a period of years.

One other major internals change is a restructuring of the terminal interaction code, by Károly Lőrentey, which allows a single Emacs process to display on X and text terminals simultaneously. Building on this "multi-tty" code, Dan Nicolescu implemented a small but clever hack, allowing Emacs to run as a daemon serving emacsclient connections.

There are several Lisp-level changes, large and small. For instance, Stefan revamped the minibuffer completion code, which is now more sophisticated about generating completions. And there are, as usual, new modes and packages: Doc-view mode, Ruby mode, nXml mode, etc.

SM: Better support for Unicode, and better support for fonts, multi-tty support, plus lots of new modes as always. Of course, I'm very happy with my new completion code, which makes partial-completion-mode obsolete (and enabled by default).

The new support for Unicode and for fonts required significant changes. Big thanks to Kenichi Handa for most of that.

djcb: Are there any features that you would have liked to add, but that were somehow not yet ready?

CYD: One feature that I'd have liked to include into 23.1 is CEDET, a set of packages by Eric Ludlum (the author of Speedbar), which turns Emacs into an IDE. There was no time to merge it for 23.1, but hopefully it will be included in 23.2.

SM: Several packages were planned for inclusion, but didn't make it. Support for GNUstep was planned (and is actually in there) but doesn't work. Also I hoped the new VC code would be developed further, but it sadly stayed at the stage where it mostly provides the same features as the old one (with all kinds of improvements in the way it supports them, tho).

djcb: There is always a bit of tension in Emacs between keeping things as they are, and changing things to be more like other programs - for example when thinking about key bindings and various defaults. What is your take on this? Should Emacs try to accommodate new users, or instead try to keep things as they are?

CYD: My impression is that I'm a little more conservative than Stefan with regards to changes, though I'm not sure what he thinks ;-) That said, we seem to arrive at the same conclusions with surprising frequency.

SM: Emacs standard key bindings (like C-x and C-c prefixes) clash badly with "standard" key bindings of other apps, so I don't think there's much hope to make Emacs like other applications. But yes, I generally believe that, all things being equal, it's better to be like others than to be different in this respect. But since changing bindings (or behaviors) is disruptive, I only consider it worthwhile if I believe the new default is really superior (not just for new users).

djcb: For example, in Emacs 23, transient-mark-mode is the default, but delete-selection-mode is not. How do you decide such things?

CYD: Typically, we try not to make flashy changes. The transient mark mode change is the exception that proves the rule: transient-mark-mode is so useful, and is so widely used (even Richard uses it), that it doesn't make sense to leave it off by default. But the rule of thumb is to improve Emacs on Emacs' own terms; for instance, CUA mode will not become the default anytime soon, I think.

SM: transient-mark-mode is an enabler: it allows some commands to behave differently depending on the activation state of the region. So it's a clear improvement. delete-selection-mode is not as important in this regard. We may see something along the lines of delete-selection-mode at some point, tho probably something more minor that only caters to the few cases where delete-selection-mode is more than just a way to avoid hitting C-w.

djcb: How do you see the competition with other text editors? Do you look for ideas elsewhere? Is there any other editor you would be using if Emacs did not exist?

CYD: I'm afraid I don't pay much attention to other editors.

SM: I used Zmacs, XEmacs, and Epoch at some point. That's about it. I do like structured editors, and I think Emacs should and will move in this direction (with more parsing going on).

djcb: It's a bit premature of course, but it's always interesting to speculate a bit about the future. Do you have any particular post-Emacs-23 plans? Obviously, this all depends on what people come up with, but are there any directions you would like Emacs to go?

CYD: The present plan is for Emacs 23.2 to contain a small number of new features, in addition to bugfixes. As mentioned above, I'd like to try to include CEDET. In general, I hope to move to shorter, more disciplined release cycles. Emacs 23 was a good step in that direction, as it was shorter than the previous cycle.

SM: My main goal for Emacs-23 was to shorten the release cycle. Hopefully, the quality has not been reduced accordingly. For 23.N there are several improvements planned (or even done), mostly about inclusion of packages like js2-mode and CEDET. In the longer term, the main goals for me are the integration of the lexical-scoped branch, the support for bidirectional display, and adding more parsing technology (basically replace syntax-tables with something like lex & yacc, maybe).

Thanks a lot Stefan and Chong!

2009-07-28

emacs 23 has been released!

Emacs 23(.1) has been released! After only just over two years since the previous version, emacs 23 has been released on July 29 2009. Time to celebrate! And a big thanks all the talented hackers that made it possible!

Emacs 23 brings many new features. Some of those have been discussed before in emacs-fu, and of course you can get the full list from the NEWS-file (C-h n). This is just a list of some of the highlights, in particular the end-user-visible ones. Let's go through them - of course I cannot mention all of them, so feel free to add your favorite one in the comments.

fonts & anti-aliasing

Finally, emacs 23 brings support for anti-aliased fonts to X (Mac/Windows users have had this for a while). If you're running emacs on X, this one change is enough to never want to go back to an older version of Emacs again.

The new font system mentioned in some posts before: setting fonts and emacs 23.

support for D-Bus and Zeroconf

You can now call other services on the desktop using the DBUS IPC system (popular on X); using d-bus: an example shows how to communicate with the Tomboy note taker program from emacs. As more and more desktop services are accessible using D-BUS, this offers great opportunities for better integrating emacs with the rest of the desktop. For example, one could imagine that emacs could communicate with a network manager when it needs a connection. Or it could show a desktop notification when an appointment is near. And all without adding hard dependencies or calling external binaries.

Using Zeroconf is also quite easy; for example, to get a list of all zeroconf-support printers, you could do something silly like:

(require 'zeroconf)
(zeroconf-init)
(dolist (srv (zeroconf-list-services "_printer._tcp"))
  (insert (format "\nprinter: %s" (nth 2 srv))))

to insert a list of the available printers in your current buffer. As with D-Bus, it's really an enabler for a lot of cool things.

support for 'headless' emacs-daemon

If you have a lot of support packages, emacs startup can be a bit slow. However, emacs 23 brings emacs --daemon, which enables you to start emacs in the background (for example when you log in). You can instantly pop up new emacs windows (frames) with emacsclient. Of course, you could already have an emacs 'server' in older versions, but being able to start it in the background makes this a much nicer solution.

The Emacs-daemon was discussed in emacs-fu in emacs –daemon and windows and daemons (for MS-Windows). Popping up new emacs windows is so fast that you can use emacs for any editing job, for example as an editor for an email program, or for quick rememember notes.

You can even combine X and console clients in one session now.

Emacs now support Xembed

This enables you to embed emacs in other programs (on X) using XEmbed. Haven't played with that yet. There is some more information in EmacsWiki/Xembed.

Support for frame opacity

You can now make you emacs frames transparent. Discussed before in transparent emacs. Not sure how useful this is, but it surely looks nice :)

Internationalization

Emacs's character set is a superset of Unicode, with about four times the space available. That should be enough for the foreseeable future… There are also many new character sets available, as well as new language environments, such as Chinese-GB18030, Khmer, Bengali, Punjabi, Gujarati, Oriya, Telugu, Sinhala, and TaiViet.

Note that, internally, emacs uses UTF-8 now.

New defaults

  • Screen motion now goes by screen lines by default, that is when you move the cursor up or down, it follows the line as you see them. Nice.
  • Transient mark mode (visible selection) is now on by default, so no need for (transient-mark-mode t) in your .emacs anymore. However, you still need to put (delete-selection-mode t) if you like replace the current selection with your typing.
  • Also shift-select mode is enabled by default, so you can select with shift + the arrow keys.

New modes and packages, and updated ones

2009-07-13

stepping through your window configurations

As a small addendum to the entry about keeping related buffers together (with Elscreen): there is also winner-mode, as was mentioned by ustunozgur. winner-mode is a bit simpler than Elscreen. It allows you to step through the various window configuration you had before - instead of having separate 'tabs' as in elscreen, you just step through your history.

I have the following in my .emacs:

(require 'winner)
(setq winner-dont-bind-my-keys t) ;; default bindings conflict with org-mode

(global-set-key (kbd "<C-s-left>") 'winner-undo)
(global-set-key (kbd "<C-s-right>") 'winner-redo)
(winner-mode t) ;; turn on the global minor mode

As you see, I am using the windows-key in the key bindings once more, but of course you can use something else as well.

2009-07-09

keeping related buffers together with elscreen

I wrote about switching buffers a couple of times. Switching buffers is one of the things I do a lot when using emacs – switching between e-mail, IRC and some blog entry. Or simply between a couple of source files in a project.

With some of the tricks mentioned, switching buffers can be made pretty easy.

However, what about programs that consist of multiple buffers? For example, my e-mail program (Wanderlust) splits the screen in separate buffers with mail headers, mail folders and the contents of one message. The same for fancy debugging with gdb, or simply when I have split my screen in two (C-x 2) to view two files at the same time. When I then try to switch buffers, only one of the related buffers will be switched – which is usually not what I want.

I'd like to treat a set of related buffers plus their screen layout as a logical unit.

There are different ways to do that in emacs. One obvious way is to use multiple frames (windows). But I prefer to keep everything in one - and I found the that the easiest solution is elscreen.

Installation is simple; download from here, and follow the instructions in the package. I've set up some easy key-bindings in my .emacs:

(load "elscreen" "ElScreen" )

;; F9 creates a new elscreen, shift-F9 kills it
(global-set-key (kbd "<f9>"    ) 'elscreen-create)
(global-set-key (kbd "S-<f9>"  ) 'elscreen-kill)  


;; Windowskey+PgUP/PgDown switches between elscreens
(global-set-key (kbd "<s-prior>") 'elscreen-previous) 
(global-set-key (kbd "<s-next>")  'elscreen-next) 

Now, whenever I want to switch to a new task, say, read e-mail, I press F9, and a new elscreen will appear (it's visible as a sort-of 'tab' at the top of your screen), and start e-mail there. I can then switch to other elscreens, and all of them maintain their buffers and window layout. I have found this very useful. There are some more tricks, and some add-on packages, but this should give you a good start.

There is one small item on my todo-list. Example: when I push M-x wl, emacs automatically switches to the Wanderlust-buffer – or starts it. Now, when using elscreen, I'd like to automatically switch to the correct screen instead of switching the current buffer.

2009-07-03

keyboard shortcuts

Emacs has many useful functions, but for the most efficient use you really need to make keybindings (as previously discussed) for the ones you use often. There's no shortage of possible shortcuts, but the number of easy-to-remember bindings is fairly limited.

I can remember bindings that I use all the time like M-w for copy (well, kill-ring-save), or M-q (fill-paragraph) to word-wrap a paragraph, even if they're not that mnemonic (interestingly, it can be hard to verbalize these bindings when someone ask me – but my fingers have no such trouble).

For functions that I use every minute, any weird key binding will do (as long as it is short). And functions that I use seldomly I can look up in a menu. The trouble is with those functions in between :)

Bindings that involve the arrow-keys are attractive, but I've found that e.g. org-mode binds many of those already. And in the olden days, the C-c-prefix was reserved for user-defined key bindings – but again, org-mode and other packages have overtaken that those. So what's left? Recently, I have been using the Windows-key a bit more. Under (my) X, it's bound to super, and emacs does not use it for anything else, so I have been using it to create a set of useful key bindings. I am trying to be a bit systematic, where super + lowercase letter starts some 'application':

(global-set-key (kbd "s-a") 'org-agenda-list) ;; Agenda
(global-set-key (kbd "s-n") 'org-todo-list)   ;; todo-list (nextactions)

;; program shortcuts
(global-set-key (kbd "s-b") 'browse-url)  ;; Browse (W3M)
(global-set-key (kbd "s-f") 'browse-url-firefox)  ;; Firefox...
(global-set-key (kbd "s-t") 'twitter-get-friends-timeline) ;; Twitter
(global-set-key (kbd "s-w") 'wl)            ;; Wanderlust

and super + uppercase opens a file / special buffer, for example:

(global-set-key (kbd "s-S") ;; scratch
  (lambda()(interactive)(switch-to-buffer "*scratch*")))
(global-set-key (kbd "s-E") ;; .emacs
  (lambda()(interactive)(find-file "~/.emacs")))
(global-set-key (kbd "s-G") ;; gtd.org
  (lambda()(interactive)(find-file "~/.emacs.d/org/agenda/gtd.org"))) 

super + arrow keys I now use for windmove (see here).

The windows-keys are not perfect of course – they don't work from the console (easily) or, ironically, on Windows. But they are mnemonic – I can remember s-t for twitter; contrast this with C-x 5 2 to create a new frame.

So, I wonder, does anyone have some clever scheme for their key bindings? I think I am getting much of the efficiency from emacs from the fact that I can do just about anything with some quick actions on the keyboard, so I'm very interested.