vim-patch:7.4.2268

Problem:    Using CTRL-N and CTRL-P for incsearch shadows completion keys.
Solution:   Use CTRL-T and CTRL-G instead.

1195669f9e
This commit is contained in:
James McCoy
2017-06-25 11:01:16 -04:00
parent 518b42db91
commit 0dd6455659
5 changed files with 149 additions and 140 deletions

View File

@@ -376,18 +376,10 @@ CTRL-D List names that match the pattern in front of the cursor.
*c_CTRL-N*
CTRL-N After using 'wildchar' which got multiple matches, go to next
match. Otherwise recall more recent command-line from history.
*/_CTRL-N*
When 'incsearch' is set, entering a search pattern for "/" or
"?" and the current match is displayed then CTRL-N will move
to the next match (does not take |search-offset| into account)
<S-Tab> *c_CTRL-P* *c_<S-Tab>*
CTRL-P After using 'wildchar' which got multiple matches, go to
previous match. Otherwise recall older command-line from
history. <S-Tab> only works with the GUI.
*/_CTRL-P*
When 'incsearch' is set, entering a search pattern for "/" or
"?" and the current match is displayed then CTRL-P will move
to the previous match (does not take |search-offset| into account).
*c_CTRL-A*
CTRL-A All names that match the pattern in front of the cursor are
inserted.
@@ -404,6 +396,19 @@ CTRL-L A match is done on the pattern in front of the cursor. If
'ignorecase' and 'smartcase' are set and the command line has
no uppercase characters, the added character is converted to
lowercase.
*c_CTRL-G* */_CTRL-G*
CTRL-G When 'incsearch' is set, entering a search pattern for "/" or
"?" and the current match is displayed then CTRL-G will move
to the next match (does not take |search-offset| into account)
Use CTRL-T to move to the previous match. Hint: on a regular
keyboard T is above G.
*c_CTRL-T* */_CTRL-T*
CTRL-T When 'incsearch' is set, entering a search pattern for "/" or
"?" and the current match is displayed then CTRL-T will move
to the previous match (does not take |search-offset| into
account).
Use CTRL-G to move to the next match. Hint: on a regular
keyboard T is above G.
The 'wildchar' option defaults to <Tab> (CTRL-E when in Vi compatible mode; in
a previous version <Esc> was used). In the pattern standard wildcards '*' and

View File

