0
0
mirror of https://github.com/vim/vim.git synced 2025-07-26 11:04:33 -04:00

patch 8.2.4617: no completion for :scriptnames

Problem:    No completion for :scriptnames.
Solution:   Implement :scriptnames completion. (Yegappan Lakshmanan,
            closes #10005)
This commit is contained in:
Yegappan Lakshmanan 2022-03-24 11:22:13 +00:00 committed by Bram Moolenaar
parent 98b7fe725e
commit 454ce6737c
9 changed files with 139 additions and 20 deletions

View File

@ -3256,6 +3256,7 @@ getcompletion({pat}, {type} [, {filtered}]) *getcompletion()*
messages |:messages| suboptions
option options
packadd optional package |pack-add| names
scriptnames sourced script names |:scriptnames|
shellcmd Shell command
sign |:sign| suboptions
syntax syntax file names |'syntax'|
@ -3275,7 +3276,10 @@ getcompletion({pat}, {type} [, {filtered}]) *getcompletion()*
If the 'wildoptions' option contains 'fuzzy', then fuzzy
matching is used to get the completion matches. Otherwise
regular expression matching is used.
regular expression matching is used. Thus this function
follows the user preference, what happens on the command line.
If you do not want this you can make 'wildoptions' empty
before calling getcompletion() and restore it afterwards.
If {type} is "cmdline", then the |cmdline-completion| result is
returned. For example, to complete the possible values after

View File

@ -1709,6 +1709,24 @@ set_context_in_breakadd_cmd(expand_T *xp, char_u *arg, cmdidx_T cmdidx)
return NULL;
}
static char_u *
set_context_in_scriptnames_cmd(expand_T *xp, char_u *arg)
{
char_u *p;
xp->xp_context = EXPAND_NOTHING;
xp->xp_pattern = NULL;
p = skipwhite(arg);
if (VIM_ISDIGIT(*p))
return NULL;
xp->xp_context = EXPAND_SCRIPTNAMES;
xp->xp_pattern = p;
return NULL;
}
#endif
/*
@ -2072,6 +2090,9 @@ set_context_by_cmdname(
case CMD_profdel:
case CMD_breakdel:
return set_context_in_breakadd_cmd(xp, arg, cmdidx);
case CMD_scriptnames:
return set_context_in_scriptnames_cmd(xp, arg);
#endif
default:
@ -2495,6 +2516,23 @@ get_breakadd_arg(expand_T *xp UNUSED, int idx)
}
return NULL;
}
/*
* Function given to ExpandGeneric() to obtain the possible arguments for the
* ":scriptnames" command.
*/
static char_u *
get_scriptnames_arg(expand_T *xp UNUSED, int idx)
{
scriptitem_T *si;
if (!SCRIPT_ID_VALID(idx + 1))
return NULL;
si = SCRIPT_ITEM(idx + 1);
home_replace(NULL, si->sn_name, NameBuff, MAXPATHL, TRUE);
return NameBuff;
}
#endif
/*
@ -2584,6 +2622,7 @@ ExpandOther(
{EXPAND_ARGLIST, get_arglist_name, TRUE, FALSE},
#ifdef FEAT_EVAL
{EXPAND_BREAKPOINT, get_breakadd_arg, TRUE, TRUE},
{EXPAND_SCRIPTNAMES, get_scriptnames_arg, TRUE, FALSE},
#endif
};
int i;
@ -2791,6 +2830,8 @@ ExpandGeneric(
int score = 0;
int fuzzy;
int match;
int sort_matches = FALSE;
int funcsort = FALSE;
fuzzy = cmdline_fuzzy_complete(pat);
*matches = NULL;
@ -2878,14 +2919,25 @@ ExpandGeneric(
if (ga.ga_len == 0)
return OK;
// Sort the results. Keep menu's in the specified order.
// sort the matches when using regular expression matching and sorting
// applies to the completion context. Menus and scriptnames should be kept
// in the specified order.
if (!fuzzy && xp->xp_context != EXPAND_MENUNAMES
&& xp->xp_context != EXPAND_MENUS)
&& xp->xp_context != EXPAND_MENUS
&& xp->xp_context != EXPAND_SCRIPTNAMES)
sort_matches = TRUE;
// <SNR> functions should be sorted to the end.
if (xp->xp_context == EXPAND_EXPRESSION
|| xp->xp_context == EXPAND_FUNCTIONS
|| xp->xp_context == EXPAND_USER_FUNC
|| xp->xp_context == EXPAND_DISASSEMBLE)
funcsort = TRUE;
// Sort the matches.
if (sort_matches)
{
if (xp->xp_context == EXPAND_EXPRESSION
|| xp->xp_context == EXPAND_FUNCTIONS
|| xp->xp_context == EXPAND_USER_FUNC
|| xp->xp_context == EXPAND_DISASSEMBLE)
if (funcsort)
// <SNR> functions should be sorted to the end.
qsort((void *)ga.ga_data, (size_t)ga.ga_len, sizeof(char_u *),
sort_func_compare);
@ -2900,15 +2952,6 @@ ExpandGeneric(
}
else
{
int funcsort = FALSE;
if (xp->xp_context == EXPAND_EXPRESSION
|| xp->xp_context == EXPAND_FUNCTIONS
|| xp->xp_context == EXPAND_USER_FUNC
|| xp->xp_context == EXPAND_DISASSEMBLE)
// <SNR> functions should be sorted to the end.
funcsort = TRUE;
if (fuzzymatches_to_strmatches(ga.ga_data, matches, ga.ga_len,
funcsort) == FAIL)
return FAIL;

View File

@ -1356,7 +1356,7 @@ EXCMD(CMD_sbrewind, "sbrewind", ex_brewind,
EX_CMDARG|EX_TRLBAR,
ADDR_NONE),
EXCMD(CMD_scriptnames, "scriptnames", ex_scriptnames,
EX_BANG|EX_RANGE|EX_COUNT|EX_TRLBAR|EX_CMDWIN|EX_LOCK_OK,
EX_BANG|EX_FILES|EX_RANGE|EX_COUNT|EX_TRLBAR|EX_CMDWIN|EX_LOCK_OK,
ADDR_OTHER),
EXCMD(CMD_scriptencoding, "scriptencoding", ex_scriptencoding,
EX_WORD1|EX_TRLBAR|EX_CMDWIN|EX_LOCK_OK,

View File

@ -1769,14 +1769,20 @@ ex_scriptnames(exarg_T *eap)
{
int i;
if (eap->addr_count > 0)
if (eap->addr_count > 0 || *eap->arg != NUL)
{
// :script {scriptId}: edit the script
if (!SCRIPT_ID_VALID(eap->line2))
if (eap->addr_count > 0 && !SCRIPT_ID_VALID(eap->line2))
emsg(_(e_invalid_argument));
else
{
eap->arg = SCRIPT_ITEM(eap->line2)->sn_name;
if (eap->addr_count > 0)
eap->arg = SCRIPT_ITEM(eap->line2)->sn_name;
else
{
expand_env(eap->arg, NameBuff, MAXPATHL);
eap->arg = NameBuff;
}
do_exedit(eap, NULL);
}
return;

View File

@ -3257,4 +3257,31 @@ func Test_cmdline_complete_breakdel()
call assert_equal("\"breakdel here ", @:)
endfunc
" Test for :scriptnames argument completion
func Test_cmdline_complete_scriptnames()
set wildmenu
call writefile(['let a = 1'], 'Xa1b2c3.vim')
source Xa1b2c3.vim
call feedkeys(":script \<Tab>\<Left>\<Left>\<C-B>\"\<CR>", 'tx')
call assert_match("\"script .*Xa1b2c3.vim$", @:)
call feedkeys(":script \<Tab>\<Left>\<Left>\<C-B>\"\<CR>", 'tx')
call assert_match("\"script .*Xa1b2c3.vim$", @:)
call feedkeys(":script b2c3\<Tab>\<C-B>\"\<CR>", 'tx')
call assert_equal("\"script b2c3", @:)
call feedkeys(":script 2\<Tab>\<C-B>\"\<CR>", 'tx')
call assert_match("\"script 2\<Tab>$", @:)
call feedkeys(":script \<Tab>\<Left>\<Left> \<Tab>\<C-B>\"\<CR>", 'tx')
call assert_match("\"script .*Xa1b2c3.vim $", @:)
call feedkeys(":script \<Tab>\<Left>\<C-B>\"\<CR>", 'tx')
call assert_equal("\"script ", @:)
call assert_match('Xa1b2c3.vim$', getcompletion('.*Xa1b2.*', 'scriptnames')[0])
call assert_equal([], getcompletion('Xa1b2', 'scriptnames'))
new
call feedkeys(":script \<Tab>\<Left>\<Left>\<CR>", 'tx')
call assert_equal('Xa1b2c3.vim', fnamemodify(@%, ':t'))
bw!
call delete('Xa1b2c3.vim')
set wildmenu&
endfunc
" vim: shiftwidth=2 sts=2 expandtab

View File

@ -6202,4 +6202,39 @@ func Test_getqflist_wiped_out_buffer()
%bw!
endfunc
" Test for the status message that is displayed when opening a new quickfix
" list
func Test_qflist_statusmsg()
cexpr "1\n2"
cexpr "1\n2\n3\ntest_quickfix.vim:1:msg"
call assert_equal('(4 of 4): msg', v:statusmsg)
call setqflist([], 'f')
%bw!
" When creating a new quickfix list, if an autocmd changes the quickfix list
" in the stack, then an error message should be displayed.
augroup QF_Test
au!
au BufEnter test_quickfix.vim colder
augroup END
cexpr "1\n2"
call assert_fails('cexpr "1\n2\n3\ntest_quickfix.vim:1:msg"', 'E925:')
call setqflist([], 'f')
augroup QF_Test
au!
augroup END
%bw!
augroup QF_Test
au!
au BufEnter test_quickfix.vim caddexpr "4"
augroup END
call assert_fails('cexpr "1\n2\n3\ntest_quickfix.vim:1:msg"', 'E925:')
call setqflist([], 'f')
augroup QF_Test
au!
augroup END
%bw!
endfunc
" vim: shiftwidth=2 sts=2 expandtab

View File

@ -93,6 +93,7 @@ static struct
{EXPAND_USER_VARS, "var"},
#if defined(FEAT_EVAL)
{EXPAND_BREAKPOINT, "breakpoint"},
{EXPAND_SCRIPTNAMES, "scriptnames"},
#endif
{0, NULL}
};

View File

@ -750,6 +750,8 @@ static char *(features[]) =
static int included_patches[] =
{ /* Add new patch number below this line */
/**/
4617,
/**/
4616,
/**/

View File

@ -802,6 +802,7 @@ extern int (*dyn_libintl_wputenv)(const wchar_t *envstring);
#define EXPAND_DIFF_BUFFERS 49
#define EXPAND_DISASSEMBLE 50
#define EXPAND_BREAKPOINT 51
#define EXPAND_SCRIPTNAMES 52
// Values for exmode_active (0 is no exmode)
#define EXMODE_NORMAL 1