diff options
-rw-r--r-- | src/nvim/ex_docmd.c | 2 | ||||
-rw-r--r-- | src/nvim/ops.c | 33 | ||||
-rw-r--r-- | src/nvim/testdir/test_registers.vim | 85 | ||||
-rw-r--r-- | test/functional/provider/clipboard_spec.lua | 16 |
4 files changed, 110 insertions, 26 deletions
diff --git a/src/nvim/ex_docmd.c b/src/nvim/ex_docmd.c index 6e915d98dc..a140d76858 100644 --- a/src/nvim/ex_docmd.c +++ b/src/nvim/ex_docmd.c @@ -8160,7 +8160,7 @@ static void ex_operators(exarg_T *eap) case CMD_yank: oa.op_type = OP_YANK; - (void)op_yank(&oa, true, false); + (void)op_yank(&oa, true); break; default: // CMD_rshift or CMD_lshift diff --git a/src/nvim/ops.c b/src/nvim/ops.c index 3f51210781..23db7fe5a3 100644 --- a/src/nvim/ops.c +++ b/src/nvim/ops.c @@ -1572,20 +1572,20 @@ int op_delete(oparg_T *oap) yankreg_T *reg = NULL; int did_yank = false; if (oap->regname != 0) { - // yank without message - did_yank = op_yank(oap, false, true); - if (!did_yank) { - // op_yank failed, don't do anything + // check for read-only register + if (!valid_yank_reg(oap->regname, true)) { + beep_flush(); return OK; } + reg = get_yank_register(oap->regname, YREG_YANK); // yank into specif'd reg + op_yank_reg(oap, false, reg, is_append_register(oap->regname)); // yank without message + did_yank = true; } - /* - * Put deleted text into register 1 and shift number registers if the - * delete contains a line break, or when a regname has been specified. - */ - if (oap->regname != 0 || oap->motion_type == kMTLineWise - || oap->line_count > 1 || oap->use_reg_one) { + // Put deleted text into register 1 and shift number registers if the + // delete contains a line break, or when using a specific operator (Vi + // compatible) + if (oap->motion_type == kMTLineWise || oap->line_count > 1 || oap->use_reg_one) { shift_delete_registers(is_append_register(oap->regname)); reg = &y_regs[1]; op_yank_reg(oap, false, reg, false); @@ -2647,12 +2647,12 @@ void free_register(yankreg_T *reg) /// Yanks the text between "oap->start" and "oap->end" into a yank register. /// If we are to append (uppercase register), we first yank into a new yank /// register and then concatenate the old and the new one. +/// Do not call this from a delete operation. Use op_yank_reg() instead. /// /// @param oap operator arguments /// @param message show message when more than `&report` lines are yanked. -/// @param deleting whether the function was called from a delete operation. /// @returns whether the operation register was writable. -bool op_yank(oparg_T *oap, bool message, int deleting) +bool op_yank(oparg_T *oap, bool message) FUNC_ATTR_NONNULL_ALL { // check for read-only register @@ -2666,11 +2666,8 @@ bool op_yank(oparg_T *oap, bool message, int deleting) yankreg_T *reg = get_yank_register(oap->regname, YREG_YANK); op_yank_reg(oap, message, reg, is_append_register(oap->regname)); - // op_delete will set_clipboard and do_autocmd - if (!deleting) { - set_clipboard(oap->regname, reg); - do_autocmd_textyankpost(oap, reg); - } + set_clipboard(oap->regname, reg); + do_autocmd_textyankpost(oap, reg); return true; } @@ -6698,7 +6695,7 @@ void do_pending_operator(cmdarg_T *cap, int old_col, bool gui_yank) } else { curwin->w_p_lbr = lbr_saved; oap->excl_tr_ws = cap->cmdchar == 'z'; - (void)op_yank(oap, !gui_yank, false); + (void)op_yank(oap, !gui_yank); } check_cursor_col(); break; diff --git a/src/nvim/testdir/test_registers.vim b/src/nvim/testdir/test_registers.vim index ecc65b240b..f78b748d71 100644 --- a/src/nvim/testdir/test_registers.vim +++ b/src/nvim/testdir/test_registers.vim @@ -62,7 +62,6 @@ func Test_display_registers() call assert_match('^\nType Name Content\n' \ . ' c "" a\n' \ . ' c "0 ba\n' - \ . ' c "1 b\n' \ . ' c "a b\n' \ . '.*' \ . ' c "- a\n' @@ -85,6 +84,90 @@ func Test_display_registers() let g:clipboard = save_clipboard endfunc +func Test_register_one() + " delete a line goes into register one + new + call setline(1, "one") + normal dd + call assert_equal("one\n", @1) + + " delete a word does not change register one, does change "- + call setline(1, "two") + normal de + call assert_equal("one\n", @1) + call assert_equal("two", @-) + + " delete a word with a register does not change register one + call setline(1, "three") + normal "ade + call assert_equal("three", @a) + call assert_equal("one\n", @1) + + " delete a word with register DOES change register one with one of a list of + " operators + " % + call setline(1, ["(12)3"]) + normal "ad% + call assert_equal("(12)", @a) + call assert_equal("(12)", @1) + + " ( + call setline(1, ["first second"]) + normal $"ad( + call assert_equal("first secon", @a) + call assert_equal("first secon", @1) + + " ) + call setline(1, ["First Second."]) + normal gg0"ad) + call assert_equal("First Second.", @a) + call assert_equal("First Second.", @1) + + " ` + call setline(1, ["start here."]) + normal gg0fhmx0"ad`x + call assert_equal("start ", @a) + call assert_equal("start ", @1) + + " / + call setline(1, ["searchX"]) + exe "normal gg0\"ad/X\<CR>" + call assert_equal("search", @a) + call assert_equal("search", @1) + + " ? + call setline(1, ["Ysearch"]) + exe "normal gg$\"ad?Y\<CR>" + call assert_equal("Ysearc", @a) + call assert_equal("Ysearc", @1) + + " n + call setline(1, ["Ynext"]) + normal gg$"adn + call assert_equal("Ynex", @a) + call assert_equal("Ynex", @1) + + " N + call setline(1, ["prevY"]) + normal gg0"adN + call assert_equal("prev", @a) + call assert_equal("prev", @1) + + " } + call setline(1, ["one", ""]) + normal gg0"ad} + call assert_equal("one\n", @a) + call assert_equal("one\n", @1) + + " { + call setline(1, ["", "two"]) + normal 2G$"ad{ + call assert_equal("\ntw", @a) + call assert_equal("\ntw", @1) + + bwipe! +endfunc + func Test_recording_status_in_ex_line() norm qx redraw! diff --git a/test/functional/provider/clipboard_spec.lua b/test/functional/provider/clipboard_spec.lua index 986db96a18..5bdfec574e 100644 --- a/test/functional/provider/clipboard_spec.lua +++ b/test/functional/provider/clipboard_spec.lua @@ -50,29 +50,33 @@ local function basic_register_test(noblock) text, stuff and some more some some text, stuff and some more]]) - -- deleting a word to named ("a) updates "1 (and not "-) + -- deleting a word to named ("a) doesn't update "1 or "- feed('gg"adwj"1P^"-P') expect([[ , stuff and some more - some textsome some text, stuff and some more]]) + some some random text + some some text, stuff and some more]]) -- deleting a line does update "" feed('ggdd""P') expect([[ , stuff and some more - some textsome some text, stuff and some more]]) + some some random text + some some text, stuff and some more]]) feed('ggw<c-v>jwyggP') if noblock then expect([[ stuf - me t + me s , stuff and some more - some textsome some text, stuff and some more]]) + some some random text + some some text, stuff and some more]]) else expect([[ stuf, stuff and some more - me tsome textsome some text, stuff and some more]]) + me ssome some random text + some some text, stuff and some more]]) end -- pasting in visual does unnamed delete of visual selection |