@@ -1282,72 +1282,12 @@ static int command_line_handle_key(CommandLineState *s)
case Ctrl_N: // next match
case Ctrl_P: // previous match
if (p_is && !cmd_silent && (s->firstc == '/' || s->firstc == '?')) {
pos_T t;
int search_flags = SEARCH_KEEP + SEARCH_NOOF + SEARCH_PEEK;
if (char_avail()) {
return 1;
}
ui_busy_start();
ui_flush();
if (s->c == Ctrl_N) {
t = s->match_end;
search_flags += SEARCH_COL;
} else {
t = s->match_start;
}
emsg_off++;
s->i = searchit(curwin, curbuf, &t,
s->c == Ctrl_N ? FORWARD : BACKWARD,
ccline.cmdbuff, s->count, search_flags,
RE_SEARCH, 0, NULL);
emsg_off--;
ui_busy_stop();
if (s->i) {
s->old_cursor = s->match_start;
s->match_end = t;
s->match_start = t;
if (s->c == Ctrl_P && s->firstc == '/') {
// move just before the current match, so that
// when nv_search finishes the cursor will be
// put back on the match
s->old_cursor = t;
(void)decl(&s->old_cursor);
}
if (lt(t, s->old_cursor) && s->c == Ctrl_N) {
// wrap around
s->old_cursor = t;
if (s->firstc == '?') {
(void)incl(&s->old_cursor);
} else {
(void)decl(&s->old_cursor);
}
}
set_search_match(&s->match_end);
curwin->w_cursor = s->match_start;
changed_cline_bef_curs();
update_topline();
validate_cursor();
highlight_match = true;
s->old_curswant = curwin->w_curswant;
s->old_leftcol = curwin->w_leftcol;
s->old_topline = curwin->w_topline;
s->old_topfill = curwin->w_topfill;
s->old_botline = curwin->w_botline;
update_screen(NOT_VALID);
redrawcmdline();
} else {
vim_beep(BO_ERROR);
}
return command_line_not_changed(s);
} else if (s->xpc.xp_numfiles > 0) {
if (s->xpc.xp_numfiles > 0) {
if (nextwild(&s->xpc, (s->c == Ctrl_P) ? WILD_PREV : WILD_NEXT,
0, s->firstc != '@') == FAIL) {
break;
}
return command_line_changed(s);
return command_line_not_changed(s);
}
// fallthrough
@@ -1488,6 +1428,70 @@ static int command_line_handle_key(CommandLineState *s)
beep_flush();
return command_line_not_changed(s);
case Ctrl_G: // next match
case Ctrl_T: // previous match
if (p_is && !cmd_silent && (s->firstc == '/' || s->firstc == '?')) {
pos_T t;
int search_flags = SEARCH_KEEP + SEARCH_NOOF + SEARCH_PEEK;
if (char_avail()) {
return 1;
}
ui_busy_start();
ui_flush();
if (s->c == Ctrl_G) {
t = s->match_end;
search_flags += SEARCH_COL;
} else {
t = s->match_start;
}
emsg_off++;
s->i = searchit(curwin, curbuf, &t,
s->c == Ctrl_G ? FORWARD : BACKWARD,
ccline.cmdbuff, s->count, search_flags,
RE_SEARCH, 0, NULL);
emsg_off--;
ui_busy_stop();
if (s->i) {
s->old_cursor = s->match_start;
s->match_end = t;
s->match_start = t;
if (s->c == Ctrl_T && s->firstc == '/') {
// move just before the current match, so that
// when nv_search finishes the cursor will be
// put back on the match
s->old_cursor = t;
(void)decl(&s->old_cursor);
}
if (lt(t, s->old_cursor) && s->c == Ctrl_G) {
// wrap around
s->old_cursor = t;
if (s->firstc == '?') {
(void)incl(&s->old_cursor);
} else {
(void)decl(&s->old_cursor);
}
}
set_search_match(&s->match_end);
curwin->w_cursor = s->match_start;
changed_cline_bef_curs();
update_topline();
validate_cursor();
highlight_match = true;
s->old_curswant = curwin->w_curswant;
s->old_leftcol = curwin->w_leftcol;
s->old_topline = curwin->w_topline;
s->old_topfill = curwin->w_topfill;
s->old_botline = curwin->w_botline;
update_screen(NOT_VALID);
redrawcmdline();
} else {
vim_beep(BO_ERROR);
}
}
return command_line_not_changed(s);
case Ctrl_V:
case Ctrl_Q:
s->ignore_drag_release = true;

View File

@@ -18,11 +18,11 @@ func Test_search_cmdline()
call feedkeys("/foobar\<cr>", 'tx')
call feedkeys("/the\<cr>",'tx')
call assert_equal('the', @/)
call feedkeys("/thes\<c-p>\<c-p>\<cr>",'tx')
call feedkeys("/thes\<C-P>\<C-P>\<cr>",'tx')
call assert_equal('foobar', @/)
" Test 2
" Ctrl-N goes from one match to the next
" Ctrl-G goes from one match to the next
" until the end of the buffer
set incsearch nowrapscan
:1
@@ -31,39 +31,39 @@ func Test_search_cmdline()
call assert_equal(' 2 these', getline('.'))
:1
" second match
call feedkeys("/the\<c-n>\<cr>", 'tx')
call feedkeys("/the\<C-G>\<cr>", 'tx')
call assert_equal(' 3 the', getline('.'))
:1
" third match
call feedkeys("/the".repeat("\<c-n>", 2)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 2)."\<cr>", 'tx')
call assert_equal(' 4 their', getline('.'))
:1
" fourth match
call feedkeys("/the".repeat("\<c-n>", 3)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 3)."\<cr>", 'tx')
call assert_equal(' 5 there', getline('.'))
:1
" fifth match
call feedkeys("/the".repeat("\<c-n>", 4)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 4)."\<cr>", 'tx')
call assert_equal(' 6 their', getline('.'))
:1
" sixth match
call feedkeys("/the".repeat("\<c-n>", 5)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 5)."\<cr>", 'tx')
call assert_equal(' 7 the', getline('.'))
:1
" seventh match
call feedkeys("/the".repeat("\<c-n>", 6)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 6)."\<cr>", 'tx')
call assert_equal(' 8 them', getline('.'))
:1
" eigth match
call feedkeys("/the".repeat("\<c-n>", 7)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 7)."\<cr>", 'tx')
call assert_equal(' 9 these', getline('.'))
:1
" no further match
call feedkeys("/the".repeat("\<c-n>", 8)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 8)."\<cr>", 'tx')
call assert_equal(' 9 these', getline('.'))
" Test 3
" Ctrl-N goes from one match to the next
" Ctrl-G goes from one match to the next
" and continues back at the top
set incsearch wrapscan
:1
@@ -72,39 +72,39 @@ func Test_search_cmdline()
call assert_equal(' 2 these', getline('.'))
:1
" second match
call feedkeys("/the\<c-n>\<cr>", 'tx')
call feedkeys("/the\<C-G>\<cr>", 'tx')
call assert_equal(' 3 the', getline('.'))
:1
" third match
call feedkeys("/the".repeat("\<c-n>", 2)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 2)."\<cr>", 'tx')
call assert_equal(' 4 their', getline('.'))
:1
" fourth match
call feedkeys("/the".repeat("\<c-n>", 3)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 3)."\<cr>", 'tx')
call assert_equal(' 5 there', getline('.'))
:1
" fifth match
call feedkeys("/the".repeat("\<c-n>", 4)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 4)."\<cr>", 'tx')
call assert_equal(' 6 their', getline('.'))
:1
" sixth match
call feedkeys("/the".repeat("\<c-n>", 5)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 5)."\<cr>", 'tx')
call assert_equal(' 7 the', getline('.'))
:1
" seventh match
call feedkeys("/the".repeat("\<c-n>", 6)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 6)."\<cr>", 'tx')
call assert_equal(' 8 them', getline('.'))
:1
" eigth match
call feedkeys("/the".repeat("\<c-n>", 7)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 7)."\<cr>", 'tx')
call assert_equal(' 9 these', getline('.'))
:1
" back at first match
call feedkeys("/the".repeat("\<c-n>", 8)."\<cr>", 'tx')
call feedkeys("/the".repeat("\<C-G>", 8)."\<cr>", 'tx')
call assert_equal(' 2 these', getline('.'))
" Test 4
" CTRL-P goes to the previous match
" CTRL-T goes to the previous match
set incsearch nowrapscan
$
" first match
@@ -112,23 +112,23 @@ func Test_search_cmdline()
call assert_equal(' 9 these', getline('.'))
$
" first match
call feedkeys("?the\<c-n>\<cr>", 'tx')
call feedkeys("?the\<C-G>\<cr>", 'tx')
call assert_equal(' 9 these', getline('.'))
$
" second match
call feedkeys("?the".repeat("\<c-p>", 1)."\<cr>", 'tx')
call feedkeys("?the".repeat("\<C-T>", 1)."\<cr>", 'tx')
call assert_equal(' 8 them', getline('.'))
$
" last match
call feedkeys("?the".repeat("\<c-p>", 7)."\<cr>", 'tx')
call feedkeys("?the".repeat("\<C-T>", 7)."\<cr>", 'tx')
call assert_equal(' 2 these', getline('.'))
$
" last match
call feedkeys("?the".repeat("\<c-p>", 8)."\<cr>", 'tx')
call feedkeys("?the".repeat("\<C-T>", 8)."\<cr>", 'tx')
call assert_equal(' 2 these', getline('.'))
" Test 5
" CTRL-P goes to the previous match
" CTRL-T goes to the previous match
set incsearch wrapscan
$
" first match
@@ -136,19 +136,19 @@ func Test_search_cmdline()
call assert_equal(' 9 these', getline('.'))
$
" first match at the top
call feedkeys("?the\<c-n>\<cr>", 'tx')
call feedkeys("?the\<C-G>\<cr>", 'tx')
call assert_equal(' 2 these', getline('.'))
$
" second match
call feedkeys("?the".repeat("\<c-p>", 1)."\<cr>", 'tx')
call feedkeys("?the".repeat("\<C-T>", 1)."\<cr>", 'tx')
call assert_equal(' 8 them', getline('.'))
$
" last match
call feedkeys("?the".repeat("\<c-p>", 7)."\<cr>", 'tx')
call feedkeys("?the".repeat("\<C-T>", 7)."\<cr>", 'tx')
call assert_equal(' 2 these', getline('.'))
$
" back at the bottom of the buffer
call feedkeys("?the".repeat("\<c-p>", 8)."\<cr>", 'tx')
call feedkeys("?the".repeat("\<C-T>", 8)."\<cr>", 'tx')
call assert_equal(' 9 these', getline('.'))
" Test 6
@@ -160,16 +160,16 @@ func Test_search_cmdline()
call assert_equal(' 2 these', getline('.'))
1
" go to next match of 'thes'
call feedkeys("/the\<c-l>\<c-n>\<cr>", 'tx')
call feedkeys("/the\<c-l>\<C-G>\<cr>", 'tx')
call assert_equal(' 9 these', getline('.'))
1
" wrap around
call feedkeys("/the\<c-l>\<c-n>\<c-n>\<cr>", 'tx')
call feedkeys("/the\<c-l>\<C-G>\<C-G>\<cr>", 'tx')
call assert_equal(' 2 these', getline('.'))
1
" wrap around
set nowrapscan
call feedkeys("/the\<c-l>\<c-n>\<c-n>\<cr>", 'tx')
call feedkeys("/the\<c-l>\<C-G>\<C-G>\<cr>", 'tx')
call assert_equal(' 9 these', getline('.'))
" Test 7
@@ -185,7 +185,7 @@ func Test_search_cmdline()
call assert_equal(' 9 these', getline('.'))
1
" delete one char, add another, go to previous match, add one char
call feedkeys("/thei\<bs>s\<bs>\<c-p>\<c-l>\<cr>", 'tx')
call feedkeys("/thei\<bs>s\<bs>\<C-T>\<c-l>\<cr>", 'tx')
call assert_equal(' 8 them', getline('.'))
1
" delete all chars, start from the beginning again
@@ -209,7 +209,7 @@ func Test_search_cmdline2()
new
call setline(1, [' 1', ' 2 these', ' 3 the theother'])
" Test 1
" Ctrl-P goes correctly back and forth
" Ctrl-T goes correctly back and forth
set incsearch
1
" first match
@@ -217,27 +217,27 @@ func Test_search_cmdline2()
call assert_equal(' 2 these', getline('.'))
1
" go to next match (on next line)
call feedkeys("/the\<c-n>\<cr>", 'tx')
call feedkeys("/the\<C-G>\<cr>", 'tx')
call assert_equal(' 3 the theother', getline('.'))
1
" go to next match (still on line 3)
call feedkeys("/the\<c-n>\<c-n>\<cr>", 'tx')
call feedkeys("/the\<C-G>\<C-G>\<cr>", 'tx')
call assert_equal(' 3 the theother', getline('.'))
1
" go to next match (still on line 3)
call feedkeys("/the\<c-n>\<c-n>\<c-n>\<cr>", 'tx')
call feedkeys("/the\<C-G>\<C-G>\<C-G>\<cr>", 'tx')
call assert_equal(' 3 the theother', getline('.'))
1
" go to previous match (on line 3)
call feedkeys("/the\<c-n>\<c-n>\<c-n>\<c-p>\<cr>", 'tx')
call feedkeys("/the\<C-G>\<C-G>\<C-G>\<C-T>\<cr>", 'tx')
call assert_equal(' 3 the theother', getline('.'))
1
" go to previous match (on line 3)
call feedkeys("/the\<c-n>\<c-n>\<c-n>\<c-p>\<c-p>\<cr>", 'tx')
call feedkeys("/the\<C-G>\<C-G>\<C-G>\<C-T>\<C-T>\<cr>", 'tx')
call assert_equal(' 3 the theother', getline('.'))
1
" go to previous match (on line 2)
call feedkeys("/the\<c-n>\<c-n>\<c-n>\<c-p>\<c-p>\<c-p>\<cr>", 'tx')
call feedkeys("/the\<C-G>\<C-G>\<C-G>\<C-T>\<C-T>\<C-T>\<cr>", 'tx')
call assert_equal(' 2 these', getline('.'))
" clean up

