mirror of
https://github.com/vim/vim
synced 2025-07-16 01:01:58 +00:00
patch 8.2.4881: "P" in Visual mode still changes some registers
Problem: "P" in Visual mode still changes some registers. Solution: Make "P" in Visual mode not change any register. (Shougo Matsushita, closes #10349)
This commit is contained in:
committed by
Bram Moolenaar
parent
434725cc4c
commit
509142ab7a
@ -1177,14 +1177,15 @@ register. With blockwise selection it also depends on the size of the block
|
||||
and whether the corners are on an existing character. (Implementation detail:
|
||||
it actually works by first putting the register after the selection and then
|
||||
deleting the selection.)
|
||||
With 'p' the previously selected text is put in the unnamed register. This is
|
||||
useful if you want to put that text somewhere else. But you cannot repeat the
|
||||
same change.
|
||||
With 'P' the unnamed register is not changed, you can repeat the same change.
|
||||
But the deleted text cannot be used. If you do need it you can use 'p' with
|
||||
another register. E.g., yank the text to copy, Visually select the text to
|
||||
replace and use "0p . You can repeat this as many times as you like, and the
|
||||
unnamed register will be changed each time.
|
||||
With |p| the previously selected text is put in the unnamed register (and
|
||||
possibly the selection and/or clipboard). This is useful if you want to put
|
||||
that text somewhere else. But you cannot repeat the same change.
|
||||
With |P| the unnamed register is not changed (and neither the selection or
|
||||
clipboard), you can repeat the same change. But the deleted text cannot be
|
||||
used. If you do need it you can use |p| with another register. E.g., yank
|
||||
the text to copy, Visually select the text to replace and use "0p . You can
|
||||
repeat this as many times as you like, and the unnamed register will be
|
||||
changed each time.
|
||||
|
||||
When you use a blockwise Visual mode command and yank only a single line into
|
||||
a register, a paste on a visual selected area will paste that single line on
|
||||
|
@ -939,7 +939,7 @@ tag command note action in Visual mode ~
|
||||
|v_K| K run 'keywordprg' on the highlighted area
|
||||
|v_O| O move horizontally to other corner of area
|
||||
|v_P| P replace highlighted area with register
|
||||
contents; unnamed register is unchanged
|
||||
contents; registers are unchanged
|
||||
Q does not start Ex mode
|
||||
|v_R| R 2 delete the highlighted lines and start
|
||||
insert
|
||||
|
@ -265,7 +265,7 @@ Additionally the following commands can be used:
|
||||
X delete (2) |v_X|
|
||||
Y yank (2) |v_Y|
|
||||
p put |v_p|
|
||||
P put without unnamed register overwrite |v_P|
|
||||
P put without overwriting registers |v_P|
|
||||
J join (1) |v_J|
|
||||
U make uppercase |v_U|
|
||||
u make lowercase |v_u|
|
||||
|
18
src/normal.c
18
src/normal.c
@ -7236,8 +7236,7 @@ nv_put_opt(cmdarg_T *cap, int fix_indent)
|
||||
int was_visual = FALSE;
|
||||
int dir;
|
||||
int flags = 0;
|
||||
int save_unnamed = FALSE;
|
||||
yankreg_T *old_y_current, *old_y_previous;
|
||||
int keep_registers = FALSE;
|
||||
|
||||
if (cap->oap->op_type != OP_NOP)
|
||||
{
|
||||
@ -7284,7 +7283,7 @@ nv_put_opt(cmdarg_T *cap, int fix_indent)
|
||||
// overwrites if the old contents is being put.
|
||||
was_visual = TRUE;
|
||||
regname = cap->oap->regname;
|
||||
save_unnamed = cap->cmdchar == 'P';
|
||||
keep_registers = cap->cmdchar == 'P';
|
||||
#ifdef FEAT_CLIPBOARD
|
||||
adjust_clip_reg(®name);
|
||||
#endif
|
||||
@ -7302,26 +7301,15 @@ nv_put_opt(cmdarg_T *cap, int fix_indent)
|
||||
}
|
||||
|
||||
// Now delete the selected text. Avoid messages here.
|
||||
if (save_unnamed)
|
||||
{
|
||||
old_y_current = get_y_current();
|
||||
old_y_previous = get_y_previous();
|
||||
}
|
||||
cap->cmdchar = 'd';
|
||||
cap->nchar = NUL;
|
||||
cap->oap->regname = NUL;
|
||||
cap->oap->regname = keep_registers ? '_' : NUL;
|
||||
++msg_silent;
|
||||
nv_operator(cap);
|
||||
do_pending_operator(cap, 0, FALSE);
|
||||
empty = (curbuf->b_ml.ml_flags & ML_EMPTY);
|
||||
--msg_silent;
|
||||
|
||||
if (save_unnamed)
|
||||
{
|
||||
set_y_current(old_y_current);
|
||||
set_y_previous(old_y_previous);
|
||||
}
|
||||
|
||||
// delete PUT_LINE_BACKWARD;
|
||||
cap->oap->regname = regname;
|
||||
|
||||
|
@ -1390,34 +1390,74 @@ func Test_visual_paste()
|
||||
call assert_equal('x', @-)
|
||||
call assert_equal('bazooxxf', getline(1))
|
||||
|
||||
if has('clipboard')
|
||||
" v_P does not overwrite unnamed register.
|
||||
call setline(1, ['xxxx'])
|
||||
call setreg('"', 'foo')
|
||||
call setreg('-', 'bar')
|
||||
normal gg0vP
|
||||
call assert_equal('foo', @")
|
||||
call assert_equal('x', @-)
|
||||
call assert_equal('fooxxx', getline(1))
|
||||
normal $vP
|
||||
call assert_equal('foo', @")
|
||||
call assert_equal('x', @-)
|
||||
call assert_equal('fooxxfoo', getline(1))
|
||||
" Test with a different register as unnamed register.
|
||||
call setline(2, ['baz'])
|
||||
normal 2gg0"rD
|
||||
call assert_equal('baz', @")
|
||||
normal gg0vP
|
||||
call assert_equal('baz', @")
|
||||
call assert_equal('f', @-)
|
||||
call assert_equal('bazooxxfoo', getline(1))
|
||||
normal $vP
|
||||
call assert_equal('baz', @")
|
||||
call assert_equal('o', @-)
|
||||
call assert_equal('bazooxxfobaz', getline(1))
|
||||
endif
|
||||
|
||||
bwipe!
|
||||
endfunc
|
||||
|
||||
func Test_visual_paste_clipboard()
|
||||
CheckFeature clipboard_working
|
||||
|
||||
if has('gui')
|
||||
" auto select feature breaks tests
|
||||
set guioptions-=a
|
||||
endif
|
||||
|
||||
" v_P does not overwrite unnamed register.
|
||||
call setline(1, ['xxxx'])
|
||||
call setreg('"', 'foo')
|
||||
call setreg('-', 'bar')
|
||||
normal gg0vP
|
||||
call assert_equal('foo', @")
|
||||
call assert_equal('bar', @-)
|
||||
call assert_equal('fooxxx', getline(1))
|
||||
normal $vP
|
||||
call assert_equal('foo', @")
|
||||
call assert_equal('bar', @-)
|
||||
call assert_equal('fooxxfoo', getline(1))
|
||||
" Test with a different register as unnamed register.
|
||||
call setline(2, ['baz'])
|
||||
normal 2gg0"rD
|
||||
call assert_equal('baz', @")
|
||||
normal gg0vP
|
||||
call assert_equal('baz', @")
|
||||
call assert_equal('bar', @-)
|
||||
call assert_equal('bazooxxfoo', getline(1))
|
||||
normal $vP
|
||||
call assert_equal('baz', @")
|
||||
call assert_equal('bar', @-)
|
||||
call assert_equal('bazooxxfobaz', getline(1))
|
||||
|
||||
" Test for unnamed clipboard
|
||||
set clipboard=unnamed
|
||||
call setline(1, ['xxxx'])
|
||||
call setreg('"', 'foo')
|
||||
call setreg('-', 'bar')
|
||||
call setreg('*', 'baz')
|
||||
normal gg0vP
|
||||
call assert_equal('foo', @")
|
||||
call assert_equal('bar', @-)
|
||||
call assert_equal('baz', @*)
|
||||
call assert_equal('bazxxx', getline(1))
|
||||
|
||||
" Test for unnamedplus clipboard
|
||||
if has('unnamedplus')
|
||||
set clipboard=unnamedplus
|
||||
call setline(1, ['xxxx'])
|
||||
call setreg('"', 'foo')
|
||||
call setreg('-', 'bar')
|
||||
call setreg('+', 'baz')
|
||||
normal gg0vP
|
||||
call assert_equal('foo', @")
|
||||
call assert_equal('bar', @-)
|
||||
call assert_equal('baz', @+)
|
||||
call assert_equal('bazxxx', getline(1))
|
||||
endif
|
||||
|
||||
set clipboard&
|
||||
if has('gui')
|
||||
set guioptions&
|
||||
endif
|
||||
bwipe!
|
||||
endfunc
|
||||
|
||||
|
||||
" vim: shiftwidth=2 sts=2 expandtab
|
||||
|
@ -746,6 +746,8 @@ static char *(features[]) =
|
||||
|
||||
static int included_patches[] =
|
||||
{ /* Add new patch number below this line */
|
||||
/**/
|
||||
4881,
|
||||
/**/
|
||||
4880,
|
||||
/**/
|
||||
|
Reference in New Issue
Block a user