Merge pull request #11445 from bfredl/fcslcs

options: make 'fillchars' and 'listchars' global-local instead of local-only
This commit is contained in:
Björn Linse 2019-11-26 22:10:13 +01:00 committed by GitHub
commit 5f9209389b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 101 additions and 30 deletions

View File

@ -2362,7 +2362,7 @@ A jump table for the options with a short description can be found at |Q_op|.
*'fillchars'* *'fcs'*
'fillchars' 'fcs' string (default "")
local to window
global or local to window |global-local|
Characters to fill the statuslines and vertical separators.
It is a comma separated list of items:
@ -3671,7 +3671,7 @@ A jump table for the options with a short description can be found at |Q_op|.
*'listchars'* *'lcs'*
'listchars' 'lcs' string (default: "tab:> ,trail:-,nbsp:+"
Vi default: "eol:$")
local to window
global or local to window |global-local|
Strings to use in 'list' mode and for the |:list| command. It is a
comma separated list of string settings.

View File

@ -2205,10 +2205,10 @@ static void didset_options2(void)
(void)opt_strings_flags(p_cb, p_cb_values, &cb_flags, true);
// Parse default for 'fillchars'.
(void)set_chars_option(curwin, &curwin->w_p_fcs);
(void)set_chars_option(curwin, &curwin->w_p_fcs, true);
// Parse default for 'listchars'.
(void)set_chars_option(curwin, &curwin->w_p_lcs);
(void)set_chars_option(curwin, &curwin->w_p_lcs, true);
// Parse default for 'wildmode'.
check_opt_wim();
@ -2663,11 +2663,11 @@ did_set_string_option(
errmsg = e_invarg;
} else {
FOR_ALL_TAB_WINDOWS(tp, wp) {
if (set_chars_option(wp, &wp->w_p_lcs) != NULL) {
if (set_chars_option(wp, &wp->w_p_lcs, true) != NULL) {
errmsg = (char_u *)_("E834: Conflicts with value of 'listchars'");
goto ambw_end;
}
if (set_chars_option(wp, &wp->w_p_fcs) != NULL) {
if (set_chars_option(wp, &wp->w_p_fcs, true) != NULL) {
errmsg = (char_u *)_("E835: Conflicts with value of 'fillchars'");
goto ambw_end;
}
@ -2868,10 +2868,26 @@ ambw_end:
}
s = skip_to_option_part(s);
}
} else if (varp == &curwin->w_p_lcs) { // 'listchars'
errmsg = set_chars_option(curwin, varp);
} else if (varp == &curwin->w_p_fcs) { // 'fillchars'
errmsg = set_chars_option(curwin, varp);
} else if (varp == &p_lcs) { // 'listchars'
errmsg = set_chars_option(curwin, varp, false);
if (!errmsg) {
FOR_ALL_TAB_WINDOWS(tp, wp) {
set_chars_option(wp, &wp->w_p_lcs, true);
}
}
redraw_all_later(NOT_VALID);
} else if (varp == &curwin->w_p_lcs) { // local 'listchars'
errmsg = set_chars_option(curwin, varp, true);
} else if (varp == &p_fcs) { // 'fillchars'
errmsg = set_chars_option(curwin, varp, false);
if (!errmsg) {
FOR_ALL_TAB_WINDOWS(tp, wp) {
set_chars_option(wp, &wp->w_p_fcs, true);
}
}
redraw_all_later(NOT_VALID);
} else if (varp == &curwin->w_p_fcs) { // local 'fillchars'
errmsg = set_chars_option(curwin, varp, true);
} else if (varp == &p_cedit) { // 'cedit'
errmsg = check_cedit();
} else if (varp == &p_vfile) { // 'verbosefile'
@ -3501,7 +3517,7 @@ skip:
///
/// @param varp either &curwin->w_p_lcs or &curwin->w_p_fcs
/// @return error message, NULL if it's OK.
static char_u *set_chars_option(win_T *wp, char_u **varp)
static char_u *set_chars_option(win_T *wp, char_u **varp, bool set)
{
int round, i, len, entries;
char_u *p, *s;
@ -3536,12 +3552,18 @@ static char_u *set_chars_option(win_T *wp, char_u **varp)
{ &wp->w_p_lcs_chars.conceal, "conceal", NUL },
};
if (varp == &wp->w_p_lcs) {
if (varp == &p_lcs || varp == &wp->w_p_lcs) {
tab = lcs_tab;
entries = ARRAY_SIZE(lcs_tab);
if (varp == &wp->w_p_lcs && wp->w_p_lcs[0] == NUL) {
varp = &p_lcs;
}
} else {
tab = fcs_tab;
entries = ARRAY_SIZE(fcs_tab);
if (varp == &wp->w_p_fcs && wp->w_p_fcs[0] == NUL) {
varp = &p_fcs;
}
if (*p_ambw == 'd') {
// XXX: If ambiwidth=double then "|" and "·" take 2 columns, which is
// forbidden (TUI limitation?). Set old defaults.
@ -3554,7 +3576,7 @@ static char_u *set_chars_option(win_T *wp, char_u **varp)
}
// first round: check for valid value, second round: assign values
for (round = 0; round <= 1; round++) {
for (round = 0; round <= set ? 1 : 0; round++) {
if (round > 0) {
// After checking that the value is valid: set defaults
for (i = 0; i < entries; i++) {
@ -3562,7 +3584,7 @@ static char_u *set_chars_option(win_T *wp, char_u **varp)
*(tab[i].cp) = tab[i].def;
}
}
if (varp == &wp->w_p_lcs) {
if (varp == &p_lcs || varp == &wp->w_p_lcs) {
wp->w_p_lcs_chars.tab1 = NUL;
wp->w_p_lcs_chars.tab3 = NUL;
}
@ -5569,6 +5591,16 @@ void unset_global_local_option(char *name, void *from)
case PV_MENC:
clear_string_option(&buf->b_p_menc);
break;
case PV_LCS:
clear_string_option(&((win_T *)from)->w_p_lcs);
set_chars_option((win_T *)from, &((win_T *)from)->w_p_lcs, true);
redraw_win_later((win_T *)from, NOT_VALID);
break;
case PV_FCS:
clear_string_option(&((win_T *)from)->w_p_fcs);
set_chars_option((win_T *)from, &((win_T *)from)->w_p_fcs, true);
redraw_win_later((win_T *)from, NOT_VALID);
break;
}
}
@ -5605,6 +5637,8 @@ static char_u *get_varp_scope(vimoption_T *p, int opt_flags)
case PV_LW: return (char_u *)&(curbuf->b_p_lw);
case PV_BKC: return (char_u *)&(curbuf->b_p_bkc);
case PV_MENC: return (char_u *)&(curbuf->b_p_menc);
case PV_FCS: return (char_u *)&(curwin->w_p_fcs);
case PV_LCS: return (char_u *)&(curwin->w_p_lcs);
}
return NULL; // "cannot happen"
}
@ -5663,6 +5697,10 @@ static char_u *get_varp(vimoption_T *p)
? (char_u *)&(curbuf->b_p_lw) : p->var;
case PV_MENC: return *curbuf->b_p_menc != NUL
? (char_u *)&(curbuf->b_p_menc) : p->var;
case PV_FCS: return *curwin->w_p_fcs != NUL
? (char_u *)&(curwin->w_p_fcs) : p->var;
case PV_LCS: return *curwin->w_p_lcs != NUL
? (char_u *)&(curwin->w_p_lcs) : p->var;
case PV_ARAB: return (char_u *)&(curwin->w_p_arab);
case PV_LIST: return (char_u *)&(curwin->w_p_list);
@ -5760,8 +5798,6 @@ static char_u *get_varp(vimoption_T *p)
case PV_KMAP: return (char_u *)&(curbuf->b_p_keymap);
case PV_SCL: return (char_u *)&(curwin->w_p_scl);
case PV_WINHL: return (char_u *)&(curwin->w_p_winhl);
case PV_FCS: return (char_u *)&(curwin->w_p_fcs);
case PV_LCS: return (char_u *)&(curwin->w_p_lcs);
case PV_WINBL: return (char_u *)&(curwin->w_p_winbl);
default: IEMSG(_("E356: get_varp ERROR"));
}
@ -5903,8 +5939,8 @@ void didset_window_options(win_T *wp)
{
check_colorcolumn(wp);
briopt_check(wp);
set_chars_option(wp, &wp->w_p_fcs);
set_chars_option(wp, &wp->w_p_lcs);
set_chars_option(wp, &wp->w_p_fcs, true);
set_chars_option(wp, &wp->w_p_lcs, true);
parse_winhl_opt(wp); // sets w_hl_needs_update also for w_p_winbl
wp->w_grid.blending = wp->w_p_winbl > 0;
}

View File

@ -484,6 +484,7 @@ EXTERN long p_linespace; // 'linespace'
EXTERN char_u *p_lispwords; // 'lispwords'
EXTERN long p_ls; // 'laststatus'
EXTERN long p_stal; // 'showtabline'
EXTERN char_u *p_lcs; // 'listchars'
EXTERN int p_lz; // 'lazyredraw'
EXTERN int p_lpl; // 'loadplugins'
@ -652,6 +653,7 @@ EXTERN long p_ul; ///< 'undolevels'
EXTERN long p_ur; ///< 'undoreload'
EXTERN long p_uc; ///< 'updatecount'
EXTERN long p_ut; ///< 'updatetime'
EXTERN char_u *p_fcs; ///< 'fillchar'
EXTERN char_u *p_shada; ///< 'shada'
EXTERN char *p_shadafile; ///< 'shadafile'
EXTERN char_u *p_vdir; ///< 'viewdir'

View File

@ -804,11 +804,12 @@ return {
},
{
full_name='fillchars', abbreviation='fcs',
type='string', list='onecomma', scope={'window'},
type='string', list='onecomma', scope={'global', 'window'},
deny_duplicates=true,
vi_def=true,
alloced=true,
redraw={'current_window'},
varname='p_fcs',
defaults={if_true={vi=''}}
},
{
@ -1420,11 +1421,12 @@ return {
},
{
full_name='listchars', abbreviation='lcs',
type='string', list='onecomma', scope={'window'},
type='string', list='onecomma', scope={'global', 'window'},
deny_duplicates=true,
vim=true,
alloced=true,
redraw={'current_window'},
varname='p_lcs',
defaults={if_true={vi="eol:$", vim="tab:> ,trail:-,nbsp:+"}}
},
{

View File

@ -71,6 +71,7 @@ func! Test_display_foldtext_mbyte()
endfunc
func Test_display_listchars_precedes()
set fillchars+=vert:\|
call NewWindow(10, 10)
" Need a physical line that wraps over the complete
" window size

View File

@ -67,15 +67,28 @@ describe("'fillchars'", function()
shouldfail('eob:xy') -- two ascii chars
shouldfail('eob:\255', 'eob:<ff>') -- invalid UTF-8
end)
it('is local to window', function()
clear()
screen = Screen.new(50, 5)
screen:attach()
it('has global value', function()
screen:try_resize(50, 5)
insert("foo\nbar")
command('set laststatus=0')
command('1,2fold')
command('vsplit')
command('set fillchars=fold:x')
screen:expect([[
^+-- 2 lines: fooxxxxxxxx+-- 2 lines: fooxxxxxxx|
~ ~ |
~ ~ |
~ ~ |
|
]])
end)
it('has local window value', function()
screen:try_resize(50, 5)
insert("foo\nbar")
command('set laststatus=0')
command('1,2fold')
command('vsplit')
command('setl fillchars=fold:x')
screen:expect([[
^+-- 2 lines: fooxxxxxxxx+-- 2 lines: foo·······|
~ ~ |
@ -96,12 +109,25 @@ describe("'listchars'", function()
screen:attach()
end)
it('is local to window', function()
it('has global value', function()
feed('i<tab><tab><tab><esc>')
command('set laststatus=0')
command('set list listchars=tab:<->')
command('set list laststatus=0')
command('vsplit')
command('set listchars&')
command('set listchars=tab:<->')
screen:expect([[
<------><------>^<------> <------><------><------>|
~ ~ |
~ ~ |
~ ~ |
|
]])
end)
it('has value local to window', function()
feed('i<tab><tab><tab><esc>')
command('set list laststatus=0')
command('setl listchars=tab:<->')
command('vsplit')
command('setl listchars<')
screen:expect([[
> > ^> <------><------><------>|
~ ~ |

View File

@ -12,7 +12,10 @@ describe('ui/mouse/input', function()
clear()
meths.set_option('mouse', 'a')
meths.set_option('list', true)
meths.set_option('listchars', 'eol:$')
-- NB: this is weird, but mostly irrelevant to the test
-- So I didn't bother to change it
command('set listchars=eol:$')
command('setl listchars=nbsp:x')
screen = Screen.new(25, 5)
screen:attach()
screen:set_default_attr_ids({
@ -812,7 +815,8 @@ describe('ui/mouse/input', function()
feed_command('set concealcursor=ni')
feed_command('set nowrap')
feed_command('set shiftwidth=2 tabstop=4 list listchars=tab:>-')
feed_command('set shiftwidth=2 tabstop=4 list')
feed_command('setl listchars=tab:>-')
feed_command('syntax match NonText "\\*" conceal')
feed_command('syntax match NonText "cats" conceal cchar=X')
feed_command('syntax match NonText "x" conceal cchar=>')