mirror of
https://github.com/neovim/neovim
synced 2025-07-16 09:11:51 +00:00
feat(ui): "append" parameter for "msg_show" UI events
Problem: Consecutive "msg_show" events stemming from an `:echon` command are supposed to be appended without a newline, this information is not encoded in the "msg_show" event. Solution: Add an "append" parameter to the "msg_show" event that is set to true to indicate the message should not start on a new line. Considered alternative: Emit a newline for the common case instead at the start of a new message. That way UIs can more closely follow the logic as it is implemented for the message grid currently. This would be a breaking change. The "append" parameter seems OK.
This commit is contained in:
@ -141,6 +141,7 @@ EDITOR
|
||||
EVENTS
|
||||
|
||||
• |CmdlineLeavePre| triggered before preparing to leave the command line.
|
||||
• New `append` paremeter for |ui-messages| `msg_show` event.
|
||||
|
||||
HIGHLIGHTS
|
||||
|
||||
|
@ -810,7 +810,7 @@ will be set to zero, but can be changed and used for the replacing cmdline or
|
||||
message window. Cmdline state is emitted as |ui-cmdline| events, which the UI
|
||||
must handle.
|
||||
|
||||
["msg_show", kind, content, replace_last, history] ~
|
||||
["msg_show", kind, content, replace_last, history, append] ~
|
||||
Display a message to the user.
|
||||
|
||||
kind
|
||||
@ -860,6 +860,10 @@ must handle.
|
||||
history
|
||||
True if the message was added to the |:messages| history.
|
||||
|
||||
append
|
||||
True if the message should be appeneded to the previous message,
|
||||
rather than started on a new line. Is set for |:echon|.
|
||||
|
||||
["msg_clear"] ~
|
||||
Clear all messages currently displayed by "msg_show". (Messages sent
|
||||
by other "msg_" events below will not be affected).
|
||||
|
@ -160,7 +160,7 @@ void wildmenu_select(Integer selected)
|
||||
void wildmenu_hide(void)
|
||||
FUNC_API_SINCE(3) FUNC_API_REMOTE_ONLY;
|
||||
|
||||
void msg_show(String kind, Array content, Boolean replace_last, Boolean history)
|
||||
void msg_show(String kind, Array content, Boolean replace_last, Boolean history, Boolean append)
|
||||
FUNC_API_SINCE(6) FUNC_API_FAST FUNC_API_REMOTE_ONLY;
|
||||
void msg_clear(void)
|
||||
FUNC_API_SINCE(6) FUNC_API_REMOTE_ONLY;
|
||||
|
@ -7863,6 +7863,7 @@ void ex_echo(exarg_T *eap)
|
||||
char *tofree = encode_tv2echo(&rettv, NULL);
|
||||
if (*tofree != NUL) {
|
||||
msg_ext_set_kind("echo");
|
||||
msg_ext_append = eap->cmdidx == CMD_echon;
|
||||
msg_multiline(cstr_as_string(tofree), echo_hl_id, true, false, &need_clear);
|
||||
}
|
||||
xfree(tofree);
|
||||
|
@ -3185,7 +3185,8 @@ void msg_ext_ui_flush(void)
|
||||
msg_ext_emit_chunk();
|
||||
if (msg_ext_chunks->size > 0) {
|
||||
Array *tofree = msg_ext_init_chunks();
|
||||
ui_call_msg_show(cstr_as_string(msg_ext_kind), *tofree, msg_ext_overwrite, msg_ext_history);
|
||||
ui_call_msg_show(cstr_as_string(msg_ext_kind), *tofree, msg_ext_overwrite, msg_ext_history,
|
||||
msg_ext_append);
|
||||
if (msg_ext_history || strequal(msg_ext_kind, "return_prompt")) {
|
||||
api_free_array(*tofree);
|
||||
} else {
|
||||
@ -3205,6 +3206,7 @@ void msg_ext_ui_flush(void)
|
||||
}
|
||||
msg_ext_overwrite = false;
|
||||
msg_ext_history = false;
|
||||
msg_ext_append = false;
|
||||
msg_ext_kind = NULL;
|
||||
}
|
||||
}
|
||||
|
@ -33,6 +33,8 @@ extern MessageHistoryEntry *msg_hist_last;
|
||||
EXTERN bool msg_ext_need_clear INIT( = false);
|
||||
// Set to true to force grouping a set of message chunks into a single `cmdline_show` event.
|
||||
EXTERN bool msg_ext_skip_flush INIT( = false);
|
||||
// Set to true when message should be appended to previous message line.
|
||||
EXTERN bool msg_ext_append INIT( = false);
|
||||
|
||||
/// allocated grid for messages. Used unless ext_messages is active.
|
||||
/// See also the description at msg_scroll_flush()
|
||||
|
@ -221,7 +221,6 @@ describe('vim.ui_attach', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { '\nSave changes?\n', 6, 10 } },
|
||||
history = false,
|
||||
kind = 'confirm',
|
||||
},
|
||||
},
|
||||
@ -477,7 +476,6 @@ describe('vim.ui_attach', function()
|
||||
},
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 100, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -530,7 +528,6 @@ describe('vim.ui_attach', function()
|
||||
},
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 100, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
|
@ -60,7 +60,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { '\ntest\n', 6, 10 } },
|
||||
history = false,
|
||||
kind = 'confirm',
|
||||
},
|
||||
},
|
||||
@ -92,7 +91,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { '\ntest\n', 6, 10 } },
|
||||
history = false,
|
||||
kind = 'confirm',
|
||||
},
|
||||
},
|
||||
@ -104,17 +102,14 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { '\ntest\n', 6, 10 } },
|
||||
history = false,
|
||||
kind = 'confirm',
|
||||
},
|
||||
{
|
||||
content = { { '1' } },
|
||||
history = false,
|
||||
kind = 'echo',
|
||||
},
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -214,7 +209,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { '?line ' } },
|
||||
history = false,
|
||||
kind = 'search_cmd',
|
||||
},
|
||||
},
|
||||
@ -238,7 +232,6 @@ describe('ui/ext_messages', function()
|
||||
{ 'links to', 18, 5 },
|
||||
{ ' SpecialChar' },
|
||||
},
|
||||
history = false,
|
||||
kind = 'list_cmd',
|
||||
},
|
||||
},
|
||||
@ -285,7 +278,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { 'The only match' } },
|
||||
history = false,
|
||||
kind = 'completion',
|
||||
},
|
||||
},
|
||||
@ -337,12 +329,10 @@ describe('ui/ext_messages', function()
|
||||
{ 'guibg=', 18, 5 },
|
||||
{ 'LightBlue' },
|
||||
},
|
||||
history = false,
|
||||
kind = 'list_cmd',
|
||||
},
|
||||
{
|
||||
content = { { '\n\tLast set from Lua (run Nvim with -V1 for more details)' } },
|
||||
history = false,
|
||||
kind = 'verbose',
|
||||
},
|
||||
{
|
||||
@ -355,17 +345,14 @@ describe('ui/ext_messages', function()
|
||||
{ 'guibg=', 18, 5 },
|
||||
{ 'LightMagenta' },
|
||||
},
|
||||
history = false,
|
||||
kind = 'list_cmd',
|
||||
},
|
||||
{
|
||||
content = { { '\n\tLast set from Lua (run Nvim with -V1 for more details)' } },
|
||||
history = false,
|
||||
kind = 'verbose',
|
||||
},
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -406,7 +393,6 @@ describe('ui/ext_messages', function()
|
||||
},
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -462,27 +448,22 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { (':!%s\r\n[No write since last change]\n'):format(cmd) } },
|
||||
history = false,
|
||||
kind = 'shell_cmd',
|
||||
},
|
||||
{
|
||||
content = { { ('stdout%s\n'):format(t.is_os('win') and '\r' or '') } },
|
||||
history = false,
|
||||
kind = 'shell_out',
|
||||
},
|
||||
{
|
||||
content = { { ('stderr%s\n'):format(t.is_os('win') and '\r' or ''), 9, 71 } },
|
||||
history = false,
|
||||
kind = 'shell_err',
|
||||
},
|
||||
{
|
||||
content = { { '\nshell returned 3\n\n' } },
|
||||
history = false,
|
||||
kind = 'shell_ret',
|
||||
},
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -497,7 +478,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { '\nType Name Content', 101, 23 }, { '\n c ". ' } },
|
||||
history = false,
|
||||
kind = 'list_cmd',
|
||||
},
|
||||
},
|
||||
@ -517,7 +497,6 @@ describe('ui/ext_messages', function()
|
||||
{ 'ChanInfo', 101, 23 },
|
||||
{ '\n*foo' },
|
||||
},
|
||||
history = false,
|
||||
kind = 'list_cmd',
|
||||
},
|
||||
},
|
||||
@ -534,7 +513,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { 'line 1\nline ' } },
|
||||
history = false,
|
||||
kind = 'list_cmd',
|
||||
},
|
||||
},
|
||||
@ -592,7 +570,6 @@ describe('ui/ext_messages', function()
|
||||
},
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -623,7 +600,6 @@ describe('ui/ext_messages', function()
|
||||
},
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -688,7 +664,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -731,7 +706,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -757,7 +731,7 @@ describe('ui/ext_messages', function()
|
||||
]],
|
||||
cmdline = { { abort = false } },
|
||||
messages = {
|
||||
{ content = { { '/line W [1/2]' } }, kind = 'search_count', history = false },
|
||||
{ content = { { '/line W [1/2]' } }, kind = 'search_count' },
|
||||
},
|
||||
}
|
||||
|
||||
@ -769,7 +743,7 @@ describe('ui/ext_messages', function()
|
||||
{1:~ }|*3
|
||||
]],
|
||||
messages = {
|
||||
{ content = { { '/line [2/2]' } }, kind = 'search_count', history = false },
|
||||
{ content = { { '/line [2/2]' } }, kind = 'search_count' },
|
||||
},
|
||||
}
|
||||
end)
|
||||
@ -784,11 +758,10 @@ describe('ui/ext_messages', function()
|
||||
]],
|
||||
cmdline = { { abort = false } },
|
||||
messages = {
|
||||
{ content = { { 'x #1' } }, kind = 'list_cmd', history = false },
|
||||
{ content = { { 'y #2' } }, kind = 'list_cmd', history = false },
|
||||
{ content = { { 'x #1' } }, kind = 'list_cmd' },
|
||||
{ content = { { 'y #2' } }, kind = 'list_cmd' },
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -908,7 +881,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -1156,7 +1128,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { 'xyz' } },
|
||||
history = false,
|
||||
kind = 'echo',
|
||||
},
|
||||
},
|
||||
@ -1194,7 +1165,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -1326,7 +1296,6 @@ stack traceback:
|
||||
{ '*', 18, 1 },
|
||||
{ ' k' },
|
||||
},
|
||||
history = false,
|
||||
kind = 'list_cmd',
|
||||
},
|
||||
},
|
||||
@ -1347,7 +1316,6 @@ stack traceback:
|
||||
messages = {
|
||||
{
|
||||
content = { { 'wildmenu wildmode\n' } },
|
||||
history = false,
|
||||
kind = 'wildlist',
|
||||
},
|
||||
},
|
||||
@ -1382,7 +1350,6 @@ stack traceback:
|
||||
messages = {
|
||||
{
|
||||
content = { { 'Change "helllo" to:\n 1 "Hello"\n 2 "Hallo"\n 3 "Hullo"' } },
|
||||
history = false,
|
||||
kind = 'confirm',
|
||||
},
|
||||
},
|
||||
@ -1405,7 +1372,6 @@ stack traceback:
|
||||
messages = {
|
||||
{
|
||||
content = { { 'Change "helllo" to:\n 1 "Hello"\n 2 "Hallo"\n 3 "Hullo"' } },
|
||||
history = false,
|
||||
kind = 'confirm',
|
||||
},
|
||||
},
|
||||
@ -1437,7 +1403,6 @@ stack traceback:
|
||||
messages = {
|
||||
{
|
||||
content = { { 'input0\ninput1' } },
|
||||
history = false,
|
||||
kind = 'confirm',
|
||||
},
|
||||
},
|
||||
@ -1487,7 +1452,6 @@ stack traceback:
|
||||
{
|
||||
content = { { '\n 1 %a "[No Name]" line 1' } },
|
||||
kind = 'list_cmd',
|
||||
history = false,
|
||||
},
|
||||
},
|
||||
}
|
||||
@ -1502,7 +1466,6 @@ stack traceback:
|
||||
messages = {
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -1631,11 +1594,7 @@ stack traceback:
|
||||
{1:~ }|*4
|
||||
]],
|
||||
messages = {
|
||||
{
|
||||
content = { { 'bar' } },
|
||||
history = false,
|
||||
kind = 'echo',
|
||||
},
|
||||
{ content = { { 'bar' } }, kind = 'echo' },
|
||||
},
|
||||
})
|
||||
feed('g<lt>')
|
||||
@ -1647,7 +1606,6 @@ stack traceback:
|
||||
messages = {
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -1685,7 +1643,6 @@ stack traceback:
|
||||
messages = {
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -1708,7 +1665,6 @@ stack traceback:
|
||||
messages = {
|
||||
{
|
||||
content = { { ' shiftwidth=8\n tabstop=8\n softtabstop=0' } },
|
||||
history = false,
|
||||
kind = 'list_cmd',
|
||||
},
|
||||
},
|
||||
@ -1730,6 +1686,25 @@ stack traceback:
|
||||
{1:~ }|*4
|
||||
]])
|
||||
end)
|
||||
|
||||
it(':echon sets append', function()
|
||||
command('echo "foo" | echon " bar" | echon " baz"')
|
||||
screen:expect({
|
||||
grid = [[
|
||||
^ |
|
||||
{1:~ }|*4
|
||||
]],
|
||||
messages = {
|
||||
{ content = { { 'foo' } }, kind = 'echo' },
|
||||
{ content = { { ' bar' } }, kind = 'echo', append = true },
|
||||
{ content = { { ' baz' } }, kind = 'echo', append = true },
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
})
|
||||
end)
|
||||
end)
|
||||
|
||||
describe('ui/builtin messages', function()
|
||||
@ -2394,7 +2369,6 @@ describe('ui/ext_messages', function()
|
||||
messages = {
|
||||
{
|
||||
content = { { 'Press ENTER or type command to continue', 6, 18 } },
|
||||
history = false,
|
||||
kind = 'return_prompt',
|
||||
},
|
||||
},
|
||||
@ -2476,7 +2450,7 @@ describe('ui/ext_messages', function()
|
||||
]],
|
||||
cmdline = { { abort = false } },
|
||||
messages = {
|
||||
{ content = { { ' cmdheight=0' } }, kind = 'list_cmd', history = false },
|
||||
{ content = { { ' cmdheight=0' } }, kind = 'list_cmd' },
|
||||
},
|
||||
})
|
||||
|
||||
@ -2493,7 +2467,7 @@ describe('ui/ext_messages', function()
|
||||
]],
|
||||
cmdline = { { abort = false } },
|
||||
messages = {
|
||||
{ content = { { ' laststatus=3' } }, kind = 'list_cmd', history = false },
|
||||
{ content = { { ' laststatus=3' } }, kind = 'list_cmd' },
|
||||
},
|
||||
})
|
||||
|
||||
@ -2514,7 +2488,7 @@ describe('ui/ext_messages', function()
|
||||
]],
|
||||
cmdline = { { abort = false } },
|
||||
messages = {
|
||||
{ content = { { ' cmdheight=0' } }, kind = 'list_cmd', history = false },
|
||||
{ content = { { ' cmdheight=0' } }, kind = 'list_cmd' },
|
||||
},
|
||||
})
|
||||
end)
|
||||
|
@ -1383,12 +1383,12 @@ function Screen:_handle_wildmenu_hide()
|
||||
self.wildmenu_items, self.wildmenu_pos = nil, nil
|
||||
end
|
||||
|
||||
function Screen:_handle_msg_show(kind, chunks, replace_last, history)
|
||||
function Screen:_handle_msg_show(kind, chunks, replace_last, history, append)
|
||||
local pos = #self.messages
|
||||
if not replace_last or pos == 0 then
|
||||
pos = pos + 1
|
||||
end
|
||||
self.messages[pos] = { kind = kind, content = chunks, history = history }
|
||||
self.messages[pos] = { kind = kind, content = chunks, history = history, append = append }
|
||||
end
|
||||
|
||||
function Screen:_handle_msg_clear()
|
||||
@ -1507,7 +1507,8 @@ function Screen:_extstate_repr(attr_state)
|
||||
messages[i] = {
|
||||
kind = entry.kind,
|
||||
content = self:_chunks_repr(entry.content, attr_state),
|
||||
history = entry.history,
|
||||
history = entry.history or nil,
|
||||
append = entry.append or nil,
|
||||
}
|
||||
end
|
||||
|
||||
|
Reference in New Issue
Block a user