# HG changeset patch # User Christian Brabandt # Date 1520109006 -3600 # Node ID 0f9dd1b43244b3b5ee40f81b9e7e8d700572e87e # Parent 6099b4bc3dc20831d10e74fd353e8e90cdd6898c patch 8.0.1563: timeout of getwinposx() can be too short commit https://github.com/vim/vim/commit/3f54fd319f6641b4bed478bcc90cdb39ede68e31 Author: Bram Moolenaar Date: Sat Mar 3 21:29:55 2018 +0100 patch 8.0.1563: timeout of getwinposx() can be too short Problem: Timeout of getwinposx() can be too short. (lilydjwg) Solution: Add getwinpos(). (closes https://github.com/vim/vim/issues/2689) diff --git a/runtime/doc/eval.txt b/runtime/doc/eval.txt --- a/runtime/doc/eval.txt +++ b/runtime/doc/eval.txt @@ -2192,8 +2192,9 @@ gettabvar({nr}, {varname} [, {def}]) gettabwinvar({tabnr}, {winnr}, {name} [, {def}]) any {name} in {winnr} in tab page {tabnr} getwininfo([{winid}]) List list of windows -getwinposx() Number X coord in pixels of GUI Vim window -getwinposy() Number Y coord in pixels of GUI Vim window +getwinpos([{tmeout}]) List X and Y coord in pixels of the Vim window +getwinposx() Number X coord in pixels of the Vim window +getwinposy() Number Y coord in pixels of the Vim window getwinvar({nr}, {varname} [, {def}]) any variable {varname} in window {nr} glob({expr} [, {nosuf} [, {list} [, {alllinks}]]]) @@ -4878,16 +4879,24 @@ gettabwinvar({tabnr}, {winnr}, {varname} :let list_is_on = gettabwinvar(1, 2, '&list') :echo "myvar = " . gettabwinvar(3, 1, 'myvar') < +getwinpos([{timeout}]) *getwinpos()* + The result is a list with two numbers, the result of + getwinposx() and getwinposy() combined: + [x-pos, y-pos] + {timeout} can be used to specify how long to wait in msec for + a response from the terminal. When omitted 100 msec is used. + *getwinposx()* getwinposx() The result is a Number, which is the X coordinate in pixels of the left hand side of the GUI Vim window. Also works for an - xterm. + xterm (uses a timeout of 100 msec). The result will be -1 if the information is not available. The value can be used with `:winpos`. *getwinposy()* getwinposy() The result is a Number, which is the Y coordinate in pixels of - the top of the GUI Vim window. Also works for an xterm. + the top of the GUI Vim window. Also works for an xterm (uses + a timeout of 100 msec). The result will be -1 if the information is not available. The value can be used with `:winpos`. diff --git a/src/evalfunc.c b/src/evalfunc.c --- a/src/evalfunc.c +++ b/src/evalfunc.c @@ -197,6 +197,7 @@ static void f_gettabinfo(typval_T *argva static void f_gettabvar(typval_T *argvars, typval_T *rettv); static void f_gettabwinvar(typval_T *argvars, typval_T *rettv); static void f_getwininfo(typval_T *argvars, typval_T *rettv); +static void f_getwinpos(typval_T *argvars, typval_T *rettv); static void f_getwinposx(typval_T *argvars, typval_T *rettv); static void f_getwinposy(typval_T *argvars, typval_T *rettv); static void f_getwinvar(typval_T *argvars, typval_T *rettv); @@ -641,6 +642,7 @@ static struct fst {"gettabvar", 2, 3, f_gettabvar}, {"gettabwinvar", 3, 4, f_gettabwinvar}, {"getwininfo", 0, 1, f_getwininfo}, + {"getwinpos", 0, 1, f_getwinpos}, {"getwinposx", 0, 0, f_getwinposx}, {"getwinposy", 0, 0, f_getwinposy}, {"getwinvar", 2, 3, f_getwinvar}, @@ -5527,6 +5529,38 @@ f_win_screenpos(typval_T *argvars, typva } /* + * "getwinpos({timeout})" function + */ + static void +f_getwinpos(typval_T *argvars UNUSED, typval_T *rettv) +{ + int x = -1; + int y = -1; + + if (rettv_list_alloc(rettv) == FAIL) + return; +#ifdef FEAT_GUI + if (gui.in_use) + gui_mch_get_winpos(&x, &y); +# if defined(HAVE_TGETENT) && defined(FEAT_TERMRESPONSE) + else +# endif +#endif +#if defined(HAVE_TGETENT) && defined(FEAT_TERMRESPONSE) + { + varnumber_T timeout = 100; + + if (argvars[0].v_type != VAR_UNKNOWN) + timeout = get_tv_number(&argvars[0]); + term_get_winpos(&x, &y, timeout); + } +#endif + list_append_number(rettv->vval.v_list, (varnumber_T)x); + list_append_number(rettv->vval.v_list, (varnumber_T)y); +} + + +/* * "getwinposx()" function */ static void @@ -5547,7 +5581,7 @@ f_getwinposx(typval_T *argvars UNUSED, t { int x, y; - if (term_get_winpos(&x, &y) == OK) + if (term_get_winpos(&x, &y, (varnumber_T)100) == OK) rettv->vval.v_number = x; } #endif @@ -5574,7 +5608,7 @@ f_getwinposy(typval_T *argvars UNUSED, t { int x, y; - if (term_get_winpos(&x, &y) == OK) + if (term_get_winpos(&x, &y, (varnumber_T)100) == OK) rettv->vval.v_number = y; } #endif diff --git a/src/proto/term.pro b/src/proto/term.pro --- a/src/proto/term.pro +++ b/src/proto/term.pro @@ -24,7 +24,7 @@ void term_cursor_right(int i); void term_append_lines(int line_count); void term_delete_lines(int line_count); void term_set_winpos(int x, int y); -int term_get_winpos(int *x, int *y); +int term_get_winpos(int *x, int *y, varnumber_T timeout); void term_set_winsize(int height, int width); void term_fg_color(int n); void term_bg_color(int n); diff --git a/src/term.c b/src/term.c --- a/src/term.c +++ b/src/term.c @@ -2789,7 +2789,7 @@ static int waiting_for_winpos = FALSE; * Returns OK or FAIL. */ int -term_get_winpos(int *x, int *y) +term_get_winpos(int *x, int *y, varnumber_T timeout) { int count = 0; @@ -2801,8 +2801,8 @@ term_get_winpos(int *x, int *y) OUT_STR(T_CGP); out_flush(); - /* Try reading the result for 100 msec. */ - while (count++ < 10) + /* Try reading the result for "timeout" msec. */ + while (count++ < timeout / 10) { (void)vpeekc_nomap(); if (winpos_x >= 0 && winpos_y >= 0) diff --git a/src/version.c b/src/version.c --- a/src/version.c +++ b/src/version.c @@ -779,6 +779,8 @@ static char *(features[]) = static int included_patches[] = { /* Add new patch number below this line */ /**/ + 1563, +/**/ 1562, /**/ 1561,