diff options
-rw-r--r-- | src/nvim/buffer_defs.h | 1 | ||||
-rw-r--r-- | src/nvim/match.c | 20 | ||||
-rw-r--r-- | src/nvim/testdir/test_search.vim | 12 | ||||
-rw-r--r-- | test/functional/ui/searchhl_spec.lua | 109 |
4 files changed, 88 insertions, 54 deletions
diff --git a/src/nvim/buffer_defs.h b/src/nvim/buffer_defs.h index baa0d1f102..c16a9c0282 100644 --- a/src/nvim/buffer_defs.h +++ b/src/nvim/buffer_defs.h @@ -1027,6 +1027,7 @@ typedef struct { colnr_T startcol; // in win_line() points to char where HL starts colnr_T endcol; // in win_line() points to char where HL ends bool is_addpos; // position specified directly by matchaddpos() + bool has_cursor; // true if the cursor is inside the match, used for CurSearch proftime_T tm; // for a time limit } match_T; diff --git a/src/nvim/match.c b/src/nvim/match.c index 256e5812d4..f6d2fe13c4 100644 --- a/src/nvim/match.c +++ b/src/nvim/match.c @@ -373,6 +373,7 @@ static int next_search_hl_pos(match_T *shl, linenr_T lnum, posmatch_T *posmatch, shl->rm.endpos[0].lnum = 0; shl->rm.endpos[0].col = end; shl->is_addpos = true; + shl->has_cursor = false; posmatch->cur = found + 1; return 1; } @@ -585,6 +586,7 @@ bool prepare_search_hl_line(win_T *wp, linenr_T lnum, colnr_T mincol, char_u **l shl->lines = 0; shl->attr_cur = 0; shl->is_addpos = false; + shl->has_cursor = false; if (cur != NULL) { cur->pos.cur = 0; } @@ -612,6 +614,17 @@ bool prepare_search_hl_line(win_T *wp, linenr_T lnum, colnr_T mincol, char_u **l } else { shl->lines = 1; } + + // check if the cursor is in the match before changing the columns + if (wp->w_cursor.lnum >= shl->lnum + && wp->w_cursor.lnum <= shl->lnum + shl->rm.endpos[0].lnum + && (wp->w_cursor.lnum > shl->lnum + || wp->w_cursor.col >= shl->rm.startpos[0].col) + && (wp->w_cursor.lnum < shl->lnum + shl->lines + || wp->w_cursor.col < shl->rm.endpos[0].col)) { + shl->has_cursor = true; + } + // Highlight one character for an empty match. if (shl->startcol == shl->endcol) { if ((*line)[shl->endcol] != NUL) { @@ -676,12 +689,7 @@ int update_search_hl(win_T *wp, linenr_T lnum, colnr_T col, char_u **line, match } // Highlight the match were the cursor is using the CurSearch // group. - if (shl == search_hl - && (HL_ATTR(HLF_LC) || wp->w_hl_ids[HLF_LC]) - && wp->w_cursor.lnum == lnum - && wp->w_cursor.lnum < shl->lnum + shl->lines - && wp->w_cursor.col >= shl->startcol - && wp->w_cursor.col < shl->endcol) { + if (shl == search_hl && shl->has_cursor && (HL_ATTR(HLF_LC) || wp->w_hl_ids[HLF_LC])) { shl->attr_cur = win_hl_attr(wp, HLF_LC) ? win_hl_attr(wp, HLF_LC) : HL_ATTR(HLF_LC); } else { shl->attr_cur = shl->attr; diff --git a/src/nvim/testdir/test_search.vim b/src/nvim/testdir/test_search.vim index 6ccc151294..24ecc58281 100644 --- a/src/nvim/testdir/test_search.vim +++ b/src/nvim/testdir/test_search.vim @@ -968,7 +968,17 @@ func Test_hlsearch_cursearch() call VerifyScreenDump(buf, 'Test_hlsearch_cursearch_single_line_3', {}) call term_sendkeys(buf, "gg/foo\\nbar\<CR>") - call VerifyScreenDump(buf, 'Test_hlsearch_cursearch_multiple_line', {}) + call VerifyScreenDump(buf, 'Test_hlsearch_cursearch_multiple_line_1', {}) + + call term_sendkeys(buf, ":call setline(1, ['---', 'abcdefg', 'hijkl', '---', 'abcdefg', 'hijkl'])\<CR>") + call term_sendkeys(buf, "gg/efg\\nhij\<CR>") + call VerifyScreenDump(buf, 'Test_hlsearch_cursearch_multiple_line_2', {}) + call term_sendkeys(buf, "h\<C-L>") + call VerifyScreenDump(buf, 'Test_hlsearch_cursearch_multiple_line_3', {}) + call term_sendkeys(buf, "j\<C-L>") + call VerifyScreenDump(buf, 'Test_hlsearch_cursearch_multiple_line_4', {}) + call term_sendkeys(buf, "h\<C-L>") + call VerifyScreenDump(buf, 'Test_hlsearch_cursearch_multiple_line_5', {}) call StopVimInTerminal(buf) call delete('Xhlsearch_cursearch') diff --git a/test/functional/ui/searchhl_spec.lua b/test/functional/ui/searchhl_spec.lua index a08db3e5e7..84dc3c59bb 100644 --- a/test/functional/ui/searchhl_spec.lua +++ b/test/functional/ui/searchhl_spec.lua @@ -163,53 +163,68 @@ describe('search highlighting', function() end) it('works for multiline match', function() - insert([[ - one - foo - bar - baz - foo - bar]]) - feed('gg/foo<CR>') - screen:expect([[ - one | - {2:^foo} | - bar | - baz | - {1:foo} | - bar | - /foo | - ]]) - feed('n') - screen:expect([[ - one | - {1:foo} | - bar | - baz | - {2:^foo} | - bar | - /foo | - ]]) - feed('?<CR>') - screen:expect([[ - one | - {2:^foo} | - bar | - baz | - {1:foo} | - bar | - ?foo | - ]]) - feed('gg/foo\\nbar<CR>') - screen:expect([[ - one | - {2:^foo} | - {1:bar} | - baz | - {1:foo} | - {1:bar} | - /foo\nbar | - ]]) + command([[call setline(1, ['one', 'foo', 'bar', 'baz', 'foo', 'bar'])]]) + feed('gg/foo<CR>') + screen:expect([[ + one | + {2:^foo} | + bar | + baz | + {1:foo} | + bar | + /foo | + ]]) + feed('n') + screen:expect([[ + one | + {1:foo} | + bar | + baz | + {2:^foo} | + bar | + /foo | + ]]) + feed('?<CR>') + screen:expect([[ + one | + {2:^foo} | + bar | + baz | + {1:foo} | + bar | + ?foo | + ]]) + feed('gg/foo\\nbar<CR>') + screen:expect([[ + one | + {2:^foo} | + {2:bar} | + baz | + {1:foo} | + {1:bar} | + /foo\nbar | + ]]) + command([[call setline(1, ['---', 'abcdefg', 'hijkl', '---', 'abcdefg', 'hijkl'])]]) + feed('gg/efg\\nhij<CR>') + screen:expect([[ + --- | + abcd{2:^efg} | + {2:hij}kl | + --- | + abcd{1:efg} | + {1:hij}kl | + /efg\nhij | + ]]) + feed('n') + screen:expect([[ + --- | + abcd{1:efg} | + {1:hij}kl | + --- | + abcd{2:^efg} | + {2:hij}kl | + /efg\nhij | + ]]) end) end) |