mirror of
https://github.com/neovim/neovim.git
synced 2025-02-25 18:55:25 -06:00
feat(float): implement footer
Problem: Now way to show text at the bottom part of floating window border (a.k.a. "footer"). Solution: Allows `footer` and `footer_pos` config fields similar to `title` and `title_pos`.
This commit is contained in:
parent
617fd5bdc6
commit
35570e4a11
@ -3138,11 +3138,18 @@ nvim_open_win({buffer}, {enter}, {*config}) *nvim_open_win()*
|
|||||||
specified by character: [ ["+", "MyCorner"], ["x",
|
specified by character: [ ["+", "MyCorner"], ["x",
|
||||||
"MyBorder"] ].
|
"MyBorder"] ].
|
||||||
|
|
||||||
• title: Title (optional) in window border, String or list.
|
• title: Title (optional) in window border, string or list.
|
||||||
List is [text, highlight] tuples. if is string the default
|
List should consist of `[text, highlight]` tuples. If
|
||||||
highlight group is `FloatTitle`.
|
string, the default highlight group is `FloatTitle`.
|
||||||
• title_pos: Title position must set with title option.
|
• title_pos: Title position. Must be set with `title`
|
||||||
value can be of `left` `center` `right` default is left.
|
option. Value can be one of "left", "center", or "right".
|
||||||
|
Default is `"left"`.
|
||||||
|
• footer: Footer (optional) in window border, string or
|
||||||
|
list. List should consist of `[text, highlight]` tuples.
|
||||||
|
If string, the default highlight group is `FloatTitle`.
|
||||||
|
• footer_pos: Footer position. Must be set with `footer`
|
||||||
|
option. Value can be one of "left", "center", or "right".
|
||||||
|
Default is `"left"`.
|
||||||
• noautocmd: If true then no buffer-related autocommand
|
• noautocmd: If true then no buffer-related autocommand
|
||||||
events such as |BufEnter|, |BufLeave| or |BufWinEnter| may
|
events such as |BufEnter|, |BufLeave| or |BufWinEnter| may
|
||||||
fire from calling this function.
|
fire from calling this function.
|
||||||
|
@ -155,6 +155,9 @@ The following new APIs and features were added.
|
|||||||
• New RPC client type `msgpack-rpc` is added for `nvim_set_client_info` to
|
• New RPC client type `msgpack-rpc` is added for `nvim_set_client_info` to
|
||||||
support fully MessagePack-RPC compliant clients.
|
support fully MessagePack-RPC compliant clients.
|
||||||
|
|
||||||
|
• Floating windows can now show footer with new `footer` and `footer_pos`
|
||||||
|
config fields.
|
||||||
|
|
||||||
==============================================================================
|
==============================================================================
|
||||||
CHANGED FEATURES *news-changed*
|
CHANGED FEATURES *news-changed*
|
||||||
|
|
||||||
|
17
runtime/lua/vim/_meta/api.lua
generated
17
runtime/lua/vim/_meta/api.lua
generated
@ -1551,11 +1551,18 @@ function vim.api.nvim_open_term(buffer, opts) end
|
|||||||
--- specified by character: [ ["+", "MyCorner"], ["x",
|
--- specified by character: [ ["+", "MyCorner"], ["x",
|
||||||
--- "MyBorder"] ].
|
--- "MyBorder"] ].
|
||||||
---
|
---
|
||||||
--- • title: Title (optional) in window border, String or list.
|
--- • title: Title (optional) in window border, string or list.
|
||||||
--- List is [text, highlight] tuples. if is string the default
|
--- List should consist of `[text, highlight]` tuples. If
|
||||||
--- highlight group is `FloatTitle`.
|
--- string, the default highlight group is `FloatTitle`.
|
||||||
--- • title_pos: Title position must set with title option.
|
--- • title_pos: Title position. Must be set with `title`
|
||||||
--- value can be of `left` `center` `right` default is left.
|
--- option. Value can be one of "left", "center", or "right".
|
||||||
|
--- Default is `"left"`.
|
||||||
|
--- • footer: Footer (optional) in window border, string or
|
||||||
|
--- list. List should consist of `[text, highlight]` tuples.
|
||||||
|
--- If string, the default highlight group is `FloatTitle`.
|
||||||
|
--- • footer_pos: Footer position. Must be set with `footer`
|
||||||
|
--- option. Value can be one of "left", "center", or "right".
|
||||||
|
--- Default is `"left"`.
|
||||||
--- • noautocmd: If true then no buffer-related autocommand
|
--- • noautocmd: If true then no buffer-related autocommand
|
||||||
--- events such as `BufEnter`, `BufLeave` or `BufWinEnter` may
|
--- events such as `BufEnter`, `BufLeave` or `BufWinEnter` may
|
||||||
--- fire from calling this function.
|
--- fire from calling this function.
|
||||||
|
2
runtime/lua/vim/_meta/api_keysets.lua
generated
2
runtime/lua/vim/_meta/api_keysets.lua
generated
@ -108,6 +108,8 @@ error('Cannot require a meta file')
|
|||||||
--- @field border? any
|
--- @field border? any
|
||||||
--- @field title? any
|
--- @field title? any
|
||||||
--- @field title_pos? string
|
--- @field title_pos? string
|
||||||
|
--- @field footer? any
|
||||||
|
--- @field footer_pos? string
|
||||||
--- @field style? string
|
--- @field style? string
|
||||||
--- @field noautocmd? boolean
|
--- @field noautocmd? boolean
|
||||||
|
|
||||||
|
@ -99,6 +99,8 @@ typedef struct {
|
|||||||
Object border;
|
Object border;
|
||||||
Object title;
|
Object title;
|
||||||
String title_pos;
|
String title_pos;
|
||||||
|
Object footer;
|
||||||
|
String footer_pos;
|
||||||
String style;
|
String style;
|
||||||
Boolean noautocmd;
|
Boolean noautocmd;
|
||||||
} Dict(float_config);
|
} Dict(float_config);
|
||||||
|
@ -145,11 +145,18 @@
|
|||||||
/// By default, `FloatBorder` highlight is used, which links to `WinSeparator`
|
/// By default, `FloatBorder` highlight is used, which links to `WinSeparator`
|
||||||
/// when not defined. It could also be specified by character:
|
/// when not defined. It could also be specified by character:
|
||||||
/// [ ["+", "MyCorner"], ["x", "MyBorder"] ].
|
/// [ ["+", "MyCorner"], ["x", "MyBorder"] ].
|
||||||
/// - title: Title (optional) in window border, String or list.
|
/// - title: Title (optional) in window border, string or list.
|
||||||
/// List is [text, highlight] tuples. if is string the default
|
/// List should consist of `[text, highlight]` tuples.
|
||||||
/// highlight group is `FloatTitle`.
|
/// If string, the default highlight group is `FloatTitle`.
|
||||||
/// - title_pos: Title position must set with title option.
|
/// - title_pos: Title position. Must be set with `title` option.
|
||||||
/// value can be of `left` `center` `right` default is left.
|
/// Value can be one of "left", "center", or "right".
|
||||||
|
/// Default is `"left"`.
|
||||||
|
/// - footer: Footer (optional) in window border, string or list.
|
||||||
|
/// List should consist of `[text, highlight]` tuples.
|
||||||
|
/// If string, the default highlight group is `FloatTitle`.
|
||||||
|
/// - footer_pos: Footer position. Must be set with `footer` option.
|
||||||
|
/// Value can be one of "left", "center", or "right".
|
||||||
|
/// Default is `"left"`.
|
||||||
/// - noautocmd: If true then no buffer-related autocommand events such as
|
/// - noautocmd: If true then no buffer-related autocommand events such as
|
||||||
/// |BufEnter|, |BufLeave| or |BufWinEnter| may fire from
|
/// |BufEnter|, |BufLeave| or |BufWinEnter| may fire from
|
||||||
/// calling this function.
|
/// calling this function.
|
||||||
@ -247,11 +254,19 @@ Dictionary config_put_bordertext(Dictionary config, FloatConfig *fconfig,
|
|||||||
AlignTextPos align;
|
AlignTextPos align;
|
||||||
char *field_name;
|
char *field_name;
|
||||||
char *field_pos_name;
|
char *field_pos_name;
|
||||||
if (bordertext_type == kBorderTextTitle) {
|
switch (bordertext_type) {
|
||||||
|
case kBorderTextTitle:
|
||||||
chunks = fconfig->title_chunks;
|
chunks = fconfig->title_chunks;
|
||||||
align = fconfig->title_pos;
|
align = fconfig->title_pos;
|
||||||
field_name = "title";
|
field_name = "title";
|
||||||
field_pos_name = "title_pos";
|
field_pos_name = "title_pos";
|
||||||
|
break;
|
||||||
|
case kBorderTextFooter:
|
||||||
|
chunks = fconfig->footer_chunks;
|
||||||
|
align = fconfig->footer_pos;
|
||||||
|
field_name = "footer";
|
||||||
|
field_pos_name = "footer_pos";
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
Array bordertext = ARRAY_DICT_INIT;
|
Array bordertext = ARRAY_DICT_INIT;
|
||||||
@ -345,6 +360,9 @@ Dictionary nvim_win_get_config(Window window, Error *err)
|
|||||||
if (config->title) {
|
if (config->title) {
|
||||||
rv = config_put_bordertext(rv, config, kBorderTextTitle);
|
rv = config_put_bordertext(rv, config, kBorderTextTitle);
|
||||||
}
|
}
|
||||||
|
if (config->footer) {
|
||||||
|
rv = config_put_bordertext(rv, config, kBorderTextFooter);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -410,10 +428,17 @@ static void parse_bordertext(Object bordertext, BorderTextType bordertext_type,
|
|||||||
bool *is_present;
|
bool *is_present;
|
||||||
VirtText *chunks;
|
VirtText *chunks;
|
||||||
int *width;
|
int *width;
|
||||||
if (bordertext_type == kBorderTextTitle) {
|
switch (bordertext_type) {
|
||||||
|
case kBorderTextTitle:
|
||||||
is_present = &fconfig->title;
|
is_present = &fconfig->title;
|
||||||
chunks = &fconfig->title_chunks;
|
chunks = &fconfig->title_chunks;
|
||||||
width = &fconfig->title_width;
|
width = &fconfig->title_width;
|
||||||
|
break;
|
||||||
|
case kBorderTextFooter:
|
||||||
|
is_present = &fconfig->footer;
|
||||||
|
chunks = &fconfig->footer_chunks;
|
||||||
|
width = &fconfig->footer_width;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (bordertext.type == kObjectTypeString) {
|
if (bordertext.type == kObjectTypeString) {
|
||||||
@ -449,8 +474,13 @@ static bool parse_bordertext_pos(String bordertext_pos, BorderTextType bordertex
|
|||||||
FloatConfig *fconfig, Error *err)
|
FloatConfig *fconfig, Error *err)
|
||||||
{
|
{
|
||||||
AlignTextPos *align;
|
AlignTextPos *align;
|
||||||
if (bordertext_type == kBorderTextTitle) {
|
switch (bordertext_type) {
|
||||||
|
case kBorderTextTitle:
|
||||||
align = &fconfig->title_pos;
|
align = &fconfig->title_pos;
|
||||||
|
break;
|
||||||
|
case kBorderTextFooter:
|
||||||
|
align = &fconfig->footer_pos;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (bordertext_pos.size == 0) {
|
if (bordertext_pos.size == 0) {
|
||||||
@ -467,8 +497,13 @@ static bool parse_bordertext_pos(String bordertext_pos, BorderTextType bordertex
|
|||||||
} else if (strequal(pos, "right")) {
|
} else if (strequal(pos, "right")) {
|
||||||
*align = kAlignRight;
|
*align = kAlignRight;
|
||||||
} else {
|
} else {
|
||||||
if (bordertext_type == kBorderTextTitle) {
|
switch (bordertext_type) {
|
||||||
|
case kBorderTextTitle:
|
||||||
api_set_error(err, kErrorTypeValidation, "invalid title_pos value");
|
api_set_error(err, kErrorTypeValidation, "invalid title_pos value");
|
||||||
|
break;
|
||||||
|
case kBorderTextFooter:
|
||||||
|
api_set_error(err, kErrorTypeValidation, "invalid footer_pos value");
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -559,8 +594,9 @@ static void parse_border_style(Object style, FloatConfig *fconfig, Error *err)
|
|||||||
String str = style.data.string;
|
String str = style.data.string;
|
||||||
if (str.size == 0 || strequal(str.data, "none")) {
|
if (str.size == 0 || strequal(str.data, "none")) {
|
||||||
fconfig->border = false;
|
fconfig->border = false;
|
||||||
// title does not work with border equal none
|
// border text does not work with border equal none
|
||||||
fconfig->title = false;
|
fconfig->title = false;
|
||||||
|
fconfig->footer = false;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
for (size_t i = 0; defaults[i].name; i++) {
|
for (size_t i = 0; defaults[i].name; i++) {
|
||||||
@ -750,6 +786,33 @@ static bool parse_float_config(Dict(float_config) *config, FloatConfig *fconfig,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (HAS_KEY_X(config, footer)) {
|
||||||
|
// footer only work with border
|
||||||
|
if (!HAS_KEY_X(config, border) && !fconfig->border) {
|
||||||
|
api_set_error(err, kErrorTypeException, "footer requires border to be set");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (fconfig->footer) {
|
||||||
|
clear_virttext(&fconfig->footer_chunks);
|
||||||
|
}
|
||||||
|
|
||||||
|
parse_bordertext(config->footer, kBorderTextFooter, fconfig, err);
|
||||||
|
if (ERROR_SET(err)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// handles unset 'footer_pos' same as empty string
|
||||||
|
if (!parse_bordertext_pos(config->footer_pos, kBorderTextFooter, fconfig, err)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (HAS_KEY_X(config, footer_pos)) {
|
||||||
|
api_set_error(err, kErrorTypeException, "footer_pos requires footer to be set");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (HAS_KEY_X(config, border)) {
|
if (HAS_KEY_X(config, border)) {
|
||||||
parse_border_style(config->border, fconfig, err);
|
parse_border_style(config->border, fconfig, err);
|
||||||
if (ERROR_SET(err)) {
|
if (ERROR_SET(err)) {
|
||||||
|
@ -938,6 +938,7 @@ typedef enum {
|
|||||||
|
|
||||||
typedef enum {
|
typedef enum {
|
||||||
kBorderTextTitle = 0,
|
kBorderTextTitle = 0,
|
||||||
|
kBorderTextFooter = 1,
|
||||||
} BorderTextType;
|
} BorderTextType;
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
@ -952,14 +953,18 @@ typedef struct {
|
|||||||
int zindex;
|
int zindex;
|
||||||
WinStyle style;
|
WinStyle style;
|
||||||
bool border;
|
bool border;
|
||||||
bool title;
|
|
||||||
bool shadow;
|
bool shadow;
|
||||||
schar_T border_chars[8];
|
schar_T border_chars[8];
|
||||||
int border_hl_ids[8];
|
int border_hl_ids[8];
|
||||||
int border_attr[8];
|
int border_attr[8];
|
||||||
|
bool title;
|
||||||
AlignTextPos title_pos;
|
AlignTextPos title_pos;
|
||||||
VirtText title_chunks;
|
VirtText title_chunks;
|
||||||
int title_width;
|
int title_width;
|
||||||
|
bool footer;
|
||||||
|
AlignTextPos footer_pos;
|
||||||
|
VirtText footer_chunks;
|
||||||
|
int footer_width;
|
||||||
bool noautocmd;
|
bool noautocmd;
|
||||||
} FloatConfig;
|
} FloatConfig;
|
||||||
|
|
||||||
|
@ -782,10 +782,17 @@ static void win_redr_border(win_T *wp)
|
|||||||
if (adj[3]) {
|
if (adj[3]) {
|
||||||
grid_put_schar(grid, irow + adj[0], 0, chars[6], attrs[6]);
|
grid_put_schar(grid, irow + adj[0], 0, chars[6], attrs[6]);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (int i = 0; i < icol; i++) {
|
for (int i = 0; i < icol; i++) {
|
||||||
int ic = (i == 0 && !adj[3] && chars[6][0]) ? 6 : 5;
|
int ic = (i == 0 && !adj[3] && chars[6][0]) ? 6 : 5;
|
||||||
grid_put_schar(grid, irow + adj[0], i + adj[3], chars[ic], attrs[ic]);
|
grid_put_schar(grid, irow + adj[0], i + adj[3], chars[ic], attrs[ic]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (wp->w_float_config.footer) {
|
||||||
|
int footer_col = win_get_bordertext_col(icol, wp->w_float_config.footer_width,
|
||||||
|
wp->w_float_config.footer_pos);
|
||||||
|
win_redr_bordertext(wp, grid, wp->w_float_config.footer_chunks, grid->rows - 1, footer_col);
|
||||||
|
}
|
||||||
if (adj[1]) {
|
if (adj[1]) {
|
||||||
grid_put_schar(grid, irow + adj[0], icol + adj[3], chars[4], attrs[4]);
|
grid_put_schar(grid, irow + adj[0], icol + adj[3], chars[4], attrs[4]);
|
||||||
}
|
}
|
||||||
|
@ -5239,8 +5239,9 @@ static void win_free(win_T *wp, tabpage_T *tp)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// free the border title text
|
// free the border text
|
||||||
clear_virttext(&wp->w_float_config.title_chunks);
|
clear_virttext(&wp->w_float_config.title_chunks);
|
||||||
|
clear_virttext(&wp->w_float_config.footer_chunks);
|
||||||
|
|
||||||
clear_matches(wp);
|
clear_matches(wp);
|
||||||
|
|
||||||
|
@ -1851,6 +1851,39 @@ describe('float window', function()
|
|||||||
eq('center', title_pos)
|
eq('center', title_pos)
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
it('validates footer footer_pos', function()
|
||||||
|
local buf = meths.create_buf(false,false)
|
||||||
|
eq("footer requires border to be set",
|
||||||
|
pcall_err(meths.open_win,buf, false, {
|
||||||
|
relative='editor', width=9, height=2, row=2, col=5, footer='Footer',
|
||||||
|
}))
|
||||||
|
eq("footer_pos requires footer to be set",
|
||||||
|
pcall_err(meths.open_win,buf, false, {
|
||||||
|
relative='editor', width=9, height=2, row=2, col=5,
|
||||||
|
border='single', footer_pos='left',
|
||||||
|
}))
|
||||||
|
end)
|
||||||
|
|
||||||
|
it('validate footer_pos in nvim_win_get_config', function()
|
||||||
|
local footer_pos = exec_lua([[
|
||||||
|
local bufnr = vim.api.nvim_create_buf(false, false)
|
||||||
|
local opts = {
|
||||||
|
relative = 'editor',
|
||||||
|
col = 2,
|
||||||
|
row = 5,
|
||||||
|
height = 2,
|
||||||
|
width = 9,
|
||||||
|
border = 'double',
|
||||||
|
footer = 'Test',
|
||||||
|
footer_pos = 'center'
|
||||||
|
}
|
||||||
|
|
||||||
|
local win_id = vim.api.nvim_open_win(bufnr, true, opts)
|
||||||
|
return vim.api.nvim_win_get_config(win_id).footer_pos
|
||||||
|
]])
|
||||||
|
|
||||||
|
eq('center', footer_pos)
|
||||||
|
end)
|
||||||
|
|
||||||
it('border with title', function()
|
it('border with title', function()
|
||||||
local buf = meths.create_buf(false, false)
|
local buf = meths.create_buf(false, false)
|
||||||
@ -2033,6 +2066,368 @@ describe('float window', function()
|
|||||||
end
|
end
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
it('border with footer', function()
|
||||||
|
local buf = meths.create_buf(false, false)
|
||||||
|
meths.buf_set_lines(buf, 0, -1, true, {' halloj! ',
|
||||||
|
' BORDAA '})
|
||||||
|
local win = meths.open_win(buf, false, {
|
||||||
|
relative='editor', width=9, height=2, row=2, col=5, border="double",
|
||||||
|
footer = "Left",footer_pos = "left",
|
||||||
|
})
|
||||||
|
|
||||||
|
if multigrid then
|
||||||
|
screen:expect{grid=[[
|
||||||
|
## grid 1
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[3:----------------------------------------]|
|
||||||
|
## grid 2
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
## grid 3
|
||||||
|
|
|
||||||
|
## grid 4
|
||||||
|
{5:╔═════════╗}|
|
||||||
|
{5:║}{1: halloj! }{5:║}|
|
||||||
|
{5:║}{1: BORDAA }{5:║}|
|
||||||
|
{5:╚}{11:Left}{5:═════╝}|
|
||||||
|
]], float_pos={
|
||||||
|
[4] = { { id = 1001 }, "NW", 1, 2, 5, true }
|
||||||
|
}, win_viewport={
|
||||||
|
[2] = {win = {id = 1000}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 1, sum_scroll_delta = 0};
|
||||||
|
[4] = {win = {id = 1001}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 2, sum_scroll_delta = 0};
|
||||||
|
}}
|
||||||
|
else
|
||||||
|
screen:expect{grid=[[
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }{5:╔═════════╗}{0: }|
|
||||||
|
{0:~ }{5:║}{1: halloj! }{5:║}{0: }|
|
||||||
|
{0:~ }{5:║}{1: BORDAA }{5:║}{0: }|
|
||||||
|
{0:~ }{5:╚}{11:Left}{5:═════╝}{0: }|
|
||||||
|
|
|
||||||
|
]]}
|
||||||
|
end
|
||||||
|
|
||||||
|
meths.win_set_config(win, {footer= "Center",footer_pos="center"})
|
||||||
|
if multigrid then
|
||||||
|
screen:expect{grid=[[
|
||||||
|
## grid 1
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[3:----------------------------------------]|
|
||||||
|
## grid 2
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
## grid 3
|
||||||
|
|
|
||||||
|
## grid 4
|
||||||
|
{5:╔═════════╗}|
|
||||||
|
{5:║}{1: halloj! }{5:║}|
|
||||||
|
{5:║}{1: BORDAA }{5:║}|
|
||||||
|
{5:╚═}{11:Center}{5:══╝}|
|
||||||
|
]], float_pos={
|
||||||
|
[4] = { { id = 1001 }, "NW", 1, 2, 5, true }
|
||||||
|
}, win_viewport={
|
||||||
|
[2] = {win = {id = 1000}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 1, sum_scroll_delta = 0};
|
||||||
|
[4] = {win = {id = 1001}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 2, sum_scroll_delta = 0};
|
||||||
|
}}
|
||||||
|
else
|
||||||
|
screen:expect{grid=[[
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }{5:╔═════════╗}{0: }|
|
||||||
|
{0:~ }{5:║}{1: halloj! }{5:║}{0: }|
|
||||||
|
{0:~ }{5:║}{1: BORDAA }{5:║}{0: }|
|
||||||
|
{0:~ }{5:╚═}{11:Center}{5:══╝}{0: }|
|
||||||
|
|
|
||||||
|
]]}
|
||||||
|
end
|
||||||
|
|
||||||
|
meths.win_set_config(win, {footer= "Right",footer_pos="right"})
|
||||||
|
if multigrid then
|
||||||
|
screen:expect{grid=[[
|
||||||
|
## grid 1
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[3:----------------------------------------]|
|
||||||
|
## grid 2
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
## grid 3
|
||||||
|
|
|
||||||
|
## grid 4
|
||||||
|
{5:╔═════════╗}|
|
||||||
|
{5:║}{1: halloj! }{5:║}|
|
||||||
|
{5:║}{1: BORDAA }{5:║}|
|
||||||
|
{5:╚════}{11:Right}{5:╝}|
|
||||||
|
]], float_pos={
|
||||||
|
[4] = { { id = 1001 }, "NW", 1, 2, 5, true }
|
||||||
|
}, win_viewport={
|
||||||
|
[2] = {win = {id = 1000}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 1, sum_scroll_delta = 0};
|
||||||
|
[4] = {win = {id = 1001}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 2, sum_scroll_delta = 0};
|
||||||
|
}}
|
||||||
|
else
|
||||||
|
screen:expect{grid=[[
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }{5:╔═════════╗}{0: }|
|
||||||
|
{0:~ }{5:║}{1: halloj! }{5:║}{0: }|
|
||||||
|
{0:~ }{5:║}{1: BORDAA }{5:║}{0: }|
|
||||||
|
{0:~ }{5:╚════}{11:Right}{5:╝}{0: }|
|
||||||
|
|
|
||||||
|
]]}
|
||||||
|
end
|
||||||
|
|
||||||
|
meths.win_set_config(win, {footer= { {"🦄"},{"BB"}},footer_pos="right"})
|
||||||
|
if multigrid then
|
||||||
|
screen:expect{grid=[[
|
||||||
|
## grid 1
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[3:----------------------------------------]|
|
||||||
|
## grid 2
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
## grid 3
|
||||||
|
|
|
||||||
|
## grid 4
|
||||||
|
{5:╔═════════╗}|
|
||||||
|
{5:║}{1: halloj! }{5:║}|
|
||||||
|
{5:║}{1: BORDAA }{5:║}|
|
||||||
|
{5:╚═════}🦄BB{5:╝}|
|
||||||
|
]], float_pos={
|
||||||
|
[4] = { { id = 1001 }, "NW", 1, 2, 5, true }
|
||||||
|
}, win_viewport={
|
||||||
|
[2] = {win = {id = 1000}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 1, sum_scroll_delta = 0};
|
||||||
|
[4] = {win = {id = 1001}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 2, sum_scroll_delta = 0};
|
||||||
|
}}
|
||||||
|
else
|
||||||
|
screen:expect{grid=[[
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }{5:╔═════════╗}{0: }|
|
||||||
|
{0:~ }{5:║}{1: halloj! }{5:║}{0: }|
|
||||||
|
{0:~ }{5:║}{1: BORDAA }{5:║}{0: }|
|
||||||
|
{0:~ }{5:╚═════}🦄BB{5:╝}{0: }|
|
||||||
|
|
|
||||||
|
]]}
|
||||||
|
end
|
||||||
|
end)
|
||||||
|
|
||||||
|
it('border with title and footer', function()
|
||||||
|
local buf = meths.create_buf(false, false)
|
||||||
|
meths.buf_set_lines(buf, 0, -1, true, {' halloj! ',
|
||||||
|
' BORDAA '})
|
||||||
|
local win = meths.open_win(buf, false, {
|
||||||
|
relative='editor', width=9, height=2, row=2, col=5, border="double",
|
||||||
|
title = "Left", title_pos = "left", footer = "Right", footer_pos = "right",
|
||||||
|
})
|
||||||
|
|
||||||
|
if multigrid then
|
||||||
|
screen:expect{grid=[[
|
||||||
|
## grid 1
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[3:----------------------------------------]|
|
||||||
|
## grid 2
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
## grid 3
|
||||||
|
|
|
||||||
|
## grid 4
|
||||||
|
{5:╔}{11:Left}{5:═════╗}|
|
||||||
|
{5:║}{1: halloj! }{5:║}|
|
||||||
|
{5:║}{1: BORDAA }{5:║}|
|
||||||
|
{5:╚════}{11:Right}{5:╝}|
|
||||||
|
]], float_pos={
|
||||||
|
[4] = { { id = 1001 }, "NW", 1, 2, 5, true }
|
||||||
|
}, win_viewport={
|
||||||
|
[2] = {win = {id = 1000}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 1, sum_scroll_delta = 0};
|
||||||
|
[4] = {win = {id = 1001}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 2, sum_scroll_delta = 0};
|
||||||
|
}}
|
||||||
|
else
|
||||||
|
screen:expect{grid=[[
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }{5:╔}{11:Left}{5:═════╗}{0: }|
|
||||||
|
{0:~ }{5:║}{1: halloj! }{5:║}{0: }|
|
||||||
|
{0:~ }{5:║}{1: BORDAA }{5:║}{0: }|
|
||||||
|
{0:~ }{5:╚════}{11:Right}{5:╝}{0: }|
|
||||||
|
|
|
||||||
|
]]}
|
||||||
|
end
|
||||||
|
|
||||||
|
meths.win_set_config(win, {title= "Center",title_pos="center",footer= "Center",footer_pos="center"})
|
||||||
|
if multigrid then
|
||||||
|
screen:expect{grid=[[
|
||||||
|
## grid 1
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[3:----------------------------------------]|
|
||||||
|
## grid 2
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
## grid 3
|
||||||
|
|
|
||||||
|
## grid 4
|
||||||
|
{5:╔═}{11:Center}{5:══╗}|
|
||||||
|
{5:║}{1: halloj! }{5:║}|
|
||||||
|
{5:║}{1: BORDAA }{5:║}|
|
||||||
|
{5:╚═}{11:Center}{5:══╝}|
|
||||||
|
]], float_pos={
|
||||||
|
[4] = { { id = 1001 }, "NW", 1, 2, 5, true }
|
||||||
|
}, win_viewport={
|
||||||
|
[2] = {win = {id = 1000}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 1, sum_scroll_delta = 0};
|
||||||
|
[4] = {win = {id = 1001}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 2, sum_scroll_delta = 0};
|
||||||
|
}}
|
||||||
|
else
|
||||||
|
screen:expect{grid=[[
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }{5:╔═}{11:Center}{5:══╗}{0: }|
|
||||||
|
{0:~ }{5:║}{1: halloj! }{5:║}{0: }|
|
||||||
|
{0:~ }{5:║}{1: BORDAA }{5:║}{0: }|
|
||||||
|
{0:~ }{5:╚═}{11:Center}{5:══╝}{0: }|
|
||||||
|
|
|
||||||
|
]]}
|
||||||
|
end
|
||||||
|
|
||||||
|
meths.win_set_config(win, {title= "Right",title_pos="right",footer= "Left",footer_pos="left"})
|
||||||
|
if multigrid then
|
||||||
|
screen:expect{grid=[[
|
||||||
|
## grid 1
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[3:----------------------------------------]|
|
||||||
|
## grid 2
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
## grid 3
|
||||||
|
|
|
||||||
|
## grid 4
|
||||||
|
{5:╔════}{11:Right}{5:╗}|
|
||||||
|
{5:║}{1: halloj! }{5:║}|
|
||||||
|
{5:║}{1: BORDAA }{5:║}|
|
||||||
|
{5:╚}{11:Left}{5:═════╝}|
|
||||||
|
]], float_pos={
|
||||||
|
[4] = { { id = 1001 }, "NW", 1, 2, 5, true }
|
||||||
|
}, win_viewport={
|
||||||
|
[2] = {win = {id = 1000}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 1, sum_scroll_delta = 0};
|
||||||
|
[4] = {win = {id = 1001}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 2, sum_scroll_delta = 0};
|
||||||
|
}}
|
||||||
|
else
|
||||||
|
screen:expect{grid=[[
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }{5:╔════}{11:Right}{5:╗}{0: }|
|
||||||
|
{0:~ }{5:║}{1: halloj! }{5:║}{0: }|
|
||||||
|
{0:~ }{5:║}{1: BORDAA }{5:║}{0: }|
|
||||||
|
{0:~ }{5:╚}{11:Left}{5:═════╝}{0: }|
|
||||||
|
|
|
||||||
|
]]}
|
||||||
|
end
|
||||||
|
|
||||||
|
meths.win_set_config(win, {title= { {"🦄"},{"BB"}},title_pos="right",footer= { {"🦄"},{"BB"}},footer_pos="right"})
|
||||||
|
if multigrid then
|
||||||
|
screen:expect{grid=[[
|
||||||
|
## grid 1
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[2:----------------------------------------]|
|
||||||
|
[3:----------------------------------------]|
|
||||||
|
## grid 2
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }|
|
||||||
|
## grid 3
|
||||||
|
|
|
||||||
|
## grid 4
|
||||||
|
{5:╔═════}🦄BB{5:╗}|
|
||||||
|
{5:║}{1: halloj! }{5:║}|
|
||||||
|
{5:║}{1: BORDAA }{5:║}|
|
||||||
|
{5:╚═════}🦄BB{5:╝}|
|
||||||
|
]], float_pos={
|
||||||
|
[4] = { { id = 1001 }, "NW", 1, 2, 5, true }
|
||||||
|
}, win_viewport={
|
||||||
|
[2] = {win = {id = 1000}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 1, sum_scroll_delta = 0};
|
||||||
|
[4] = {win = {id = 1001}, topline = 0, botline = 2, curline = 0, curcol = 0, linecount = 2, sum_scroll_delta = 0};
|
||||||
|
}}
|
||||||
|
else
|
||||||
|
screen:expect{grid=[[
|
||||||
|
^ |
|
||||||
|
{0:~ }|
|
||||||
|
{0:~ }{5:╔═════}🦄BB{5:╗}{0: }|
|
||||||
|
{0:~ }{5:║}{1: halloj! }{5:║}{0: }|
|
||||||
|
{0:~ }{5:║}{1: BORDAA }{5:║}{0: }|
|
||||||
|
{0:~ }{5:╚═════}🦄BB{5:╝}{0: }|
|
||||||
|
|
|
||||||
|
]]}
|
||||||
|
end
|
||||||
|
end)
|
||||||
|
|
||||||
it('terminates border on edge of viewport when window extends past viewport', function()
|
it('terminates border on edge of viewport when window extends past viewport', function()
|
||||||
local buf = meths.create_buf(false, false)
|
local buf = meths.create_buf(false, false)
|
||||||
meths.open_win(buf, false, {relative='editor', width=40, height=7, row=0, col=0, border="single", zindex=201})
|
meths.open_win(buf, false, {relative='editor', width=40, height=7, row=0, col=0, border="single", zindex=201})
|
||||||
|
Loading…
Reference in New Issue
Block a user