patch 9.1.0908: not possible to configure :messages
Problem: not possible to configure :messages
Solution: add the 'messagesopt' option (Shougo Matsushita)
closes: #16068
Co-authored-by: h_east <h.east.727@gmail.com>
Signed-off-by: Shougo Matsushita <Shougo.Matsu@gmail.com>
Signed-off-by: Christian Brabandt <cb@256bit.org>
diff --git a/src/message.c b/src/message.c
index 15eaaae..34a2692 100644
--- a/src/message.c
+++ b/src/message.c
@@ -16,6 +16,7 @@
#include "vim.h"
static void add_msg_hist(char_u *s, int len, int attr);
+static void check_msg_hist(void);
static void hit_return_msg(void);
static void msg_home_replace_attr(char_u *fname, int attr);
static void msg_puts_attr_len(char *str, int maxlen, int attr);
@@ -51,6 +52,21 @@
static struct msg_hist *first_msg_hist = NULL;
static struct msg_hist *last_msg_hist = NULL;
static int msg_hist_len = 0;
+static int msg_hist_max = 500; // The default max value is 500
+
+// flags obtained from the 'messagesopt' option
+#define MESSAGES_HIT_ENTER 0x001
+#define MESSAGES_WAIT 0x002
+#define MESSAGES_HISTORY 0x004
+
+// args in 'messagesopt' option
+#define MESSAGES_OPT_HIT_ENTER "hit-enter"
+#define MESSAGES_OPT_WAIT "wait:"
+#define MESSAGES_OPT_HISTORY "history:"
+
+// The default is "hit-enter,history:500"
+static int msg_flags = MESSAGES_HIT_ENTER | MESSAGES_HISTORY;
+static int msg_wait = 0;
static FILE *verbose_fd = NULL;
static int verbose_did_open = FALSE;
@@ -1060,14 +1076,76 @@
return OK;
}
- void
+ static void
check_msg_hist(void)
{
// Don't let the message history get too big
- while (msg_hist_len > 0 && msg_hist_len > p_mhi)
+ while (msg_hist_len > 0 && msg_hist_len > msg_hist_max)
(void)delete_first_msg();
}
+
+ int
+messagesopt_changed(void)
+{
+ char_u *p;
+ int messages_flags_new = 0;
+ int messages_wait_new = 0;
+ int messages_history_new = 0;
+
+ p = p_meo;
+ while (*p != NUL)
+ {
+ if (STRNCMP(p, MESSAGES_OPT_HIT_ENTER,
+ STRLEN_LITERAL(MESSAGES_OPT_HIT_ENTER)) == 0)
+ {
+ p += STRLEN_LITERAL(MESSAGES_OPT_HIT_ENTER);
+ messages_flags_new |= MESSAGES_HIT_ENTER;
+ }
+ else if (STRNCMP(p, MESSAGES_OPT_WAIT,
+ STRLEN_LITERAL(MESSAGES_OPT_WAIT)) == 0
+ && VIM_ISDIGIT(p[STRLEN_LITERAL(MESSAGES_OPT_WAIT)]))
+ {
+ p += STRLEN_LITERAL(MESSAGES_OPT_WAIT);
+ messages_wait_new = getdigits(&p);
+ messages_flags_new |= MESSAGES_WAIT;
+ }
+ else if (STRNCMP(p, MESSAGES_OPT_HISTORY,
+ STRLEN_LITERAL(MESSAGES_OPT_HISTORY)) == 0
+ && VIM_ISDIGIT(p[STRLEN_LITERAL(MESSAGES_OPT_HISTORY)]))
+ {
+ p += STRLEN_LITERAL(MESSAGES_OPT_HISTORY);
+ messages_history_new = getdigits(&p);
+ messages_flags_new |= MESSAGES_HISTORY;
+ }
+
+ if (*p != ',' && *p != NUL)
+ return FAIL;
+ if (*p == ',')
+ ++p;
+ }
+
+ // Either "wait" or "hit-enter" is required
+ if (!(messages_flags_new & (MESSAGES_HIT_ENTER | MESSAGES_WAIT)))
+ return FAIL;
+
+ // "history" must be set
+ if (!(messages_flags_new & MESSAGES_HISTORY))
+ return FAIL;
+
+ // "history" must be <= 10000
+ if (messages_history_new > 10000)
+ return FAIL;
+
+ msg_flags = messages_flags_new;
+ msg_wait = messages_wait_new;
+
+ msg_hist_max = messages_history_new;
+ check_msg_hist();
+
+ return OK;
+}
+
/*
* ":messages" command.
*/
@@ -1228,118 +1306,127 @@
if (need_check_timestamps)
check_timestamps(FALSE);
- hit_return_msg();
-
- do
+ if (msg_flags & MESSAGES_HIT_ENTER)
{
- // Remember "got_int", if it is set vgetc() probably returns a
- // CTRL-C, but we need to loop then.
- had_got_int = got_int;
+ hit_return_msg();
- // Don't do mappings here, we put the character back in the
- // typeahead buffer.
- ++no_mapping;
- ++allow_keys;
+ do
+ {
+ // Remember "got_int", if it is set vgetc() probably returns a
+ // CTRL-C, but we need to loop then.
+ had_got_int = got_int;
- // Temporarily disable Recording. If Recording is active, the
- // character will be recorded later, since it will be added to the
- // typebuf after the loop
- save_reg_recording = reg_recording;
- save_scriptout = scriptout;
- reg_recording = 0;
- scriptout = NULL;
- c = safe_vgetc();
- if (had_got_int && !global_busy)
- got_int = FALSE;
- --no_mapping;
- --allow_keys;
- reg_recording = save_reg_recording;
- scriptout = save_scriptout;
+ // Don't do mappings here, we put the character back in the
+ // typeahead buffer.
+ ++no_mapping;
+ ++allow_keys;
+
+ // Temporarily disable Recording. If Recording is active, the
+ // character will be recorded later, since it will be added to the
+ // typebuf after the loop
+ save_reg_recording = reg_recording;
+ save_scriptout = scriptout;
+ reg_recording = 0;
+ scriptout = NULL;
+ c = safe_vgetc();
+ if (had_got_int && !global_busy)
+ got_int = FALSE;
+ --no_mapping;
+ --allow_keys;
+ reg_recording = save_reg_recording;
+ scriptout = save_scriptout;
#ifdef FEAT_CLIPBOARD
- // Strange way to allow copying (yanking) a modeless selection at
- // the hit-enter prompt. Use CTRL-Y, because the same is used in
- // Cmdline-mode and it's harmless when there is no selection.
- if (c == Ctrl_Y && clip_star.state == SELECT_DONE)
- {
- clip_copy_modeless_selection(TRUE);
- c = K_IGNORE;
- }
-#endif
-
- /*
- * Allow scrolling back in the messages.
- * Also accept scroll-down commands when messages fill the screen,
- * to avoid that typing one 'j' too many makes the messages
- * disappear.
- */
- if (p_more && !p_cp)
- {
- if (c == 'b' || c == 'k' || c == 'u' || c == 'g'
- || c == K_UP || c == K_PAGEUP)
+ // Strange way to allow copying (yanking) a modeless selection at
+ // the hit-enter prompt. Use CTRL-Y, because the same is used in
+ // Cmdline-mode and it's harmless when there is no selection.
+ if (c == Ctrl_Y && clip_star.state == SELECT_DONE)
{
- if (msg_scrolled > Rows)
- // scroll back to show older messages
- do_more_prompt(c);
- else
- {
- msg_didout = FALSE;
- c = K_IGNORE;
- msg_col =
-#ifdef FEAT_RIGHTLEFT
- cmdmsg_rl ? Columns - 1 :
-#endif
- 0;
- }
- if (quit_more)
- {
- c = CAR; // just pretend CR was hit
- quit_more = FALSE;
- got_int = FALSE;
- }
- else if (c != K_IGNORE)
- {
- c = K_IGNORE;
- hit_return_msg();
- }
- }
- else if (msg_scrolled > Rows - 2
- && (c == 'j' || c == 'd' || c == 'f'
- || c == K_DOWN || c == K_PAGEDOWN))
+ clip_copy_modeless_selection(TRUE);
c = K_IGNORE;
- }
- } while ((had_got_int && c == Ctrl_C)
- || c == K_IGNORE
-#ifdef FEAT_GUI
- || c == K_VER_SCROLLBAR || c == K_HOR_SCROLLBAR
+ }
#endif
- || c == K_LEFTDRAG || c == K_LEFTRELEASE
- || c == K_MIDDLEDRAG || c == K_MIDDLERELEASE
- || c == K_RIGHTDRAG || c == K_RIGHTRELEASE
- || c == K_MOUSELEFT || c == K_MOUSERIGHT
- || c == K_MOUSEDOWN || c == K_MOUSEUP
- || c == K_MOUSEMOVE
- || (!mouse_has(MOUSE_RETURN)
- && mouse_row < msg_row
- && (c == K_LEFTMOUSE
- || c == K_MIDDLEMOUSE
- || c == K_RIGHTMOUSE
- || c == K_X1MOUSE
- || c == K_X2MOUSE))
- );
- ui_breakcheck();
- // Avoid that the mouse-up event causes Visual mode to start.
- if (c == K_LEFTMOUSE || c == K_MIDDLEMOUSE || c == K_RIGHTMOUSE
- || c == K_X1MOUSE || c == K_X2MOUSE)
- (void)jump_to_mouse(MOUSE_SETPOS, NULL, 0);
- else if (vim_strchr((char_u *)"\r\n ", c) == NULL && c != Ctrl_C)
+ /*
+ * Allow scrolling back in the messages.
+ * Also accept scroll-down commands when messages fill the screen,
+ * to avoid that typing one 'j' too many makes the messages
+ * disappear.
+ */
+ if (p_more && !p_cp)
+ {
+ if (c == 'b' || c == 'k' || c == 'u' || c == 'g'
+ || c == K_UP || c == K_PAGEUP)
+ {
+ if (msg_scrolled > Rows)
+ // scroll back to show older messages
+ do_more_prompt(c);
+ else
+ {
+ msg_didout = FALSE;
+ c = K_IGNORE;
+ msg_col =
+#ifdef FEAT_RIGHTLEFT
+ cmdmsg_rl ? Columns - 1 :
+#endif
+ 0;
+ }
+ if (quit_more)
+ {
+ c = CAR; // just pretend CR was hit
+ quit_more = FALSE;
+ got_int = FALSE;
+ }
+ else if (c != K_IGNORE)
+ {
+ c = K_IGNORE;
+ hit_return_msg();
+ }
+ }
+ else if (msg_scrolled > Rows - 2
+ && (c == 'j' || c == 'd' || c == 'f'
+ || c == K_DOWN || c == K_PAGEDOWN))
+ c = K_IGNORE;
+ }
+ } while ((had_got_int && c == Ctrl_C)
+ || c == K_IGNORE
+#ifdef FEAT_GUI
+ || c == K_VER_SCROLLBAR || c == K_HOR_SCROLLBAR
+#endif
+ || c == K_LEFTDRAG || c == K_LEFTRELEASE
+ || c == K_MIDDLEDRAG || c == K_MIDDLERELEASE
+ || c == K_RIGHTDRAG || c == K_RIGHTRELEASE
+ || c == K_MOUSELEFT || c == K_MOUSERIGHT
+ || c == K_MOUSEDOWN || c == K_MOUSEUP
+ || c == K_MOUSEMOVE
+ || (!mouse_has(MOUSE_RETURN)
+ && mouse_row < msg_row
+ && (c == K_LEFTMOUSE
+ || c == K_MIDDLEMOUSE
+ || c == K_RIGHTMOUSE
+ || c == K_X1MOUSE
+ || c == K_X2MOUSE))
+ );
+ ui_breakcheck();
+
+ // Avoid that the mouse-up event causes Visual mode to start.
+ if (c == K_LEFTMOUSE || c == K_MIDDLEMOUSE || c == K_RIGHTMOUSE
+ || c == K_X1MOUSE || c == K_X2MOUSE)
+ (void)jump_to_mouse(MOUSE_SETPOS, NULL, 0);
+ else if (vim_strchr((char_u *)"\r\n ", c) == NULL && c != Ctrl_C)
+ {
+ // Put the character back in the typeahead buffer. Don't use the
+ // stuff buffer, because lmaps wouldn't work.
+ ins_char_typebuf(vgetc_char, vgetc_mod_mask);
+ do_redraw = TRUE; // need a redraw even though there is
+ // typeahead
+ }
+ }
+ else
{
- // Put the character back in the typeahead buffer. Don't use the
- // stuff buffer, because lmaps wouldn't work.
- ins_char_typebuf(vgetc_char, vgetc_mod_mask);
- do_redraw = TRUE; // need a redraw even though there is
- // typeahead
+ c = CAR;
+ // Wait to allow the user to verify the output.
+ do_sleep(msg_wait, TRUE);
}
}
redir_off = FALSE;