diff options
author | Evgeni Chasnovski <evgeni.chasnovski@gmail.com> | 2023-08-25 10:53:29 +0300 |
---|---|---|
committer | Evgeni Chasnovski <evgeni.chasnovski@gmail.com> | 2023-08-26 19:37:18 +0300 |
commit | 617fd5bdc6ab9a82bfc6136f549fc31dcf442ed7 (patch) | |
tree | 4ad54237929208622604484014f87edb94b23966 | |
parent | afd0c648a89ff88c9bff1b24c37e139813ec13c9 (diff) | |
download | rneovim-617fd5bdc6ab9a82bfc6136f549fc31dcf442ed7.tar.gz rneovim-617fd5bdc6ab9a82bfc6136f549fc31dcf442ed7.tar.bz2 rneovim-617fd5bdc6ab9a82bfc6136f549fc31dcf442ed7.zip |
refactor(float): extract "title" and "title_pos" handling
-rw-r--r-- | src/nvim/api/win_config.c | 127 | ||||
-rw-r--r-- | src/nvim/api/win_config.h | 1 | ||||
-rw-r--r-- | src/nvim/buffer_defs.h | 4 | ||||
-rw-r--r-- | src/nvim/drawscreen.c | 40 |
4 files changed, 111 insertions, 61 deletions
diff --git a/src/nvim/api/win_config.c b/src/nvim/api/win_config.c index b666d1efa2..9473803652 100644 --- a/src/nvim/api/win_config.c +++ b/src/nvim/api/win_config.c @@ -240,6 +240,48 @@ void nvim_win_set_config(Window window, Dict(float_config) *config, Error *err) } } +Dictionary config_put_bordertext(Dictionary config, FloatConfig *fconfig, + BorderTextType bordertext_type) +{ + VirtText chunks; + AlignTextPos align; + char *field_name; + char *field_pos_name; + if (bordertext_type == kBorderTextTitle) { + chunks = fconfig->title_chunks; + align = fconfig->title_pos; + field_name = "title"; + field_pos_name = "title_pos"; + } + + Array bordertext = ARRAY_DICT_INIT; + for (size_t i = 0; i < chunks.size; i++) { + Array tuple = ARRAY_DICT_INIT; + ADD(tuple, CSTR_TO_OBJ(chunks.items[i].text)); + if (chunks.items[i].hl_id > 0) { + ADD(tuple, CSTR_TO_OBJ(syn_id2name(chunks.items[i].hl_id))); + } + ADD(bordertext, ARRAY_OBJ(tuple)); + } + PUT(config, field_name, ARRAY_OBJ(bordertext)); + + char *pos; + switch (align) { + case kAlignLeft: + pos = "left"; + break; + case kAlignCenter: + pos = "center"; + break; + case kAlignRight: + pos = "right"; + break; + } + PUT(config, field_pos_name, CSTR_TO_OBJ(pos)); + + return config; +} + /// Gets window configuration. /// /// The returned value may be given to |nvim_open_win()|. @@ -301,26 +343,7 @@ Dictionary nvim_win_get_config(Window window, Error *err) } PUT(rv, "border", ARRAY_OBJ(border)); if (config->title) { - Array titles = ARRAY_DICT_INIT; - VirtText title_datas = config->title_chunks; - for (size_t i = 0; i < title_datas.size; i++) { - Array tuple = ARRAY_DICT_INIT; - ADD(tuple, CSTR_TO_OBJ(title_datas.items[i].text)); - if (title_datas.items[i].hl_id > 0) { - ADD(tuple, CSTR_TO_OBJ(syn_id2name(title_datas.items[i].hl_id))); - } - ADD(titles, ARRAY_OBJ(tuple)); - } - PUT(rv, "title", ARRAY_OBJ(titles)); - char *title_pos; - if (config->title_pos == kAlignLeft) { - title_pos = "left"; - } else if (config->title_pos == kAlignCenter) { - title_pos = "center"; - } else { - title_pos = "right"; - } - PUT(rv, "title_pos", CSTR_TO_OBJ(title_pos)); + rv = config_put_bordertext(rv, config, kBorderTextTitle); } } } @@ -381,54 +404,72 @@ static bool parse_float_bufpos(Array bufpos, lpos_T *out) return true; } -static void parse_border_title(Object title, FloatConfig *fconfig, Error *err) +static void parse_bordertext(Object bordertext, BorderTextType bordertext_type, + FloatConfig *fconfig, Error *err) { - if (title.type == kObjectTypeString) { - if (title.data.string.size == 0) { - fconfig->title = false; + bool *is_present; + VirtText *chunks; + int *width; + if (bordertext_type == kBorderTextTitle) { + is_present = &fconfig->title; + chunks = &fconfig->title_chunks; + width = &fconfig->title_width; + } + + if (bordertext.type == kObjectTypeString) { + if (bordertext.data.string.size == 0) { + *is_present = false; return; } int hl_id = syn_check_group(S_LEN("FloatTitle")); - kv_push(fconfig->title_chunks, ((VirtTextChunk){ .text = xstrdup(title.data.string.data), - .hl_id = hl_id })); - fconfig->title_width = (int)mb_string2cells(title.data.string.data); - fconfig->title = true; + kv_push(*chunks, ((VirtTextChunk){ .text = xstrdup(bordertext.data.string.data), + .hl_id = hl_id })); + *width = (int)mb_string2cells(bordertext.data.string.data); + *is_present = true; return; } - if (title.type != kObjectTypeArray) { + if (bordertext.type != kObjectTypeArray) { api_set_error(err, kErrorTypeValidation, "title must be string or array"); return; } - if (title.data.array.size == 0) { + if (bordertext.data.array.size == 0) { api_set_error(err, kErrorTypeValidation, "title cannot be an empty array"); return; } - fconfig->title_width = 0; - fconfig->title_chunks = parse_virt_text(title.data.array, err, &fconfig->title_width); + *width = 0; + *chunks = parse_virt_text(bordertext.data.array, err, width); - fconfig->title = true; + *is_present = true; } -static bool parse_title_pos(String title_pos, FloatConfig *fconfig, Error *err) +static bool parse_bordertext_pos(String bordertext_pos, BorderTextType bordertext_type, + FloatConfig *fconfig, Error *err) { - if (title_pos.size == 0) { - fconfig->title_pos = kAlignLeft; + AlignTextPos *align; + if (bordertext_type == kBorderTextTitle) { + align = &fconfig->title_pos; + } + + if (bordertext_pos.size == 0) { + *align = kAlignLeft; return true; } - char *pos = title_pos.data; + char *pos = bordertext_pos.data; if (strequal(pos, "left")) { - fconfig->title_pos = kAlignLeft; + *align = kAlignLeft; } else if (strequal(pos, "center")) { - fconfig->title_pos = kAlignCenter; + *align = kAlignCenter; } else if (strequal(pos, "right")) { - fconfig->title_pos = kAlignRight; + *align = kAlignRight; } else { - api_set_error(err, kErrorTypeValidation, "invalid title_pos value"); + if (bordertext_type == kBorderTextTitle) { + api_set_error(err, kErrorTypeValidation, "invalid title_pos value"); + } return false; } return true; @@ -693,13 +734,13 @@ static bool parse_float_config(Dict(float_config) *config, FloatConfig *fconfig, clear_virttext(&fconfig->title_chunks); } - parse_border_title(config->title, fconfig, err); + parse_bordertext(config->title, kBorderTextTitle, fconfig, err); if (ERROR_SET(err)) { return false; } // handles unset 'title_pos' same as empty string - if (!parse_title_pos(config->title_pos, fconfig, err)) { + if (!parse_bordertext_pos(config->title_pos, kBorderTextTitle, fconfig, err)) { return false; } } else { diff --git a/src/nvim/api/win_config.h b/src/nvim/api/win_config.h index a4614f02ce..426a74fb3e 100644 --- a/src/nvim/api/win_config.h +++ b/src/nvim/api/win_config.h @@ -3,6 +3,7 @@ #include "nvim/api/keysets.h" #include "nvim/api/private/defs.h" +#include "nvim/buffer_defs.h" #ifdef INCLUDE_GENERATED_DECLARATIONS # include "api/win_config.h.generated.h" diff --git a/src/nvim/buffer_defs.h b/src/nvim/buffer_defs.h index 2d83242275..ba6a3a1e27 100644 --- a/src/nvim/buffer_defs.h +++ b/src/nvim/buffer_defs.h @@ -936,6 +936,10 @@ typedef enum { kAlignRight = 2, } AlignTextPos; +typedef enum { + kBorderTextTitle = 0, +} BorderTextType; + typedef struct { Window window; lpos_T bufpos; diff --git a/src/nvim/drawscreen.c b/src/nvim/drawscreen.c index bd177884fb..4b23a9f1eb 100644 --- a/src/nvim/drawscreen.c +++ b/src/nvim/drawscreen.c @@ -701,20 +701,32 @@ void end_search_hl(void) screen_search_hl.rm.regprog = NULL; } -static void win_border_redr_title(win_T *wp, ScreenGrid *grid, int col) +static void win_redr_bordertext(win_T *wp, ScreenGrid *grid, VirtText text_chunks, int row, int col) { - VirtText title_chunks = wp->w_float_config.title_chunks; - - for (size_t i = 0; i < title_chunks.size; i++) { - char *text = title_chunks.items[i].text; + for (size_t i = 0; i < text_chunks.size; i++) { + char *text = text_chunks.items[i].text; int cell = (int)mb_string2cells(text); - int hl_id = title_chunks.items[i].hl_id; + int hl_id = text_chunks.items[i].hl_id; int attr = hl_id ? syn_id2attr(hl_id) : 0; - grid_puts(grid, text, 0, col, attr); + grid_puts(grid, text, row, col, attr); col += cell; } } +int win_get_bordertext_col(int total_col, int text_width, AlignTextPos align) +{ + switch (align) { + case kAlignLeft: + return 1; + case kAlignCenter: + return (total_col - text_width) / 2 + 1; + case kAlignRight: + return total_col - text_width + 1; + default: + abort(); + } +} + static void win_redr_border(win_T *wp) { wp->w_redr_border = false; @@ -741,17 +753,9 @@ static void win_redr_border(win_T *wp) } if (wp->w_float_config.title) { - int title_col = 0; - int title_width = wp->w_float_config.title_width; - AlignTextPos title_pos = wp->w_float_config.title_pos; - - if (title_pos == kAlignCenter) { - title_col = (icol - title_width) / 2 + 1; - } else { - title_col = title_pos == kAlignLeft ? 1 : icol - title_width + 1; - } - - win_border_redr_title(wp, grid, title_col); + int title_col = win_get_bordertext_col(icol, wp->w_float_config.title_width, + wp->w_float_config.title_pos); + win_redr_bordertext(wp, grid, wp->w_float_config.title_chunks, 0, title_col); } if (adj[1]) { grid_put_schar(grid, 0, icol + adj[3], chars[2], attrs[2]); |