aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorzeertzjq <zeertzjq@outlook.com>2021-07-31 09:51:26 +0800
committerGitHub <noreply@github.com>2021-07-30 21:51:26 -0400
commit5f01714b255d1c037abcb836b835096cf817adfd (patch)
treeb92eaf569a18e18340f9e7f85334cfc7da23ecc7
parent15698eb5a1991790476febbd3b9f9b392e74f6b9 (diff)
downloadrneovim-5f01714b255d1c037abcb836b835096cf817adfd.tar.gz
rneovim-5f01714b255d1c037abcb836b835096cf817adfd.tar.bz2
rneovim-5f01714b255d1c037abcb836b835096cf817adfd.zip
vim-patch:8.1.2019: 'cursorline' always highlights the whole line (#15161)
Problem: 'cursorline' always highlights the whole line. Solution: Add 'cursorlineopt' to specify what is highlighted. (closes vim/vim#4693) https://github.com/vim/vim/commit/410e98a70bc00ea4bed51e55a8fe20e56a72c087
-rw-r--r--runtime/doc/options.txt16
-rw-r--r--runtime/doc/quickref.txt1
-rw-r--r--runtime/doc/syntax.txt3
-rw-r--r--runtime/optwin.vim3
-rw-r--r--src/nvim/buffer_defs.h2
-rw-r--r--src/nvim/option.c11
-rw-r--r--src/nvim/option_defs.h1
-rw-r--r--src/nvim/options.lua7
-rw-r--r--src/nvim/screen.c16
-rw-r--r--src/nvim/testdir/test_alot.vim1
-rw-r--r--src/nvim/testdir/test_cursorline.vim108
11 files changed, 160 insertions, 9 deletions
diff --git a/runtime/doc/options.txt b/runtime/doc/options.txt
index ab2230641d..5292847240 100644
--- a/runtime/doc/options.txt
+++ b/runtime/doc/options.txt
@@ -1802,13 +1802,23 @@ A jump table for the options with a short description can be found at |Q_op|.
*'cursorline'* *'cul'* *'nocursorline'* *'nocul'*
'cursorline' 'cul' boolean (default off)
local to window
- Highlight the screen line of the cursor with CursorLine
- |hl-CursorLine|. Useful to easily spot the cursor. Will make screen
- redrawing slower.
+ Highlight the text line of the cursor with CursorLine |hl-CursorLine|.
+ Useful to easily spot the cursor. Will make screen redrawing slower.
When Visual mode is active the highlighting isn't used to make it
easier to see the selected text.
+ *'cursorlineopt'* *'culopt'*
+'cursorlineopt' 'culopt' string (default: "both")
+ local to window
+ Settings for how 'cursorline' is displayed. Valid values:
+ "line" Highlight the text line of the cursor with
+ CursorLine |hl-CursorLine|.
+ "number" Highlight the line number of the cursor with
+ CursorLineNr |hl-CursorLineNr|.
+ "both" Highlight as both "line" and "number" are set.
+
+
*'debug'*
'debug' string (default "")
global
diff --git a/runtime/doc/quickref.txt b/runtime/doc/quickref.txt
index c19b05f6c7..77e69a3eea 100644
--- a/runtime/doc/quickref.txt
+++ b/runtime/doc/quickref.txt
@@ -659,6 +659,7 @@ Short explanation of each option: *option-list*
'cursorbind' 'crb' move cursor in window as it moves in other windows
'cursorcolumn' 'cuc' highlight the screen column of the cursor
'cursorline' 'cul' highlight the screen line of the cursor
+'cursorlineopt' 'culopt' settings for 'cursorline'
'debug' set to "msg" to see all error messages
'define' 'def' pattern to be used to find a macro definition
'delcombine' 'deco' delete combining characters on their own
diff --git a/runtime/doc/syntax.txt b/runtime/doc/syntax.txt
index bc7a1e34c3..0cd3aed7a2 100644
--- a/runtime/doc/syntax.txt
+++ b/runtime/doc/syntax.txt
@@ -5065,7 +5065,8 @@ Substitute |:substitute| replacement text highlighting
LineNr Line number for ":number" and ":#" commands, and when 'number'
or 'relativenumber' option is set.
*hl-CursorLineNr*
-CursorLineNr Like LineNr when 'cursorline' or 'relativenumber' is set for
+CursorLineNr Like LineNr when 'cursorline' is set and 'cursorlineopt' is
+ set to "number" or "both", or 'relativenumber' is set, for
the cursor line.
*hl-MatchParen*
MatchParen The character under the cursor or just before it, if it
diff --git a/runtime/optwin.vim b/runtime/optwin.vim
index 633cb9e509..d4c10f7afa 100644
--- a/runtime/optwin.vim
+++ b/runtime/optwin.vim
@@ -440,6 +440,9 @@ if has("syntax")
call append("$", "cursorline\thighlight the screen line of the cursor")
call append("$", "\t(local to window)")
call <SID>BinOptionL("cul")
+ call append("$", "cursorlineopt\tspecifies which area 'cursorline' highlights")
+ call append("$", "\t(local to window)")
+ call <SID>OptionL("culopt")
call append("$", "colorcolumn\tcolumns to highlight")
call append("$", "\t(local to window)")
call <SID>OptionL("cc")
diff --git a/src/nvim/buffer_defs.h b/src/nvim/buffer_defs.h
index 2fe85e0543..1099573f83 100644
--- a/src/nvim/buffer_defs.h
+++ b/src/nvim/buffer_defs.h
@@ -226,6 +226,8 @@ typedef struct {
# define w_p_cuc w_onebuf_opt.wo_cuc // 'cursorcolumn'
int wo_cul;
# define w_p_cul w_onebuf_opt.wo_cul // 'cursorline'
+ char_u *wo_culopt;
+# define w_p_culopt w_onebuf_opt.wo_culopt // 'cursorlineopt'
char_u *wo_cc;
# define w_p_cc w_onebuf_opt.wo_cc // 'colorcolumn'
char_u *wo_stl;
diff --git a/src/nvim/option.c b/src/nvim/option.c
index f67cfd109b..95970a77f8 100644
--- a/src/nvim/option.c
+++ b/src/nvim/option.c
@@ -322,6 +322,7 @@ static char *(p_scl_values[]) = { "yes", "no", "auto", "auto:1", "auto:2",
static char *(p_fdc_values[]) = { "auto", "auto:1", "auto:2",
"auto:3", "auto:4", "auto:5", "auto:6", "auto:7", "auto:8", "auto:9",
"0", "1", "2", "3", "4", "5", "6", "7", "8", "9", NULL };
+static char *(p_culopt_values[]) = { "line", "number", "both", NULL };
/// All possible flags for 'shm'.
static char_u SHM_ALL[] = {
@@ -2411,6 +2412,12 @@ did_set_string_option(
os_setenv("VIMRUNTIME", "", 1);
didset_vimruntime = false;
}
+ } else if (varp == &curwin->w_p_culopt
+ || gvarp == &curwin->w_allbuf_opt.wo_culopt) { // 'cursorlineopt'
+ if (**varp == NUL
+ || check_opt_strings(*varp, p_culopt_values, false) != OK) {
+ errmsg = e_invarg;
+ }
} else if (varp == &curwin->w_p_cc) { // 'colorcolumn'
errmsg = check_colorcolumn(curwin);
} else if (varp == &p_hlg) { // 'helplang'
@@ -5652,6 +5659,7 @@ static char_u *get_varp(vimoption_T *p)
case PV_SPELL: return (char_u *)&(curwin->w_p_spell);
case PV_CUC: return (char_u *)&(curwin->w_p_cuc);
case PV_CUL: return (char_u *)&(curwin->w_p_cul);
+ case PV_CULOPT: return (char_u *)&(curwin->w_p_culopt);
case PV_CC: return (char_u *)&(curwin->w_p_cc);
case PV_DIFF: return (char_u *)&(curwin->w_p_diff);
case PV_FDC: return (char_u *)&(curwin->w_p_fdc);
@@ -5799,6 +5807,7 @@ void copy_winopt(winopt_T *from, winopt_T *to)
to->wo_spell = from->wo_spell;
to->wo_cuc = from->wo_cuc;
to->wo_cul = from->wo_cul;
+ to->wo_culopt = vim_strsave(from->wo_culopt);
to->wo_cc = vim_strsave(from->wo_cc);
to->wo_diff = from->wo_diff;
to->wo_diff_saved = from->wo_diff_saved;
@@ -5849,6 +5858,7 @@ static void check_winopt(winopt_T *wop)
check_string_option(&wop->wo_scl);
check_string_option(&wop->wo_rlc);
check_string_option(&wop->wo_stl);
+ check_string_option(&wop->wo_culopt);
check_string_option(&wop->wo_cc);
check_string_option(&wop->wo_cocu);
check_string_option(&wop->wo_briopt);
@@ -5871,6 +5881,7 @@ void clear_winopt(winopt_T *wop)
clear_string_option(&wop->wo_scl);
clear_string_option(&wop->wo_rlc);
clear_string_option(&wop->wo_stl);
+ clear_string_option(&wop->wo_culopt);
clear_string_option(&wop->wo_cc);
clear_string_option(&wop->wo_cocu);
clear_string_option(&wop->wo_briopt);
diff --git a/src/nvim/option_defs.h b/src/nvim/option_defs.h
index 5e40bdd6ef..37e75a6cc7 100644
--- a/src/nvim/option_defs.h
+++ b/src/nvim/option_defs.h
@@ -870,6 +870,7 @@ enum {
, WV_SPELL
, WV_CUC
, WV_CUL
+ , WV_CULOPT
, WV_CC
, WV_STL
, WV_WFH
diff --git a/src/nvim/options.lua b/src/nvim/options.lua
index 0830fb4638..7b8170094e 100644
--- a/src/nvim/options.lua
+++ b/src/nvim/options.lua
@@ -556,6 +556,13 @@ return {
defaults={if_true={vi=false}}
},
{
+ full_name='cursorlineopt', abbreviation='culopt',
+ short_desc=N_("settings for 'cursorline'"),
+ type='string', scope={'window'},
+ redraw={'current_window_only'},
+ defaults={if_true={vi="both"}}
+ },
+ {
full_name='debug',
short_desc=N_("to \"msg\" to see all error messages"),
type='string', scope={'global'},
diff --git a/src/nvim/screen.c b/src/nvim/screen.c
index aee10c06ad..b048facfb7 100644
--- a/src/nvim/screen.c
+++ b/src/nvim/screen.c
@@ -2362,7 +2362,8 @@ static int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow,
if (lnum == wp->w_cursor.lnum) {
// Do not show the cursor line when Visual mode is active, because it's
// not clear what is selected then.
- if (wp->w_p_cul && !(wp == curwin && VIsual_active)) {
+ if (wp->w_p_cul && !(wp == curwin && VIsual_active)
+ && *wp->w_p_culopt != 'n') {
int cul_attr = win_hl_attr(wp, HLF_CUL);
HlAttrs ae = syn_attr2entry(cul_attr);
@@ -2786,6 +2787,7 @@ static int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow,
// :sign defined with "numhl" highlight.
char_attr = num_sattr->sat_numhl;
} else if ((wp->w_p_cul || wp->w_p_rnu)
+ && *wp->w_p_culopt != 'l'
&& lnum == wp->w_cursor.lnum
&& filler_todo == 0) {
// When 'cursorline' is set highlight the line number of
@@ -2821,7 +2823,8 @@ static int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow,
if (diff_hlf != (hlf_T)0) {
char_attr = win_hl_attr(wp, diff_hlf);
- if (wp->w_p_cul && lnum == wp->w_cursor.lnum) {
+ if (wp->w_p_cul && lnum == wp->w_cursor.lnum
+ && *wp->w_p_culopt != 'n') {
char_attr = hl_combine_attr(char_attr, win_hl_attr(wp, HLF_CUL));
}
}
@@ -2881,7 +2884,8 @@ static int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow,
if (tocol == vcol)
tocol += n_extra;
// Combine 'showbreak' with 'cursorline', prioritizing 'showbreak'.
- if (wp->w_p_cul && lnum == wp->w_cursor.lnum) {
+ if (wp->w_p_cul && lnum == wp->w_cursor.lnum
+ && *wp->w_p_culopt != 'n') {
char_attr = hl_combine_attr(win_hl_attr(wp, HLF_CUL), char_attr);
}
}
@@ -3116,7 +3120,8 @@ static int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow,
}
line_attr = win_hl_attr(wp, diff_hlf);
// Overlay CursorLine onto diff-mode highlight.
- if (wp->w_p_cul && lnum == wp->w_cursor.lnum) {
+ if (wp->w_p_cul && lnum == wp->w_cursor.lnum
+ && *wp->w_p_culopt != 'n') {
line_attr = 0 != line_attr_lowprio // Low-priority CursorLine
? hl_combine_attr(hl_combine_attr(win_hl_attr(wp, HLF_CUL),
line_attr),
@@ -3924,7 +3929,8 @@ static int win_line(win_T *wp, linenr_T lnum, int startrow, int endrow,
}
int eol_attr = char_attr;
- if (wp->w_p_cul && lnum == wp->w_cursor.lnum) {
+ if (wp->w_p_cul && lnum == wp->w_cursor.lnum
+ && *wp->w_p_culopt != 'n') {
eol_attr = hl_combine_attr(win_hl_attr(wp, HLF_CUL), eol_attr);
}
linebuf_attr[off] = eol_attr;
diff --git a/src/nvim/testdir/test_alot.vim b/src/nvim/testdir/test_alot.vim
index b5c50b5894..cc767a9bcf 100644
--- a/src/nvim/testdir/test_alot.vim
+++ b/src/nvim/testdir/test_alot.vim
@@ -7,6 +7,7 @@ source test_cd.vim
source test_changedtick.vim
source test_compiler.vim
source test_cursor_func.vim
+source test_cursorline.vim
source test_ex_equal.vim
source test_ex_undo.vim
source test_ex_z.vim
diff --git a/src/nvim/testdir/test_cursorline.vim b/src/nvim/testdir/test_cursorline.vim
new file mode 100644
index 0000000000..46fbd0cd64
--- /dev/null
+++ b/src/nvim/testdir/test_cursorline.vim
@@ -0,0 +1,108 @@
+" Test for cursorline and cursorlineopt
+"
+source view_util.vim
+source check.vim
+
+function! s:screen_attr(lnum) abort
+ return map(range(1, 8), 'screenattr(a:lnum, v:val)')
+endfunction
+
+function! s:test_windows(h, w) abort
+ call NewWindow(a:h, a:w)
+endfunction
+
+function! s:close_windows() abort
+ call CloseWindow()
+endfunction
+
+function! s:new_hi() abort
+ redir => save_hi
+ silent! hi CursorLineNr
+ redir END
+ let save_hi = join(split(substitute(save_hi, '\s*xxx\s*', ' ', ''), "\n"), '')
+ exe 'hi' save_hi 'ctermbg=0 guibg=Black'
+ return save_hi
+endfunction
+
+func Test_cursorline_highlight1()
+ let save_hi = s:new_hi()
+ try
+ call s:test_windows(10, 20)
+ call setline(1, repeat(['aaaa'], 10))
+ redraw
+ let attr01 = s:screen_attr(1)
+ call assert_equal(repeat([attr01[0]], 8), attr01)
+
+ setl number numberwidth=4
+ redraw
+ let attr11 = s:screen_attr(1)
+ call assert_equal(repeat([attr11[0]], 4), attr11[0:3])
+ call assert_equal(repeat([attr11[4]], 4), attr11[4:7])
+ call assert_notequal(attr11[0], attr11[4])
+
+ setl cursorline
+ redraw
+ let attr21 = s:screen_attr(1)
+ let attr22 = s:screen_attr(2)
+ call assert_equal(repeat([attr21[0]], 4), attr21[0:3])
+ call assert_equal(repeat([attr21[4]], 4), attr21[4:7])
+ call assert_equal(attr11, attr22)
+ call assert_notequal(attr22, attr21)
+
+ setl nocursorline relativenumber
+ redraw
+ let attr31 = s:screen_attr(1)
+ call assert_equal(attr21[0:3], attr31[0:3])
+ call assert_equal(attr11[4:7], attr31[4:7])
+
+ call s:close_windows()
+ finally
+ exe 'hi' save_hi
+ endtry
+endfunc
+
+func Test_cursorline_highlight2()
+ CheckOption cursorlineopt
+
+ let save_hi = s:new_hi()
+ try
+ call s:test_windows(10, 20)
+ call setline(1, repeat(['aaaa'], 10))
+ redraw
+ let attr0 = s:screen_attr(1)
+ call assert_equal(repeat([attr0[0]], 8), attr0)
+
+ setl number
+ redraw
+ let attr1 = s:screen_attr(1)
+ call assert_notequal(attr0[0:3], attr1[0:3])
+ call assert_equal(attr0[0:3], attr1[4:7])
+
+ setl cursorline cursorlineopt=both
+ redraw
+ let attr2 = s:screen_attr(1)
+ call assert_notequal(attr1[0:3], attr2[0:3])
+ call assert_notequal(attr1[4:7], attr2[4:7])
+
+ setl cursorlineopt=line
+ redraw
+ let attr3 = s:screen_attr(1)
+ call assert_equal(attr1[0:3], attr3[0:3])
+ call assert_equal(attr2[4:7], attr3[4:7])
+
+ setl cursorlineopt=number
+ redraw
+ let attr4 = s:screen_attr(1)
+ call assert_equal(attr2[0:3], attr4[0:3])
+ call assert_equal(attr1[4:7], attr4[4:7])
+
+ setl nonumber
+ redraw
+ let attr5 = s:screen_attr(1)
+ call assert_equal(attr0, attr5)
+
+ call s:close_windows()
+ finally
+ exe 'hi' save_hi
+ endtry
+endfunc