Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for "surround copy (yank)" and "surround paste" #1325

Open
2 tasks done
thalesmello opened this issue Nov 6, 2024 · 4 comments
Open
2 tasks done

Add support for "surround copy (yank)" and "surround paste" #1325

thalesmello opened this issue Nov 6, 2024 · 4 comments
Labels
feature-request Request for a feature to existing module mini.surround

Comments

@thalesmello
Copy link

Contributing guidelines

Module(s)

mini.surround

Description

I was playing with my mini.surround config the other day, and I realized that occasionally I want to "copy" a surround, particularly complex ones like "f", and "paste" the same text in another piece of code.

Thinking about it conceptually, executing a command such as "syf" over a function call like vim.print(my_variable), so it would internally store { left = "vim.print(", right = ")" }. Then it should be possible to execute spiw over my_other_variable to get vim.print(my_other_variable).

I it a go in implement this feature, and it was easier to implement than I anticipated. If there's interest, I can format it and open a proper pull request.

@thalesmello thalesmello added the feature-request Request for a feature to existing module label Nov 6, 2024
@echasnovski
Copy link
Owner

Thanks for the suggestion!

This is indeed an interesting feature. In my mind it might be implemented a bit differently:

  • sy to yank text of surrounding into some fixed surrounding id (like y). This will populate both input and output of target surrounding.
  • Then "paste" is the same as add (saiwy), while also any other methods are usable.

One thing to consider here is that it will be a breaking feature:

  • It will require users who don't use default mappings (like LazyVim's gs and 'vim-surround' like keys) to update their config.
  • It will "take away" one surrounding id. So it might be a good idea to make it configurable, but not yet sure how.

All in all, I think this has good chances of being implemented. And in that case, I also would like to do this myself, if you don't mind.

@thalesmello
Copy link
Author

I quite like your idea of sy (surround yank) storing the the spec in a special character than can then be used with the other operators.

I gave it some thought overnight, and I think it would make the most sense to assign it to and then reading the spec from a register. This would require allowing termcodes as surrounds, but it has several benefits:

  • would have nice parity with how <c-r> works in insert mode
  • wouldn't break anyone's existing surrounds
  • it would allow people reassigning the special <c-r> to whatever config they like, via { custom_surrounds = { y = MiniSurround.spec_from_register } }
  • because it would work with registers ("asyf would store spec in register a), one could potentially keep surrounds in multiple registers for more complex macros

I updated my implementation to reflect my comment above.

A followup from your answer above:

This will populate both input and output of target surrounding

How would input be helpful with other operators (seemingly replace)?

All in all, I think this has good chances of being implemented. And in that case, I also would like to do this myself, if you don't mind.

All good man, whatever is easiest for you to maintain :)

@echasnovski
Copy link
Owner

My initial impression is that I don't really like the idea of mixing registers here. Can't really put that into words, though. Mostly a combination of "it introduces another abstraction", "register is for contiguous charwise/linewise/blockwise text region", and "requires more code", but maybe something else.

This will populate both input and output of target surrounding

How would input be helpful with other operators (seemingly replace)?

Same as user prompt and would find surrounding with that exact yanked left and right edges.

@thalesmello
Copy link
Author

thalesmello commented Nov 6, 2024

My initial impression is that I don't really like the idea of mixing registers here. Can't really put that into words, though. Mostly a combination of "it introduces another abstraction", "register is for contiguous charwise/linewise/blockwise text region", and "requires more code", but maybe something else.

I like registers (and so I'll likely stick with my fork), but implement it however you see fit :)

A suggestion that could be in the line of what you're thinking:

  • "surround yank" listens to an input char, then to an output char
  • the input char and its input spec will be used to find the surrounding
  • the found surrounding will be stored into the "output char"

e.g. sy)a will get the surrounding and assign it to MiniSurround.custom_surrounds.a = {output = {left="(", right=")"}, input=..}

This way, you only need to implement the "yank" operator, and it will automatically work with any other operator by using the recorded output char.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
feature-request Request for a feature to existing module mini.surround
Projects
None yet
Development

No branches or pull requests

2 participants