Tweaking deft: quicker notes

I posted recently about using deft to make quick notes, and after using it for a bit I like it a lot, but wanted to make a few tweaks to the way it works. This gave me an excuse to learn a few lisp techniques, which other lisp novices might find useful.

I really like the way that org-capture lets me quickly make a note and return me seamlessly to where I was before, and so I wanted deft to be a bit more like that. By default, if I launch deft and make a note, I have to:

  • save the buffer
  • kill the buffer which takes me back to the deft menu
  • quit deft

This is too much work. Okay, I could save the note buffer and then switch back to my original buffer using e.g. winner-undo but that is still too much work!

Instead I’ve dabbled in a bit of lisp coding which I think illustrates a few nice ways you can customise your emacs with minimal lisp skills (like mine).

To start with I made my first attempt to advise a function. This is a way to make a function built into emacs or a package behave differently. Here I advise deft to save my window configuration before it launches:

;;advise deft to save window config
(defun bjm-deft-save-windows (orig-fun &rest args)
  (setq bjm-pre-deft-window-config (current-window-configuration))
  (apply orig-fun args)
  )

(advice-add 'deft :around #'bjm-deft-save-windows)

Side note: in principal, I think something similar could be done using hooks, but my reading of the deft code suggested that the hooks would run after the window configuration had been changed, which is not what I wanted.

I then make a function to save the current buffer, kill the current buffer, kill the deft buffer, and then restore the pre-deft configuration. I then set up a shortcut for this function.

;;function to quit a deft edit cleanly back to pre deft window
(defun bjm-quit-deft ()
  "Save buffer, kill buffer, kill deft buffer, and restore window config to the way it was before deft was invoked"
  (interactive)
  (save-buffer)
  (kill-this-buffer)
  (switch-to-buffer "*Deft*")
  (kill-this-buffer)
  (when (window-configuration-p bjm-pre-deft-window-config)
    (set-window-configuration bjm-pre-deft-window-config)
    )
  )

(global-set-key (kbd "C-c q") 'bjm-quit-deft)

So now, I can launch deft with C-c d make a quick note and then quit with C-c q to get back to where I was. This is pleasingly close to the experience of org-capture.

Note that bjm-quit-deft is not bullet proof; there is nothing to stop you running it in a buffer that is not a note opened from deft, but if you do, nothing terrible will happen. If I was a better lisp programmer I could probably come up with a way to test if the current buffer was opened from deft and issue a warning from bjm-quit-deft if not, but I am not much of a lisp programmer!

More to follow on tweaking deft…

  • Kaushal Modi

    You can bind `bjm-quit-deft` in the `deft-mode-map` (I am assuming that such a map exists :)). That way, you don’t expose a mode-specific command in the global map.

    • Ben Maughan

      Thanks for the suggestion. There is a deft-mode-map, but once I have used deft to open the notes file I am no longer in deft mode, but in org mode, so I would not be able to use the keybinding.

      • Kaushal Modi

        Inspired by your post, I tried out deft today and made the following customization: (1) One wrapper function to implement deft open/kill deft file (2) I also don’t like to have spaces in the file names and want them to be always in lower case and thus this.

        • Ben Maughan

          Very nice – I can learn a few things from your code! Also, great minds think alike – my next deft post is about removing the spaces from the file names. I have a different (possibly more naive) solution. I’ll be interested to hear what you think…

          • Kaushal Modi

            Thanks! I pushed myself to try out this package; until now I always thought that org-capture is more than enough. But I now think that this can compliment that to add a collection of notes broken down by categories that won’t always be suitable to be in the captured notes. Looking forward to the next post of yours! 🙂

  • Gregory Hugaerts

    if using bind-key you can add
    (unbind-key “C-c q” org-mode-map)
    to bjm-quit-deft and use
    (add-hook ‘deft-mode-hook (lambda ()
    (bind-key “C-c q” ‘bjm-quit-deft org-mode-map)))
    to get emacs to set and unset the keybinds when entering/exiting deft

    • Ben Maughan

      Thanks – this is a useful suggestion. I think I’ll implement it!