From 4a2feecd03ce98e247fce5267534775718440c83 Mon Sep 17 00:00:00 2001 From: Josh Rahm Date: Mon, 12 Sep 2022 14:38:51 -0600 Subject: charadd.vim: add ability to increment/decrement to characters in a text object. adds cx, cxx, cX, cXX, cgx, cgxx, cgX, cgXX which is [count]c[g](x|X) add/subtract v:count to each codepoint in the given text motion. if g is present, modify /all/ codepoints if g is not present, modify only non-space codepoints if X is used, subtract v:count from each codepoint if x is used, add v:count to each codepoint if x or X is repeated, operate on the line. repeatable with '.' --- plugin/charadd.vim | 65 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 65 insertions(+) create mode 100644 plugin/charadd.vim (limited to 'plugin') diff --git a/plugin/charadd.vim b/plugin/charadd.vim new file mode 100644 index 0000000..b8d25bf --- /dev/null +++ b/plugin/charadd.vim @@ -0,0 +1,65 @@ +" Add/substracts a number from all the characters in a text object. +" +" [count]cx - increment all the characters in the text object by count, +" except whitespace +" [count]cX - decrement all characters in the text object by count, except +" whitespace +" [count]cgx - like cx, but include whitespace characters +" [count]cgX - like cX, but include whitespace characters +" +" The following convinence functions are added +" +" cxx, cXX, cgxx, cgXX to operate on lines. +" + +noremap cx call set_dir(v:count1,0)set operatorfunc=charaddg@ +nnoremap cxx call set_dir(v:count1,0)set operatorfunc=charaddg@_ +noremap cX call set_dir(-v:count1,0)set operatorfunc=charaddg@ +nnoremap cXX call set_dir(-v:count1,0)set operatorfunc=charaddg@_ + + +noremap cgx call set_dir(v:count1,1)set operatorfunc=charaddg@ +nnoremap cgxx call set_dir(v:count1,1)set operatorfunc=charaddg@_ +noremap cgX call set_dir(-v:count1,1)set operatorfunc=charaddg@ +nnoremap cgXX call set_dir(-v:count1,1)set operatorfunc=charaddg@_ + +let s:dir = 1 +let s:incl = 0 +function! s:set_dir(d, i) abort + let s:dir = a:d + let s:incl = a:i +endfunction + +function! s:charadd(arg, ...) abort + let save_a = getreg('a') + let save_a_type = getregtype('a') + + if a:0 + echo a:1 + let vis = '`<' . a:arg . '`>' + elseif a:arg == 'line' + let vis = "'[V']" + elseif a:arg == 'block' + let vis = "`[\`]" + else + let vis = "`[v`]" + endif + + silent! exec printf("norm! %s\"ay", vis) + let r = getreg('a', 1) + let rtyp = getregtype('a') + + let nl = "" + for c in r + if s:incl || ! (c =~ '\_s') + let n = char2nr(c) + let nl .= nr2char(n + s:dir) + else + let nl .= c + endif + endfor + + call setreg('a', nl, rtyp) + silent! exec printf("norm! gv\"ap`[") + call setreg('a', save_a, save_a_type) +endfunction -- cgit