vim

sheluchin 2022-10-21T11:16:31.458659Z

I wish there was a way to evaluate just the form under the cursor in a let form without having to comment out the siblings. Like this, where | is the cursor position.:

(let [k :foo]
 (x k)
 (y |k)
 (z k))
To do it now the x and z lines need to get commented out. It's just a lot of extra operations. vim-iced's https://liquidz.github.io/vim-iced/#evaluate_in_context really helps, but sometimes a let form can be more convenient, especially when you need to set up a large context.

emilaasa 2022-10-21T13:10:36.657739Z

Which flavor of repl integration are you using?

sheluchin 2022-10-21T13:23:06.535749Z

@emilaasa vim-iced uses CIDER nREPL.

Martynas Maciulevičius 2022-10-21T19:05:07.437649Z

Actually you could write this in Clojure šŸ¤” Cider nREPL is Clojure so... there is nothing that prevents you to take that form and remove all sibling forms to get the output you want šŸ¤”

🤯 1
sheluchin 2022-10-21T19:08:04.912009Z

That had never occurred to me at all. I was thinking of maybe trying to hack something together modelled after https://github.com/liquidz/vim-iced/blob/main/autoload/iced/nrepl/eval.vim#L280-L282, but I barely know vimscript at all. @invertisment_clojuria do you happen to know of an example of your suggested approach out there somewhere?

Martynas Maciulevičius 2022-10-21T19:09:53.634569Z

I don't have an example and I don't use vim-iced. Instead I use Conjure and I wrote my own small plugin for Conjure (yes, it's weird) that interacts with nREPL tests. I suggest to look how vim-iced evaluates top-level form and then wrap this form into your macro or a function. And only then send to REPL to evaluate. This way you would control the output.

sheluchin 2022-10-21T19:12:37.735299Z

iced does some similar logic for comment blocks, where it either only evals the form under the cursor or treats the whole comment as a do if the cursor isn't inside a form. That's what I was thinking of as a starting point.

Martynas Maciulevičius 2022-10-21T19:13:51.533459Z

Basically I suggest to you to write a code block that would take this data structure and format it so that it would simply be a chunk of Clojure code. For instance this is a string that my plugin sends to nREPL to do something. So nothing prevents you to take the ns-level form and insert it into this kind of string: https://github.com/Invertisment/conjure-clj-additions-cider-nrepl-mw/blob/master/fnl/conjure-clj-additions-nrepl/additional-fns.fnl#L43 (this is fennel -- a weird clojure-lisp-like layer on top of lua) Unfortunately I don't have examples that use vim-iced.

sheluchin 2022-10-21T19:18:16.913859Z

If I understand correctly, the goal is to be able to get the current form as a string along with the cursor position within it, and re-write the string into some other valid Clojure form before sending it to the nREPL for eval?

Martynas Maciulevičius 2022-10-21T19:18:18.749819Z

What's more interesting is that you'll need to represent a cursor in some way. So probably it would be a good idea to use update-in syntax for it. I imagine this has to be twothree-step algorithm: 1. get the outer let 2. get path to the form that the cursor is in that is immediate child to let 3. remove later children (you probably want to preserve earlier children)

Martynas Maciulevičius 2022-10-21T19:21:15.764549Z

> get the current form as a string along with the cursor position within it You'll already be able to get the string. But you'll need to send a clojure code chunk to nREPL. So in this position you'd need to do string formatting. And then in that string you'll have to call edn/read-string because you'll be inserting a string into your valid clojure code. Your clojure code will be parsed by the middleware of the plugin but the inserted code chunk will still be in the string form. And after you do it you'll need to do the actual algorithmic work.

Martynas Maciulevičius 2022-10-21T19:21:28.260499Z

Also you'll need to send the cursor position as well

Martynas Maciulevičius 2022-10-21T19:22:24.505659Z

And somehow not mess up where it is. So probably you'll need to also send the starting position of the form so that you'd be able to calculate where the cursor is

Martynas Maciulevičius 2022-10-21T19:23:15.132839Z

I marked those with X:

(defn other-form-that-could-mess-it-up [])

Xlet [k :foo]
 (x k)
 (y Xk)
 (z k))

Martynas Maciulevičius 2022-10-21T19:26:00.910919Z

The more I talk the more complicated it looks šŸ˜… Basically -- if you do it then don't do it in vimscript, do it in Clojure only.

sheluchin 2022-10-21T19:26:39.528379Z

I don't understand that part. I don't get how to go from vim-iced's vimscript to nREPL's clj.

sheluchin 2022-10-21T19:27:58.942439Z

There are a bunch of nice helper functions here that help select some parts of the form: https://github.com/liquidz/vim-iced/blob/main/autoload/iced/paredit.vim but then how to move from there to writing Clojure is not clear.

Martynas Maciulevičius 2022-10-21T19:28:22.558489Z

When you evaluate a form you send the form to nREPL. So what I explain is to send more code.

sheluchin 2022-10-21T19:29:15.277659Z

But the payload formation is all in vimscript, right?

Martynas Maciulevičius 2022-10-21T19:29:35.169829Z

Unfortunately yes

Martynas Maciulevičius 2022-10-21T19:29:51.572859Z

But it's mostly "get cursor, get form position, put it all into a long string"

sheluchin 2022-10-21T19:35:54.087529Z

Okay, makes sense. Yeah, it looks kinda doable, especially using those helper functions that are available. I'll give it a shot sometime. Thanks for the tips, @invertisment_clojuria.

Martynas Maciulevičius 2022-10-21T19:37:37.243909Z

Yeah, I didn't know if something like this exists and I didn't offer an easy way out. But it's something.