View File

@@ -176,7 +176,7 @@ static const int included_patches[] = {
// 2271 NA
// 2270 NA
2269,
// 2268,
2268,
// 2267 NA
2266,
2265,

View File

@@ -48,49 +48,49 @@ describe('search cmdline', function()
2 {inc:the}se |
/the^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
2 these |
3 {inc:the} |
/the^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
3 the |
4 {inc:the}ir |
/the^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
4 their |
5 {inc:the}re |
/the^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
5 there |
6 {inc:the}ir |
/the^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
6 their |
7 {inc:the} |
/the^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
7 the |
8 {inc:the}m |
/the^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
8 them |
9 {inc:the}se |
/the^ |
]])
feed('<C-N>')
feed('<C-G>')
if wrapscan == 'wrapscan' then
screen:expect([[
2 {inc:the}se |
@@ -117,7 +117,7 @@ describe('search cmdline', function()
?the^ |
]])
if wrapscan == 'wrapscan' then
feed('<C-N>')
feed('<C-G>')
screen:expect([[
2 {inc:the}se |
3 the |
@@ -130,7 +130,7 @@ describe('search cmdline', function()
?the |
]])
else
feed('<C-N>')
feed('<C-G>')
screen:expect([[
9 {inc:the}se |
10 foobar |
@@ -150,14 +150,14 @@ describe('search cmdline', function()
10 foobar |
?the^ |
]])
feed('<C-P>')
feed('<C-T>')
screen:expect([[
8 {inc:the}m |
9 these |
?the^ |
]])
for i = 1, 6 do
feed('<C-P>')
feed('<C-T>')
-- Avoid sleep just before expect, otherwise expect will take the full
-- timeout
if i ~= 6 then
@@ -169,7 +169,7 @@ describe('search cmdline', function()
3 the |
?the^ |
]])
feed('<C-P>')
feed('<C-T>')
if wrapscan == 'wrapscan' then
screen:expect([[
9 {inc:the}se |
@@ -185,19 +185,19 @@ describe('search cmdline', function()
end
end
it("using <C-N> and 'nowrapscan'", function()
it("using <C-G> and 'nowrapscan'", function()
forwarditer('nowrapscan')
end)
it("using <C-N> and 'wrapscan'", function()
it("using <C-G> and 'wrapscan'", function()
forwarditer('wrapscan')
end)
it("using <C-P> and 'nowrapscan'", function()
it("using <C-T> and 'nowrapscan'", function()
backiter('nowrapscan')
end)
it("using <C-P> and 'wrapscan'", function()
it("using <C-T> and 'wrapscan'", function()
backiter('wrapscan')
end)
end)
@@ -218,13 +218,13 @@ describe('search cmdline', function()
2 {inc:thes}e |
/thes^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
9 {inc:thes}e |
10 foobar |
/thes^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
2 {inc:thes}e |
3 the |
@@ -251,13 +251,13 @@ describe('search cmdline', function()
2 {inc:thes}e |
/thes^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
9 {inc:thes}e |
10 foobar |
/thes^ |
]])
feed('<C-N><CR>')
feed('<C-G><CR>')
screen:expect([[
9 ^these |
10 foobar |
@@ -298,7 +298,7 @@ describe('search cmdline', function()
/the^ |
]])
-- Advance to previous match
feed('<C-P>')
feed('<C-T>')
screen:expect([[
8 {inc:the}m |
9 these |
@@ -332,7 +332,7 @@ describe('search cmdline', function()
]])
end)
it('can traverse matches in the same line with <C-N>/<C-P>', function()
it('can traverse matches in the same line with <C-G>/<C-T>', function()
funcs.setline(1, { ' 1', ' 2 these', ' 3 the theother' })
command('1')
command('set incsearch')
@@ -346,7 +346,7 @@ describe('search cmdline', function()
]])
-- Next match, different line
feed('<C-N>')
feed('<C-G>')
screen:expect([[
2 these |
3 {inc:the} theother |
@@ -354,13 +354,13 @@ describe('search cmdline', function()
]])
-- Next match, same line
feed('<C-N>')
feed('<C-G>')
screen:expect([[
2 these |
3 the {inc:the}other |
/the^ |
]])
feed('<C-N>')
feed('<C-G>')
screen:expect([[
2 these |
3 the theo{inc:the}r |
@@ -368,13 +368,13 @@ describe('search cmdline', function()
]])
-- Previous match, same line
feed('<C-P>')
feed('<C-T>')
screen:expect([[
2 these |
3 the {inc:the}other |
/the^ |
]])
feed('<C-P>')
feed('<C-T>')
screen:expect([[
2 these |
3 {inc:the} theother |
@@ -382,7 +382,7 @@ describe('search cmdline', function()
]])
-- Previous match, different line
feed('<C-P>')
feed('<C-T>')
screen:expect([[
2 {inc:the}se |
3 the theother |