Hello
This is a request for comments about a little utility I’ve been
working on.
I’ve created a mode (which is not finished just yet), which deals with
comments in Clojure(Script) mode. It is very much inspired by
comment-dwim-2
, in that when you have something like this:
█(ns foo.bar
(:require [foo.baz]))
and you M-x clojure-comment-dwim
it turns the code into:
#_(ns foo.bar
(:require [foo.baz]))
`
then when you invoke the function again, it changes the comment style
to:
;;(ns foo.bar
(:require [foo.baz]))
Yes, that does mess up the parens, but then it’s up to you what
particular style of comment is appropriate.
And a final tweak is that if you turn off
clojure-comment-dwim-ignore-trailing-comment
it allows you to have
trailing comments:
(ns foo.bar ;
(:require [foo.baz]))
What I’m wondering is if instead of the behaviour above, which cycles
through the different comment types, it can comment out the form
following it. For example, with the code like this where the cursor is
just after the ns
:
(ns█foo.bar
(:require [foo.baz]))
by invoking clojure-comment-dwim
, it should insert #_
, so that you get:
(ns #_foo.bar
(:require [foo.baz]))
And then the subsequent invocations should have the already existing
behaviour described above, where the comment is inserted at the
beginning of line.
What are your thoughts on this? Thanks
Repo of the mode so far (which is not yet finished):
https://github.com/dotemacs/clojure-comment-dwim.elI’ve implemented the functionality where you can (un)comment #_
, uncomment (comment ...)
and when a region is selected, comment with (comment ...), all under a *single function*. With a prefix argument
C-u n` you can go up n
s-expressions from point, and comment them out.
There’s bound to be some edge cases and tests need to be added to prevent regressions, but it works so far. (Yes, there is some duplication and I intend on cleaning that up).
See what you think (note, the new changes are in s-expressions-only
branch):
https://github.com/dotemacs/clojure-comment-dwim.el/blob/s-expressions-only/clojure-comment-dwim.el
I like being able to comment out multiple forms using the numeric argument, which comes up surprisingly often in clojure due to "pairs" in maps and binding forms:
C-u 4 clojure-toggle-ignore-form =>
{a 1 #_#_#_#_ b 2 c 3 d 4}
Are you thinking of submitting it to clojure-mode or a MELPA package? I've been planning to contribute my above snippet to clojure-mode too, seeing as Calva added a similar feature recently 🙂
I’ve put a bunch of scenarios in this issue, along with the discussion on the prefix argument behaviour: https://github.com/dotemacs/clojure-comment-dwim.el/issues/2
Looks like you put a lot of thought into this! I think a lot of this comes down to personal preference and workflow habits - different users will prefer having multiple specific commands vs. having a single command with context-sensitive or cycling behaviour.
In any case it seems that some sort of #_
command should belong in the main clojure-mode package for everyone's benefit.
I'll open an issue on the clojure-mode repo to get feedback, hope you don't mind if I link to your repo in its current state
Just sharing my thoughts and workflow. I would like to see a clojure-mode function that just toggles #_ on the current expression, preferably without having to use C-u argument. I have some code I someone wrote for me a year or so ago, which I just bind to C-# and it does the trick. It's Evil aware so it works with Spacemacs. There are already several ways to toggle ;; style comments for lines and regions (certainly in Spacemacs) I only use one comment block per namespace, so toggling would be of no value to me. I think there is a (comment ) yasnippet (or its really easy to add one.
Thanks for the feedback @jr0cket.
> I would like to see a clojure-mode function that just toggles #_ on the current expression, preferably without having to use C-u argument.
I’ve got that covered right now in clojure-comment-dwim.el
.
But if you select a region, it figures out if this region is a s-expression, in which case it still uses #_
, otherwise if it isn’t a s-expression, it wraps it in (comment ...)
.
> It’s Evil aware so it works with Spacemacs.
Not sure how Evil/Spacemacs works, as I don’t use it, but I assume that it just invokes Elisp functions bound to a certain key(combo)?
> There are already several ways to toggle ;; style comments for lines and regions (certainly in Spacemacs)
comment-dwim
as part of stock Emacs does this.
The main issue I have with your implementation is that #_
and comment
forms are semantically very different in the way they're commonly used. Treating them as equivalent and choosing which to use based on some heuristic would encourage bad style.
OK, so let me understand that better, how would you comment out a section of the code here:
{:a 1
:b 2
:c 3}
If you selected the region containing :b 2
, what would be your preference @qythium?
Something like:
a)
{:a 1
#_ :b #_2
:c 3}
b)
{:a 1
#_ #_ :b 2
:c 3}
c)
{:a 1
#_(:b 2)
:c 3}
Or just standard comment-dwim
style:
d)
{:a 1
;; :b 2
:c 3}
hey sorry for the late reply, I would use option b
For me comment
is reserved mostly for top-level comment forms, ie. temporary test code or things that are meant to be executed interactively, and ;;
line comments are for text
In your example @dotemacs option b would be the result I expect to see (although comments in maps is not an approach I would typically use).
The only time I seem to use the #_
comment within an expression is in a threading macro, where I would expect a single #_
would comment out the part of the execution pipeline I wanted to exclude. I guess it could also be useful in cond too, but don't really use that much.
Thank you both for the feedback!
I don't understand the utility of cycling to a ;;
comment and unbalancing parens in the process - I imagine most of the time it's a 2-state toggle between inserting and deleting #_
, so having a 3rd state seems like more unneccessary steps
here's the function I use for that purpose, which also has some other "dwim" behaviour like wrapping in a comment
form when a region is selected:
https://gist.github.com/yuhan0/38ac43c764017917fc3f3e5dc9104f1b
Thanks for the feedback @qythium. It was influenced by comment-dwim-2
, which acts this way.
I like what you’ve done with your gist.
I had another idea, after your feedback, for any given point, if the command is invoked, insert #_
even if it’s in a middle of a s-expression. Then the function is invoked again, uncomment it.
With an argument supplied, go up a s-expression and (un)comment.
And I like your idea of using comment
on the region, but I’ll try to borrow from your approach and comment-dwim-2
’s, in applying it against a region, but not from just a “starting” & “ending” points, but for the s-expressions within the region.
Thanks again