Fork me on GitHub
#emacs
<
2023-02-08
>
ag14:02:57

I need a quick and dirty piece of elisp that checks a string of code and figures out whether it's EDN or JSON. I'm thinking if I should even bother beyond checking the first couple of keys and if keywords, then that's Clojure. Probably would be good enough for most of my use cases. Even though it feels a bit stupid. Any better ideas, folks?

vemv14:02:53

try parsing it within a try/catch? remember there's parseedn.el or a little cleaner, grep for a ": ? I'd say that generally can only be json

馃憤 4
ag14:02:09

Yeah, probably the latter would be fast and good enough. Thanks!

ag14:02:35

Also, I didn't know about parseedn.el. Will check it out

pithyless20:02:03

Is anyone aware of a good way of rendering more vertical whitespace between top-level forms? Perhaps this is doable via some font-locking customization?

ag20:02:33

can you post a screenshot and expand on exactly what you mean, please? It's hard to grasp it without seeing it

pithyless20:02:43

File Contents:

(def foo)

(def bar)
Rendering:
(def foo)
 
 
(def bar)

pithyless20:02:16

I'm a fan of having two newlines per top-level form, and would like this rendering even when editing code that doesn't have this convention

ag20:02:47

I don't think that's possible. afaik there's no special text-property there to distinguish the beginning and end of the top form

pithyless20:02:54

I was thinking about how the asciidoc-mode changes font sizes for various headers; it would be cool if we could distinguish we're between top-level forms.

Benjamin C20:02:18

Maybe something treesitter could do?

ag20:02:18

Maybe, but you still have to traverse the file, find every top form and inject an overlay or a text-property

ag20:02:33

@U05476190 alternatively what you can do is to use form feed character and use page-break-lines.el, but you still have to manually insert them. Besides, that character still will show up in the source code.

ag20:02:06

you can write a function that inserts overlays, but you still gonna have to traverse and find every top form.

ag20:02:22

and run that function on some hook, like find-file-hook, etc.

pithyless20:02:24

Yeah, I suppose a different hack would be to run cljstyle to format all files (since it supports this kind of formatter out of the box). But then I'd need to make sure I can run e.g. magit such that it will ignore all whitespaces in status, diffs, etc.

馃憤 2
ag20:02:31

> I'd need to make sure I can run e.g. magit such that it will ignore all whitespaces "D -w" in magit-status

馃憤 4
pithyless20:02:14

It's just a quality of life improvement when reading code, so may not be worth the hassle. But I wanted to ask just in case there was an easy solution. Thanks for the input!

ag20:02:39

If I really, really wanted that, I'd probably use overlays. It's an interesting thing to hack on. I may even give it a try. But no promises.

pithyless20:02:59

I'm not familiar with overlays, but I'm assuming that's also what clojure-lsp uses for things like the code references? https://clojure-lsp.io/features/#code-lenses-showing-symbol-references

ericdallo20:02:43

yes, lsp-mode lens are overlays

ag20:02:01

yup. Also, if you ever used magit margins, in magit-log buffer, press L - that should toggle the margins - details about each commit. Those are also overlays. That's why you can't easily copy them out.

ag20:02:50

btw, about symbol references. @UKFSJSM38, you don't use Org-Roam do you? I've been wanting to have exactly the same feature that would show the number of backlinks for headings. But I can't find time to hack on it.

ericdallo20:02:41

I used some time ago, but I never get used, I think I'm just bad at organization 馃槀 anyway, I touched a good portion of lsp-mode code lens, specially the one that show code lens at the end of line and I love code lens, they are pretty fun.

ericdallo20:02:52

sounds like a nice feature for org-roam indeed

ericdallo20:02:33

https://emacs-lsp.github.io/lsp-dart/#flutter-widget-guides is another cool feature I did with overlays for lsp-dart, pretty fun, those lines

vemv20:02:57

There's (setq-local line-spacing 20) but it's global, it doesn't know what a top-level form is I have a custom command that temporarily collapses all forms and increases the line spacing:

vemv20:02:04

it's my poor man's ns outline

ag20:02:28

why not use imenu?

ag20:02:46

or lsp-treemacs

vemv20:02:57

because I'm poor 馃槆

ag20:02:50

I mean... why am I even asking? It's inappropriate and rude to ask "why do you do X in Emacs?"... "well, because I want to and I can... isn't that obvious?"

馃挴 4
馃槄 2
emacs-spin 2
vemv20:02:28

I wish there was a :emacs-spin: emoji clojure-spin

ag20:02:28

Emacs doesn't spin. When it does, we do pkill -SIGUSR2

2
ag21:02:29

What? You guys really have too much time to fiddle around, heh? Have you switched to VSCode or something? I've heard that using Emacs is so taxing, you need to constantly tweak it, whenever you have a minute.

馃槀 4
ericdallo21:02:59

yeah, was one of the weekly org-roam tasks 馃槀

ag21:02:51

I spent whole twenty minutes today figuring out how to test REST APIs but instead of sending and receiving json, it would work with edn. No job was done in those twenty minutes. I should've used VSCode, where "everything works". And I wouldn't even dare to dream about not staring into json.

emacs-spin 2
Benjamin15:02:40

(defface lisp-large-top-level-whitespace-overlay-face
  '((t (:inherit default :height 1.5)))
  "Face for the space between toplevel forms")

(defun lisp-large-toplevel-whitespace-remove ()
  (interactive)
  (remove-overlays nil nil 'category 'lisp-large-toplevel))

;; there is a "bug", if you have a comment right above the form
;; you want to move back to the nearest empty line ?
(defun lisp-large-toplevel-whitespace-render ()
  (interactive)
  (lisp-large-toplevel-whitespace-remove)
  (save-excursion
    (goto-char (point-min))
    (while (not (eobp))
      (forward-list)
      (save-excursion
        (beginning-of-defun)
        (forward-line -1)
        (when (looking-at-p "$")
          (let ((ov (make-overlay (point) (1+ (point)))))
            (overlay-put ov 'face 'lisp-large-top-level-whitespace-overlay-face)
            (overlay-put ov 'category 'lisp-large-toplevel)))))))
Every hour I spend fiddleling with emacs payed of. Now I can render vertical space where when I decide to do so emacs-spin

Benjamin15:02:55

better picture showcasing the effect

馃帀 2
ag17:02:53

That's awesome! Looks great. I may steal this into my config.

鈽猴笍 2
Benjamin17:02:56

it doesn't detect if there is only a single empty line right now. Maybe another unless with (looking-back "^$") or something would do that

ag21:02:30

ah, shit... yes, a while ago I struggled with a similar problem. I got annoyed that when I'd kill empty lines it would place them in the kill ring. That absurdly annoyed me, I don't know, I have OCD or something. And I just couldn't get the regexp right.

pithyless05:02:19

Very cool @U02CV2P4J6S! Bookmarked and will try it over the weekend. Thanks a lot!

馃槢 2
Benjamin08:02:18

@U0G75ARHC

(advice-add
 #'consult-yank-pop
 :before
 (defun mm/remove-whitespace-only-from-kill-ring (&rest args)
   (setf kill-ring (cl-remove-if #'s-blank-str? kill-ring))))
for me I only felt this pain when I doing yank pop (useless empty lines, sometimes many). I guess the more radical way is to advice kill-new