I'm finally converting my init file to use use-package. Thanks very much for your work on it (and for taking on maintainership of Emacs!).
I seem to be unable to use :bind to bind keys to lambdas. I've tried several combinations:
(use-package org
:bind (("<C-f5>" (lambda () (interactive) (org-agenda nil "A")))))
(use-package org
:bind (("<C-f5>" '(lambda () (interactive) (org-agenda nil "A")))))
(use-package org
:bind (("<C-f5>" . (lambda () (interactive) (org-agenda nil "A")))))
(use-package org
:bind (("<C-f5>" . '(lambda () (interactive) (org-agenda nil "A")))))
For all of those I get this error:
mapcar: Wrong type argument: listp, "<C-f5>"
I've searched Google and the issue tracker, but I can't find anything about this problem. I can't even find anyone using lambdas in :bind. But it does work with bind-key:
(bind-key "<C-f5>" (lambda () (interactive) (org-agenda nil "A")))
Thanks for your help.
I think :bind only accepts symbols or a strings.
Define the command as a function in your init or config section instead.
It might need to be in :preface, but yes, we do not support lambdas.
Could support for lambdas be added? It seems strange that :bind doesn't support it when global-set-key does. I usually use named functions for as much as I can, but for something as tiny as the one in the example, it seems like a lambda makes sense. :)
If that's not possible, it would be helpful if a note could be added to the docstrings and the guide. I spent probably half an hour trying to figure out why it works in global-set-key but not in :bind, because I thought :bind was supposed to be capable of everything global-set-key and bind-key do.
Thanks.
:bind is a convenience keyword for common patterns. At this time I don't plan to add lambdas, because then I would have to largely disable the error checking that we currently perform on bind patterns. I'll keep thinking about it, though.
Ah, well, that would be quite unfortunate! I have already come to appreciate the error checking use-package does. Oh well. :)
One thing I do wonder is if another syntax could allow this:
:bind (KEY . FUNCTION)
or
:bind (KEY FORM)
Where if FORM is not a lambda form, we automatically turn it into one.
However, this make the possibility of incorrectly diagnosed errors much higher. :(
I guess it's probably not worth it. If someone really wants a lambda that badly, they can do it in :config. Defined functions are probably better for keymaps anyway, because they make it easier to see what your binds do.
I know this is closed, but there are modes where you have a common behaviour that you then want to minimally change depending on the key. An example could be LaTEX. There you have different format macros and you may want to have a key sequence for italics, another for sans-serif, another for bold, etc. etc. Beofre using use-package, I had keymaps with:
(define-key "C-c fb" '(lambda() (interactive) <code for bold font>)
(define-key "C-c fi" '(lambda() (interactive) <code for italics>)
(define-key "C-c fs" '(lambda() (interactive) <code for sans>)
even
(define-key "M-t c" '(lambda() (interactive) <code for citation>)
with all that code refering to a single common function. Clean code, reusability, etc. as I suppose more than one of us has been taught when learning basic programming skills.
Beofre using use-package, I had keymaps with:
Nothing about use-package stops you from using that same code.
I really strongly desire to have lambdas in use-package.
Use-package is a huge convinience tool for cleaning up init files. But by not supporting lambdas, it creates a situation where I end up having to define functions in the global name-space that don't really need to be in the global name space.
This means that the convinence of use-package comes at the cost of name-space clutter.
Since lambdas are really a standard lisp idiom, not supporting them is also counter-intuitive.
I get the desire to have robust error checking. So maybe just have a separate key from :bind? :bind-lambdas maybe? The user then would be explicitely saying "hey -- I KNOW what I'm doing here, this isn't by accident!"
I'll add lambda support to :bind, just as :hook has it now.
I think the documentation needs to be updated?
Could I see an example where a lambda is used? I'm currently trying:
(use-package elisp-mode
:bind
(("C-c e s" . '(lambda () (switch-to-buffer "*scratch*"))))
Most helpful comment
I'll add lambda support to
:bind, just as:hookhas it now.