aboutsummaryrefslogtreecommitdiff
path: root/src/nvim/message.c
diff options
context:
space:
mode:
authorJosh Rahm <joshuarahm@gmail.com>2024-11-25 19:15:05 +0000
committerJosh Rahm <joshuarahm@gmail.com>2024-11-25 19:27:38 +0000
commitc5d770d311841ea5230426cc4c868e8db27300a8 (patch)
treedd21f70127b4b8b5f109baefc8ecc5016f507c91 /src/nvim/message.c
parent9be89f131f87608f224f0ee06d199fcd09d32176 (diff)
parent081beb3659bd6d8efc3e977a160b1e72becbd8a2 (diff)
downloadrneovim-c5d770d311841ea5230426cc4c868e8db27300a8.tar.gz
rneovim-c5d770d311841ea5230426cc4c868e8db27300a8.tar.bz2
rneovim-c5d770d311841ea5230426cc4c868e8db27300a8.zip
Merge remote-tracking branch 'upstream/master' into mix_20240309
Diffstat (limited to 'src/nvim/message.c')
-rw-r--r--src/nvim/message.c282
1 files changed, 138 insertions, 144 deletions
diff --git a/src/nvim/message.c b/src/nvim/message.c
index 79e6bc8be7..47f33c8967 100644
--- a/src/nvim/message.c
+++ b/src/nvim/message.c
@@ -36,6 +36,7 @@
#include "nvim/grid.h"
#include "nvim/highlight.h"
#include "nvim/highlight_defs.h"
+#include "nvim/highlight_group.h"
#include "nvim/indent.h"
#include "nvim/input.h"
#include "nvim/keycodes.h"
@@ -73,7 +74,7 @@ struct msgchunk_S {
msgchunk_T *sb_prev;
char sb_eol; // true when line ends after this text
int sb_msg_col; // column in which text starts
- int sb_attr; // text attributes
+ int sb_hl_id; // text highlight id
char sb_text[]; // text to be displayed
};
@@ -118,7 +119,7 @@ bool keep_msg_more = false; // keep_msg was set by msgmore()
// msg_scrolled How many lines the screen has been scrolled (because of
// messages). Used in update_screen() to scroll the screen
// back. Incremented each time the screen scrolls a line.
-// msg_scrolled_ign true when msg_scrolled is non-zero and msg_puts_attr()
+// msg_scrolled_ign true when msg_scrolled is non-zero and msg_puts_hl_id()
// writes something without scrolling should not make
// need_wait_return to be set. This is a hack to make ":ts"
// work without an extra prompt.
@@ -138,6 +139,7 @@ static const char *msg_ext_kind = NULL;
static Array *msg_ext_chunks = NULL;
static garray_T msg_ext_last_chunk = GA_INIT(sizeof(char), 40);
static sattr_T msg_ext_last_attr = -1;
+static int msg_ext_last_hl_id;
static size_t msg_ext_cur_len = 0;
static bool msg_ext_overwrite = false; ///< will overwrite last message
@@ -199,7 +201,7 @@ void msg_grid_validate(void)
ui_call_grid_resize(msg_grid.handle, msg_grid.cols, msg_grid.rows);
msg_scrolled_at_flush = msg_scrolled;
- msg_grid.focusable = false;
+ msg_grid.mouse_enabled = false;
msg_grid_adj.target = &msg_grid;
} else if (!should_alloc && msg_grid.chars) {
ui_comp_remove_grid(&msg_grid);
@@ -231,7 +233,7 @@ void msg_grid_validate(void)
int verb_msg(const char *s)
{
verbose_enter();
- int n = msg_attr_keep(s, 0, false, false);
+ int n = msg_hl_keep(s, 0, false, false);
verbose_leave();
return n;
@@ -241,45 +243,43 @@ int verb_msg(const char *s)
/// When terminal not initialized (yet) printf("%s", ..) is used.
///
/// @return true if wait_return() not called
-bool msg(const char *s, const int attr)
+bool msg(const char *s, const int hl_id)
FUNC_ATTR_NONNULL_ARG(1)
{
- return msg_attr_keep(s, attr, false, false);
+ return msg_hl_keep(s, hl_id, false, false);
}
-/// Similar to msg_outtrans, but support newlines and tabs.
-void msg_multiline(const char *s, int attr, bool check_int, bool *need_clear)
+/// Similar to msg_outtrans_len, but support newlines and tabs.
+void msg_multiline(String str, int hl_id, bool check_int, bool hist, bool *need_clear)
FUNC_ATTR_NONNULL_ALL
{
- const char *next_spec = s;
-
- while (next_spec != NULL) {
+ const char *s = str.data;
+ const char *chunk = s;
+ while ((size_t)(s - str.data) < str.size) {
if (check_int && got_int) {
return;
}
- next_spec = strpbrk(s, "\t\n\r");
-
- if (next_spec != NULL) {
- // Printing all char that are before the char found by strpbrk
- msg_outtrans_len(s, (int)(next_spec - s), attr);
+ if (*s == '\n' || *s == TAB || *s == '\r') {
+ // Print all chars before the delimiter
+ msg_outtrans_len(chunk, (int)(s - chunk), hl_id, hist);
- if (*next_spec != TAB && *need_clear) {
+ if (*s != TAB && *need_clear) {
msg_clr_eos();
*need_clear = false;
}
- msg_putchar_attr((uint8_t)(*next_spec), attr);
- s = next_spec + 1;
+ msg_putchar_hl((uint8_t)(*s), hl_id);
+ chunk = s + 1;
}
+ s++;
}
- // Print the rest of the message. We know there is no special
- // character because strpbrk returned NULL
- if (*s != NUL) {
- msg_outtrans(s, attr);
+ // Print the rest of the message
+ if (*chunk != NUL) {
+ msg_outtrans_len(chunk, (int)(str.size - (size_t)(chunk - str.data)), hl_id, hist);
}
}
-void msg_multiattr(HlMessage hl_msg, const char *kind, bool history)
+void msg_multihl(HlMessage hl_msg, const char *kind, bool history)
{
no_wait_return++;
msg_start();
@@ -288,17 +288,17 @@ void msg_multiattr(HlMessage hl_msg, const char *kind, bool history)
msg_ext_set_kind(kind);
for (uint32_t i = 0; i < kv_size(hl_msg); i++) {
HlMessageChunk chunk = kv_A(hl_msg, i);
- msg_multiline(chunk.text.data, chunk.attr, true, &need_clear);
+ msg_multiline(chunk.text, chunk.hl_id, true, false, &need_clear);
}
if (history && kv_size(hl_msg)) {
- add_msg_hist_multiattr(NULL, 0, 0, true, hl_msg);
+ add_msg_hist_multihl(NULL, 0, 0, true, hl_msg);
}
no_wait_return--;
msg_end();
}
/// @param keep set keep_msg if it doesn't scroll
-bool msg_attr_keep(const char *s, int attr, bool keep, bool multiline)
+bool msg_hl_keep(const char *s, int hl_id, bool keep, bool multiline)
FUNC_ATTR_NONNULL_ALL
{
static int entered = 0;
@@ -316,7 +316,7 @@ bool msg_attr_keep(const char *s, int attr, bool keep, bool multiline)
return true;
}
- if (attr == 0) {
+ if (hl_id == 0) {
set_vim_var_string(VV_STATUSMSG, s, -1);
}
@@ -335,7 +335,7 @@ bool msg_attr_keep(const char *s, int attr, bool keep, bool multiline)
&& last_msg_hist != NULL
&& last_msg_hist->msg != NULL
&& strcmp(s, last_msg_hist->msg) != 0)) {
- add_msg_hist(s, -1, attr, multiline);
+ add_msg_hist(s, -1, hl_id, multiline);
}
// Truncate the message if needed.
@@ -347,9 +347,9 @@ bool msg_attr_keep(const char *s, int attr, bool keep, bool multiline)
bool need_clear = true;
if (multiline) {
- msg_multiline(s, attr, false, &need_clear);
+ msg_multiline(cstr_as_string(s), hl_id, false, false, &need_clear);
} else {
- msg_outtrans(s, attr);
+ msg_outtrans(s, hl_id, false);
}
if (need_clear) {
msg_clr_eos();
@@ -484,7 +484,7 @@ void trunc_string(const char *s, char *buf, int room_in, int buflen)
}
}
-/// Shows a printf-style message with attributes.
+/// Shows a printf-style message with highlight id.
///
/// Note: Caller must check the resulting string is shorter than IOSIZE!!!
///
@@ -492,7 +492,7 @@ void trunc_string(const char *s, char *buf, int room_in, int buflen)
/// @see swmsg
///
/// @param s printf-style format message
-int smsg(int attr, const char *s, ...)
+int smsg(int hl_id, const char *s, ...)
FUNC_ATTR_PRINTF(2, 3)
{
va_list arglist;
@@ -500,10 +500,10 @@ int smsg(int attr, const char *s, ...)
va_start(arglist, s);
vim_vsnprintf(IObuff, IOSIZE, s, arglist);
va_end(arglist);
- return msg(IObuff, attr);
+ return msg(IObuff, hl_id);
}
-int smsg_attr_keep(int attr, const char *s, ...)
+int smsg_hl_keep(int hl_id, const char *s, ...)
FUNC_ATTR_PRINTF(2, 3)
{
va_list arglist;
@@ -511,7 +511,7 @@ int smsg_attr_keep(int attr, const char *s, ...)
va_start(arglist, s);
vim_vsnprintf(IObuff, IOSIZE, s, arglist);
va_end(arglist);
- return msg_attr_keep(IObuff, attr, true, false);
+ return msg_hl_keep(IObuff, hl_id, true, false);
}
// Remember the last sourcing name/lnum used in an error message, so that it
@@ -588,7 +588,7 @@ static char *get_emsg_lnum(void)
/// Display name and line number for the source of an error.
/// Remember the file name and line number, so that for the next error the info
/// is only displayed if it changed.
-void msg_source(int attr)
+void msg_source(int hl_id)
{
static bool recursive = false;
@@ -602,12 +602,12 @@ void msg_source(int attr)
char *p = get_emsg_source();
if (p != NULL) {
msg_scroll = true; // this will take more than one line
- msg(p, attr);
+ msg(p, hl_id);
xfree(p);
}
p = get_emsg_lnum();
if (p != NULL) {
- msg(p, HL_ATTR(HLF_N));
+ msg(p, HLF_N);
xfree(p);
last_sourcing_lnum = SOURCING_LNUM; // only once for each line
}
@@ -736,7 +736,7 @@ bool emsg_multiline(const char *s, bool multiline)
}
emsg_on_display = true; // remember there is an error message
- int attr = HL_ATTR(HLF_E); // set highlight mode for error messages
+ int hl_id = HLF_E; // set highlight mode for error messages
if (msg_scrolled != 0) {
need_wait_return = true; // needed in case emsg() is called after
} // wait_return() has reset need_wait_return
@@ -748,11 +748,11 @@ bool emsg_multiline(const char *s, bool multiline)
// Display name and line number for the source of the error.
msg_scroll = true;
- msg_source(attr);
+ msg_source(hl_id);
// Display the error message itself.
msg_nowait = false; // Wait for this msg.
- return msg_attr_keep(s, attr, false, multiline);
+ return msg_hl_keep(s, hl_id, false, multiline);
}
/// emsg() - display an error message
@@ -907,15 +907,15 @@ void msg_schedule_semsg_multiline(const char *const fmt, ...)
/// Careful: The string may be changed by msg_may_trunc()!
///
/// @return a pointer to the printed message, if wait_return() not called.
-char *msg_trunc(char *s, bool force, int attr)
+char *msg_trunc(char *s, bool force, int hl_id)
{
// Add message to history before truncating.
- add_msg_hist(s, -1, attr, false);
+ add_msg_hist(s, -1, hl_id, false);
char *ts = msg_may_trunc(force, s);
msg_hist_off = true;
- bool n = msg(ts, attr);
+ bool n = msg(ts, hl_id);
msg_hist_off = false;
if (n) {
@@ -965,21 +965,21 @@ void hl_msg_free(HlMessage hl_msg)
}
/// @param[in] len Length of s or -1.
-static void add_msg_hist(const char *s, int len, int attr, bool multiline)
+static void add_msg_hist(const char *s, int len, int hl_id, bool multiline)
{
- add_msg_hist_multiattr(s, len, attr, multiline, (HlMessage)KV_INITIAL_VALUE);
+ add_msg_hist_multihl(s, len, hl_id, multiline, (HlMessage)KV_INITIAL_VALUE);
}
-static void add_msg_hist_multiattr(const char *s, int len, int attr, bool multiline,
- HlMessage multiattr)
+static void add_msg_hist_multihl(const char *s, int len, int hl_id, bool multiline,
+ HlMessage multihl)
{
if (msg_hist_off || msg_silent != 0) {
- hl_msg_free(multiattr);
+ hl_msg_free(multihl);
return;
}
// Don't let the message history get too big
- while (msg_hist_len > MAX_MSG_HIST_LEN) {
+ while (msg_hist_len > p_mhi) {
delete_first_msg();
}
@@ -1002,9 +1002,9 @@ static void add_msg_hist_multiattr(const char *s, int len, int attr, bool multil
p->msg = NULL;
}
p->next = NULL;
- p->attr = attr;
+ p->hl_id = hl_id;
p->multiline = multiline;
- p->multiattr = multiattr;
+ p->multihl = multihl;
p->kind = msg_ext_kind;
if (last_msg_hist != NULL) {
last_msg_hist->next = p;
@@ -1031,7 +1031,7 @@ int delete_first_msg(void)
last_msg_hist = NULL;
}
xfree(p->msg);
- hl_msg_free(p->multiattr);
+ hl_msg_free(p->multihl);
xfree(p);
msg_hist_len--;
return OK;
@@ -1077,22 +1077,24 @@ void ex_messages(exarg_T *eap)
}
Array entries = ARRAY_DICT_INIT;
for (; p != NULL; p = p->next) {
- if (kv_size(p->multiattr) || (p->msg && p->msg[0])) {
+ if (kv_size(p->multihl) || (p->msg && p->msg[0])) {
Array entry = ARRAY_DICT_INIT;
ADD(entry, CSTR_TO_OBJ(p->kind));
Array content = ARRAY_DICT_INIT;
- if (kv_size(p->multiattr)) {
- for (uint32_t i = 0; i < kv_size(p->multiattr); i++) {
- HlMessageChunk chunk = kv_A(p->multiattr, i);
+ if (kv_size(p->multihl)) {
+ for (uint32_t i = 0; i < kv_size(p->multihl); i++) {
+ HlMessageChunk chunk = kv_A(p->multihl, i);
Array content_entry = ARRAY_DICT_INIT;
- ADD(content_entry, INTEGER_OBJ(chunk.attr));
+ ADD(content_entry, INTEGER_OBJ(chunk.hl_id ? syn_id2attr(chunk.hl_id) : 0));
ADD(content_entry, STRING_OBJ(copy_string(chunk.text, NULL)));
+ ADD(content_entry, INTEGER_OBJ(chunk.hl_id));
ADD(content, ARRAY_OBJ(content_entry));
}
} else if (p->msg && p->msg[0]) {
Array content_entry = ARRAY_DICT_INIT;
- ADD(content_entry, INTEGER_OBJ(p->attr));
+ ADD(content_entry, INTEGER_OBJ(p->hl_id ? syn_id2attr(p->hl_id) : 0));
ADD(content_entry, CSTR_TO_OBJ(p->msg));
+ ADD(content_entry, INTEGER_OBJ(p->hl_id));
ADD(content, ARRAY_OBJ(content_entry));
}
ADD(entry, ARRAY_OBJ(content));
@@ -1106,10 +1108,10 @@ void ex_messages(exarg_T *eap)
} else {
msg_hist_off = true;
for (; p != NULL && !got_int; p = p->next) {
- if (kv_size(p->multiattr)) {
- msg_multiattr(p->multiattr, p->kind, false);
+ if (kv_size(p->multihl)) {
+ msg_multihl(p->multihl, p->kind, false);
} else if (p->msg != NULL) {
- msg_attr_keep(p->msg, p->attr, false, p->multiline);
+ msg_hl_keep(p->msg, p->hl_id, false, p->multiline);
}
}
msg_hist_off = false;
@@ -1338,7 +1340,7 @@ static void hit_return_msg(bool newline_sb)
msg_puts(_("Interrupt: "));
}
- msg_puts_attr(_("Press ENTER or type command to continue"), HL_ATTR(HLF_R));
+ msg_puts_hl(_("Press ENTER or type command to continue"), HLF_R, false);
if (!msg_use_printf()) {
msg_clr_eos();
}
@@ -1346,7 +1348,7 @@ static void hit_return_msg(bool newline_sb)
}
/// Set "keep_msg" to "s". Free the old value and check for NULL pointer.
-void set_keep_msg(const char *s, int attr)
+void set_keep_msg(const char *s, int hl_id)
{
xfree(keep_msg);
if (s != NULL && msg_silent == 0) {
@@ -1355,7 +1357,7 @@ void set_keep_msg(const char *s, int attr)
keep_msg = NULL;
}
keep_msg_more = false;
- keep_msg_attr = attr;
+ keep_msg_hl_id = hl_id;
}
/// Return true if printing messages should currently be done.
@@ -1480,10 +1482,10 @@ void msg_starthere(void)
void msg_putchar(int c)
{
- msg_putchar_attr(c, 0);
+ msg_putchar_hl(c, 0);
}
-void msg_putchar_attr(int c, int attr)
+void msg_putchar_hl(int c, int hl_id)
{
char buf[MB_MAXCHAR + 1];
@@ -1495,7 +1497,7 @@ void msg_putchar_attr(int c, int attr)
} else {
buf[utf_char2bytes(c, buf)] = NUL;
}
- msg_puts_attr(buf, attr);
+ msg_puts_hl(buf, hl_id, false);
}
void msg_outnum(int n)
@@ -1508,48 +1510,42 @@ void msg_outnum(int n)
void msg_home_replace(const char *fname)
{
- msg_home_replace_attr(fname, 0);
-}
-
-void msg_home_replace_hl(const char *fname)
-{
- msg_home_replace_attr(fname, HL_ATTR(HLF_D));
+ msg_home_replace_hl(fname, 0);
}
-static void msg_home_replace_attr(const char *fname, int attr)
+static void msg_home_replace_hl(const char *fname, int hl_id)
{
char *name = home_replace_save(NULL, fname);
- msg_outtrans(name, attr);
+ msg_outtrans(name, hl_id, false);
xfree(name);
}
-/// Output 'len' characters in 'str' (including NULs) with translation
-/// if 'len' is -1, output up to a NUL character.
-/// Use attributes 'attr'.
+/// Output "len" characters in "str" (including NULs) with translation
+/// if "len" is -1, output up to a NUL character. Use highlight "hl_id".
///
/// @return the number of characters it takes on the screen.
-int msg_outtrans(const char *str, int attr)
+int msg_outtrans(const char *str, int hl_id, bool hist)
{
- return msg_outtrans_len(str, (int)strlen(str), attr);
+ return msg_outtrans_len(str, (int)strlen(str), hl_id, hist);
}
/// Output one character at "p".
/// Handles multi-byte characters.
///
/// @return pointer to the next character.
-const char *msg_outtrans_one(const char *p, int attr)
+const char *msg_outtrans_one(const char *p, int hl_id, bool hist)
{
int l;
if ((l = utfc_ptr2len(p)) > 1) {
- msg_outtrans_len(p, l, attr);
+ msg_outtrans_len(p, l, hl_id, hist);
return p + l;
}
- msg_puts_attr(transchar_byte_buf(NULL, (uint8_t)(*p)), attr);
+ msg_puts_hl(transchar_byte_buf(NULL, (uint8_t)(*p)), hl_id, hist);
return p + 1;
}
-int msg_outtrans_len(const char *msgstr, int len, int attr)
+int msg_outtrans_len(const char *msgstr, int len, int hl_id, bool hist)
{
int retval = 0;
const char *str = msgstr;
@@ -1561,10 +1557,8 @@ int msg_outtrans_len(const char *msgstr, int len, int attr)
// Only quit when got_int was set in here.
got_int = false;
- // if MSG_HIST flag set, add message to history
- if (attr & MSG_HIST) {
- add_msg_hist(str, len, attr, false);
- attr &= ~MSG_HIST;
+ if (hist) {
+ add_msg_hist(str, len, hl_id, false);
}
// When drawing over the command line no need to clear it later or remove
@@ -1588,10 +1582,10 @@ int msg_outtrans_len(const char *msgstr, int len, int attr)
// Unprintable multi-byte char: print the printable chars so
// far and the translation of the unprintable char.
if (str > plain_start) {
- msg_puts_len(plain_start, str - plain_start, attr);
+ msg_puts_len(plain_start, str - plain_start, hl_id, hist);
}
plain_start = str + mb_l;
- msg_puts_attr(transchar_buf(NULL, c), attr == 0 ? HL_ATTR(HLF_8) : attr);
+ msg_puts_hl(transchar_buf(NULL, c), hl_id == 0 ? HLF_8 : hl_id, false);
retval += char2cells(c);
}
len -= mb_l - 1;
@@ -1602,10 +1596,10 @@ int msg_outtrans_len(const char *msgstr, int len, int attr)
// Unprintable char: print the printable chars so far and the
// translation of the unprintable char.
if (str > plain_start) {
- msg_puts_len(plain_start, str - plain_start, attr);
+ msg_puts_len(plain_start, str - plain_start, hl_id, hist);
}
plain_start = str + 1;
- msg_puts_attr(s, attr == 0 ? HL_ATTR(HLF_8) : attr);
+ msg_puts_hl(s, hl_id == 0 ? HLF_8 : hl_id, false);
retval += (int)strlen(s);
} else {
retval++;
@@ -1616,7 +1610,7 @@ int msg_outtrans_len(const char *msgstr, int len, int attr)
if (str > plain_start && !got_int) {
// Print the printable chars at the end.
- msg_puts_len(plain_start, str - plain_start, attr);
+ msg_puts_len(plain_start, str - plain_start, hl_id, hist);
}
got_int |= save_got_int;
@@ -1666,7 +1660,7 @@ int msg_outtrans_special(const char *strstart, bool from, int maxlen)
}
const char *str = strstart;
int retval = 0;
- int attr = HL_ATTR(HLF_8);
+ int hl_id = HLF_8;
while (*str != NUL) {
const char *text;
@@ -1686,9 +1680,7 @@ int msg_outtrans_special(const char *strstart, bool from, int maxlen)
break;
}
// Highlight special keys
- msg_puts_attr(text, (len > 1
- && utfc_ptr2len(text) <= 1
- ? attr : 0));
+ msg_puts_hl(text, (len > 1 && utfc_ptr2len(text) <= 1 ? hl_id : 0), false);
retval += len;
}
return retval;
@@ -1856,7 +1848,7 @@ void msg_prt_line(const char *s, bool list)
schar_T sc_final = 0;
const char *p_extra = NULL; // init to make SASC shut up. ASCII only!
int n;
- int attr = 0;
+ int hl_id = 0;
const char *lead = NULL;
bool in_multispace = false;
int multispace_pos = 0;
@@ -1920,7 +1912,7 @@ void msg_prt_line(const char *s, bool list)
s += l;
continue;
} else {
- attr = 0;
+ hl_id = 0;
int c = (uint8_t)(*s++);
sc_extra = NUL;
sc_final = NUL;
@@ -1944,13 +1936,13 @@ void msg_prt_line(const char *s, bool list)
: curwin->w_p_lcs_chars.tab1;
sc_extra = curwin->w_p_lcs_chars.tab2;
sc_final = curwin->w_p_lcs_chars.tab3;
- attr = HL_ATTR(HLF_0);
+ hl_id = HLF_0;
}
} else if (c == NUL && list && curwin->w_p_lcs_chars.eol != NUL) {
p_extra = "";
n_extra = 1;
sc = curwin->w_p_lcs_chars.eol;
- attr = HL_ATTR(HLF_AT);
+ hl_id = HLF_AT;
s--;
} else if (c != NUL && (n = byte2cells(c)) > 1) {
n_extra = n - 1;
@@ -1958,7 +1950,7 @@ void msg_prt_line(const char *s, bool list)
sc = schar_from_ascii(*p_extra++);
// Use special coloring to be able to distinguish <hex> from
// the same in plain text.
- attr = HL_ATTR(HLF_0);
+ hl_id = HLF_0;
} else if (c == ' ') {
if (lead != NULL && s <= lead && in_multispace
&& curwin->w_p_lcs_chars.leadmultispace != NULL) {
@@ -1966,23 +1958,23 @@ void msg_prt_line(const char *s, bool list)
if (curwin->w_p_lcs_chars.leadmultispace[multispace_pos] == NUL) {
multispace_pos = 0;
}
- attr = HL_ATTR(HLF_0);
+ hl_id = HLF_0;
} else if (lead != NULL && s <= lead && curwin->w_p_lcs_chars.lead != NUL) {
sc = curwin->w_p_lcs_chars.lead;
- attr = HL_ATTR(HLF_0);
+ hl_id = HLF_0;
} else if (trail != NULL && s > trail) {
sc = curwin->w_p_lcs_chars.trail;
- attr = HL_ATTR(HLF_0);
+ hl_id = HLF_0;
} else if (in_multispace
&& curwin->w_p_lcs_chars.multispace != NULL) {
sc = curwin->w_p_lcs_chars.multispace[multispace_pos++];
if (curwin->w_p_lcs_chars.multispace[multispace_pos] == NUL) {
multispace_pos = 0;
}
- attr = HL_ATTR(HLF_0);
+ hl_id = HLF_0;
} else if (list && curwin->w_p_lcs_chars.space != NUL) {
sc = curwin->w_p_lcs_chars.space;
- attr = HL_ATTR(HLF_0);
+ hl_id = HLF_0;
} else {
sc = schar_from_ascii(' '); // SPACE!
}
@@ -1998,7 +1990,7 @@ void msg_prt_line(const char *s, bool list)
// TODO(bfredl): this is such baloney. need msg_put_schar
char buf[MAX_SCHAR_SIZE];
schar_get(buf, sc);
- msg_puts_attr(buf, attr);
+ msg_puts_hl(buf, hl_id, false);
col++;
}
msg_clr_eos();
@@ -2008,42 +2000,42 @@ void msg_prt_line(const char *s, bool list)
/// Update msg_row and msg_col for the next message.
void msg_puts(const char *s)
{
- msg_puts_attr(s, 0);
+ msg_puts_hl(s, 0, false);
}
void msg_puts_title(const char *s)
{
- msg_puts_attr(s, HL_ATTR(HLF_T));
+ msg_puts_hl(s, HLF_T, false);
}
/// Show a message in such a way that it always fits in the line. Cut out a
/// part in the middle and replace it with "..." when necessary.
/// Does not handle multi-byte characters!
-void msg_outtrans_long(const char *longstr, int attr)
+void msg_outtrans_long(const char *longstr, int hl_id)
{
int len = (int)strlen(longstr);
int slen = len;
int room = Columns - msg_col;
if (len > room && room >= 20) {
slen = (room - 3) / 2;
- msg_outtrans_len(longstr, slen, attr);
- msg_puts_attr("...", HL_ATTR(HLF_8));
+ msg_outtrans_len(longstr, slen, hl_id, false);
+ msg_puts_hl("...", HLF_8, false);
}
- msg_outtrans_len(longstr + len - slen, slen, attr);
+ msg_outtrans_len(longstr + len - slen, slen, hl_id, len);
}
-/// Basic function for writing a message with highlight attributes.
-void msg_puts_attr(const char *const s, const int attr)
+/// Basic function for writing a message with highlight id.
+void msg_puts_hl(const char *const s, const int hl_id, const bool hist)
{
- msg_puts_len(s, -1, attr);
+ msg_puts_len(s, -1, hl_id, hist);
}
-/// Write a message with highlight attributes
+/// Write a message with highlight id.
///
/// @param[in] str NUL-terminated message string.
/// @param[in] len Length of the string or -1.
-/// @param[in] attr Highlight attribute.
-void msg_puts_len(const char *const str, const ptrdiff_t len, int attr)
+/// @param[in] hl_id Highlight id.
+void msg_puts_len(const char *const str, const ptrdiff_t len, int hl_id, bool hist)
FUNC_ATTR_NONNULL_ALL
{
assert(len < 0 || memchr(str, 0, (size_t)len) == NULL);
@@ -2055,10 +2047,8 @@ void msg_puts_len(const char *const str, const ptrdiff_t len, int attr)
return;
}
- // if MSG_HIST flag set, add message to history
- if (attr & MSG_HIST) {
- add_msg_hist(str, (int)len, attr, false);
- attr &= ~MSG_HIST;
+ if (hist) {
+ add_msg_hist(str, (int)len, hl_id, false);
}
// When writing something to the screen after it has scrolled, requires a
@@ -2095,7 +2085,7 @@ void msg_puts_len(const char *const str, const ptrdiff_t len, int attr)
}
}
if (!msg_use_printf() || (headless_mode && default_grid.chars)) {
- msg_puts_display(str, (int)len, attr, false);
+ msg_puts_display(str, (int)len, hl_id, false);
}
need_fileinfo = false;
@@ -2104,11 +2094,11 @@ void msg_puts_len(const char *const str, const ptrdiff_t len, int attr)
/// Print a formatted message
///
/// Message printed is limited by #IOSIZE. Must not be used from inside
-/// msg_puts_attr().
+/// msg_puts_hl_id().
///
-/// @param[in] attr Highlight attributes.
+/// @param[in] hl_id Highlight id.
/// @param[in] fmt Format string.
-void msg_printf_attr(const int attr, const char *const fmt, ...)
+void msg_printf_hl(const int hl_id, const char *const fmt, ...)
FUNC_ATTR_NONNULL_ARG(2) FUNC_ATTR_PRINTF(2, 3)
{
static char msgbuf[IOSIZE];
@@ -2119,7 +2109,7 @@ void msg_printf_attr(const int attr, const char *const fmt, ...)
va_end(ap);
msg_scroll = true;
- msg_puts_len(msgbuf, (ptrdiff_t)len, attr);
+ msg_puts_len(msgbuf, (ptrdiff_t)len, hl_id, true);
}
static void msg_ext_emit_chunk(void)
@@ -2136,16 +2126,18 @@ static void msg_ext_emit_chunk(void)
msg_ext_last_attr = -1;
String text = ga_take_string(&msg_ext_last_chunk);
ADD(chunk, STRING_OBJ(text));
+ ADD(chunk, INTEGER_OBJ(msg_ext_last_hl_id));
ADD(*msg_ext_chunks, ARRAY_OBJ(chunk));
}
/// The display part of msg_puts_len().
/// May be called recursively to display scroll-back text.
-static void msg_puts_display(const char *str, int maxlen, int attr, int recurse)
+static void msg_puts_display(const char *str, int maxlen, int hl_id, int recurse)
{
const char *s = str;
const char *sb_str = str;
int sb_col = msg_col;
+ int attr = hl_id ? syn_id2attr(hl_id) : 0;
did_wait_return = false;
@@ -2153,6 +2145,7 @@ static void msg_puts_display(const char *str, int maxlen, int attr, int recurse)
if (attr != msg_ext_last_attr) {
msg_ext_emit_chunk();
msg_ext_last_attr = attr;
+ msg_ext_last_hl_id = hl_id;
}
// Concat pieces with the same highlight
size_t len = maxlen < 0 ? strlen(str) : strnlen(str, (size_t)maxlen);
@@ -2172,7 +2165,7 @@ static void msg_puts_display(const char *str, int maxlen, int attr, int recurse)
if (msg_col >= Columns) {
if (p_more && !recurse) {
// Store text for scrolling back.
- store_sb_text(&sb_str, s, attr, &sb_col, true);
+ store_sb_text(&sb_str, s, hl_id, &sb_col, true);
}
if (msg_no_more && lines_left == 0) {
break;
@@ -2262,7 +2255,7 @@ static void msg_puts_display(const char *str, int maxlen, int attr, int recurse)
msg_row++;
if (p_more && !recurse) {
// Store text for scrolling back.
- store_sb_text(&sb_str, s, attr, &sb_col, true);
+ store_sb_text(&sb_str, s, hl_id, &sb_col, true);
}
} else if (c == '\r') { // go to column 0
msg_col = 0;
@@ -2291,7 +2284,7 @@ static void msg_puts_display(const char *str, int maxlen, int attr, int recurse)
msg_cursor_goto(msg_row, msg_col);
if (p_more && !recurse) {
- store_sb_text(&sb_str, s, attr, &sb_col, false);
+ store_sb_text(&sb_str, s, hl_id, &sb_col, false);
}
msg_check();
@@ -2481,7 +2474,7 @@ static sb_clear_T do_clear_sb_text = SB_CLEAR_NONE;
/// @param sb_str start of string
/// @param s just after string
/// @param finish line ends
-static void store_sb_text(const char **sb_str, const char *s, int attr, int *sb_col, int finish)
+static void store_sb_text(const char **sb_str, const char *s, int hl_id, int *sb_col, int finish)
{
msgchunk_T *mp;
@@ -2499,7 +2492,7 @@ static void store_sb_text(const char **sb_str, const char *s, int attr, int *sb_
mp = xmalloc(offsetof(msgchunk_T, sb_text) + (size_t)(s - *sb_str) + 1);
mp->sb_eol = (char)finish;
mp->sb_msg_col = *sb_col;
- mp->sb_attr = attr;
+ mp->sb_hl_id = hl_id;
memcpy(mp->sb_text, *sb_str, (size_t)(s - *sb_str));
mp->sb_text[s - *sb_str] = NUL;
@@ -2637,7 +2630,7 @@ static msgchunk_T *disp_sb_line(int row, msgchunk_T *smp)
msg_row = row;
msg_col = mp->sb_msg_col;
char *p = mp->sb_text;
- msg_puts_display(p, -1, mp->sb_attr, true);
+ msg_puts_display(p, -1, mp->sb_hl_id, true);
if (mp->sb_eol || mp->sb_next == NULL) {
break;
}
@@ -2694,12 +2687,13 @@ static void msg_puts_printf(const char *str, const ptrdiff_t maxlen)
// primitive way to compute the current column
if (*s == '\r' || *s == '\n') {
msg_col = 0;
+ msg_didout = false;
} else {
msg_col += cw;
+ msg_didout = true;
}
s += len;
}
- msg_didout = true; // assume that line is not empty
}
/// Show the more-prompt and handle the user response.
@@ -3321,17 +3315,17 @@ void give_warning(const char *message, bool hl)
set_vim_var_string(VV_WARNINGMSG, message, -1);
XFREE_CLEAR(keep_msg);
if (hl) {
- keep_msg_attr = HL_ATTR(HLF_W);
+ keep_msg_hl_id = HLF_W;
} else {
- keep_msg_attr = 0;
+ keep_msg_hl_id = 0;
}
if (msg_ext_kind == NULL) {
msg_ext_set_kind("wmsg");
}
- if (msg(message, keep_msg_attr) && msg_scrolled == 0) {
- set_keep_msg(message, keep_msg_attr);
+ if (msg(message, keep_msg_hl_id) && msg_scrolled == 0) {
+ set_keep_msg(message, keep_msg_hl_id);
}
msg_didout = false; // Overwrite this message.
msg_nowait = true; // Don't wait for this message.
@@ -3664,7 +3658,7 @@ void display_confirm_msg(void)
confirm_msg_used++;
if (confirm_msg != NULL) {
msg_ext_set_kind("confirm");
- msg_puts_attr(confirm_msg, HL_ATTR(HLF_M));
+ msg_puts_hl(confirm_msg, HLF_M, false);
}
confirm_msg_used--;
}