mirror of
https://github.com/neovim/neovim.git
synced 2025-10-02 07:58:35 +00:00
startup: wait for embedder before executing startup commands and files
Give embeders a chance to set up nvim, by processing a request before startup. This allows an external UI to show messages and prompts from --cmd and buffer loading (e.g. swap files)
This commit is contained in:
@@ -344,6 +344,24 @@ int main(int argc, char **argv)
|
||||
p_lpl = false;
|
||||
}
|
||||
|
||||
// give embedders a chance to set up nvim, by processing a request before
|
||||
// startup. This allows an external UI to show messages and prompts from
|
||||
// --cmd and buffer loading (e.g. swap files)
|
||||
bool early_ui = false;
|
||||
if (embedded_mode) {
|
||||
TIME_MSG("waiting for embedder to make request");
|
||||
rpc_wait_for_request();
|
||||
TIME_MSG("done waiting for embedder");
|
||||
|
||||
if (ui_active()) {
|
||||
// prepare screen now, so external UIs can display messages
|
||||
starting = NO_BUFFERS;
|
||||
screenclear();
|
||||
early_ui = true;
|
||||
TIME_MSG("initialized screen early for embedder");
|
||||
}
|
||||
}
|
||||
|
||||
// Execute --cmd arguments.
|
||||
exe_pre_commands(¶ms);
|
||||
|
||||
@@ -456,8 +474,10 @@ int main(int argc, char **argv)
|
||||
|
||||
setmouse(); // may start using the mouse
|
||||
|
||||
if (exmode_active) {
|
||||
must_redraw = CLEAR; // Don't clear the screen when starting in Ex mode.
|
||||
if (exmode_active || early_ui) {
|
||||
// Don't clear the screen when starting in Ex mode, or when an
|
||||
// embedding UI might have displayed messages
|
||||
must_redraw = CLEAR;
|
||||
} else {
|
||||
screenclear(); // clear screen
|
||||
TIME_MSG("clearing screen");
|
||||
|
@@ -40,6 +40,8 @@
|
||||
static PMap(cstr_t) *event_strings = NULL;
|
||||
static msgpack_sbuffer out_buffer;
|
||||
|
||||
static bool got_stdio_request = false;
|
||||
|
||||
#ifdef INCLUDE_GENERATED_DECLARATIONS
|
||||
# include "msgpack_rpc/channel.c.generated.h"
|
||||
#endif
|
||||
@@ -329,6 +331,9 @@ static void handle_request(Channel *channel, msgpack_object *request)
|
||||
send_error(channel, request_id, error.msg);
|
||||
api_clear_error(&error);
|
||||
api_free_array(args);
|
||||
if (channel->id == CHAN_STDIO) {
|
||||
got_stdio_request = true;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -344,6 +349,9 @@ static void handle_request(Channel *channel, msgpack_object *request)
|
||||
if (is_get_mode && !input_blocking()) {
|
||||
// Defer the event to a special queue used by os/input.c. #6247
|
||||
multiqueue_put(ch_before_blocking_events, on_request_event, 1, evdata);
|
||||
if (channel->id == CHAN_STDIO) {
|
||||
got_stdio_request = true;
|
||||
}
|
||||
} else {
|
||||
// Invoke immediately.
|
||||
on_request_event((void **)&evdata);
|
||||
@@ -378,6 +386,11 @@ static void on_request_event(void **argv)
|
||||
channel_decref(channel);
|
||||
xfree(e);
|
||||
api_clear_error(&error);
|
||||
bool is_api_info = handler.fn == handle_nvim_get_api_info;
|
||||
// api info is used to initiate client library, ignore it
|
||||
if (channel->id == CHAN_STDIO && !is_api_info) {
|
||||
got_stdio_request = true;
|
||||
}
|
||||
}
|
||||
|
||||
static bool channel_write(Channel *channel, WBuffer *buffer)
|
||||
@@ -744,3 +757,16 @@ static void log_msg_close(FILE *f, msgpack_object msg)
|
||||
}
|
||||
#endif
|
||||
|
||||
/// Wait until embedder has done a request
|
||||
void rpc_wait_for_request(void)
|
||||
{
|
||||
Channel *channel = find_rpc_channel(CHAN_STDIO);
|
||||
if (!channel) {
|
||||
// this function should only be called in --embed mode, stdio channel
|
||||
// can be assumed.
|
||||
abort();
|
||||
}
|
||||
|
||||
LOOP_PROCESS_EVENTS_UNTIL(&main_loop, channel->events, -1, got_stdio_request);
|
||||
}
|
||||
|
||||
|
@@ -6332,7 +6332,6 @@ int load_colors(char_u *name)
|
||||
apply_autocmds(EVENT_COLORSCHEME, name, curbuf->b_fname, FALSE, curbuf);
|
||||
|
||||
recursive = false;
|
||||
ui_refresh();
|
||||
|
||||
return retval;
|
||||
}
|
||||
@@ -6885,7 +6884,7 @@ void do_highlight(const char *line, const bool forceit, const bool init)
|
||||
// "fg", which have been changed now.
|
||||
highlight_attr_set_all();
|
||||
|
||||
if (!ui_is_external(kUINewgrid)) {
|
||||
if (!ui_is_external(kUINewgrid) && starting != NO_SCREEN) {
|
||||
// Older UIs assume that we clear the screen after normal group is
|
||||
// changed
|
||||
ui_refresh();
|
||||
|
Reference in New Issue
Block a user