3

As is well known, di( deletes the contents inside a () block. When the cursor is not within a group of (), the cursor jumps to the near () group and delete the contents in it.

Is there any way to disable this jumping?

Namely, if the cursor is not within a group, then just do nothing.

3
  • 1
    This is rather funny because i( didn't work like that for a long time and people have been asking for and writing plugins to fix the discrepancy between i" and i( for decades. Now that the default behavior has been changed to match user expectations, people are starting to ask for the original behavior. I guess one could take one of the old workarounds and reverse it?
    – romainl
    Commented Jun 22, 2023 at 18:34
  • @romainl but hey, Vim is my editor, not everyone's editor :)
    – Futarimiti
    Commented Jun 23, 2023 at 10:10
  • @goaqiang, how can we help you further? Do you have something open in your question? If not maybe could you accept an answer using the v button next to the arrow voting buttons. It allow the question to rest :-) Commented Jun 23, 2023 at 18:48

1 Answer 1

2

I would do:

nnoremap <expr> di( (searchpairpos('(', '', ')', 'n') == [0, 0] ? '' : 'di(')

The searchpairpos('(', '', ')', 'n') call searches for a matching pair without moving the cursor (the n flag). If it doesn't find a matching pair it returns [0, 0]

The mapping map the di( to:

  • the empty string if no matching is pair is found,
  • di( otherwise

As suggested by @filbranden another solution would be to onoremap to make it working for all the verbs (d, y and c) you could do:

onoremap <expr> i( (searchpairpos('(', '', ')', 'n') == [0, 0] ? '\<Esc>' : 'i(')

In order to make it work for v you could do:

xnoremap <expr> i( (searchpairpos('(', '', ')', 'n') == [0, 0] ? '\<Esc>' : 'i(')

Remark: Both mappings work fine with count (e.g. 2di()

2
  • 1
    I think this solution could be improved by using an onoremap <expr> i( to have the i( text object work in all contexts, not only after d, and a corresponding xnoremap i( to have it also work in Visual mode. There's also other possibly relevant corner cases, such as passing a count, also considering similar text objects such as a( and possible synonyms such as i) and a) (though maybe those could be left with the original behavior?) This is a great start, but as usual, it's a lot of work to make things really robust in Vimscript :-)
    – filbranden
    Commented Jun 23, 2023 at 15:27
  • 1
    @filbranden, thanks for the feedback. I'll try my best :-) Commented Jun 23, 2023 at 15:42

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.