diff options
author | Bram Moolenaar <Bram@vim.org> | 2019-08-03 16:18:07 +0200 |
---|---|---|
committer | Bram Moolenaar <Bram@vim.org> | 2019-08-03 16:18:07 +0200 |
commit | 749fa0af85232be1d44b77a09161f71cdbace62c (patch) | |
tree | 1aae6e9a655399ecadba0db9e399323077e0d705 | |
parent | eda35f7127c6ac51573eda808687f6369c31ee2d (diff) | |
download | vim-git-749fa0af85232be1d44b77a09161f71cdbace62c.tar.gz |
patch 8.1.1799: cannot avoid mapping for a popup windowv8.1.1799
Problem: Cannot avoid mapping for a popup window.
Solution: Add the "mapping" property, default TRUE.
-rw-r--r-- | runtime/doc/popup.txt | 29 | ||||
-rw-r--r-- | src/getchar.c | 3 | ||||
-rw-r--r-- | src/popupwin.c | 31 | ||||
-rw-r--r-- | src/proto/popupwin.pro | 1 | ||||
-rw-r--r-- | src/testdir/test_popupwin.vim | 7 | ||||
-rw-r--r-- | src/version.c | 2 | ||||
-rw-r--r-- | src/vim.h | 1 |
7 files changed, 69 insertions, 5 deletions
diff --git a/runtime/doc/popup.txt b/runtime/doc/popup.txt index b58ade69d..bac34331f 100644 --- a/runtime/doc/popup.txt +++ b/runtime/doc/popup.txt @@ -246,6 +246,7 @@ popup_dialog({what}, {options}) *popup_dialog()* \ drag: 1, \ border: [], \ padding: [], + \ mapping: 0, \}) < Use {options} to change the properties. E.g. add a 'filter' option with value 'popup_filter_yesno'. Example: > @@ -369,12 +370,20 @@ popup_menu({what}, {options}) *popup_menu()* \ cursorline: 1, \ padding: [0,1,0,1], \ filter: 'popup_filter_menu', + \ mapping: 0, \ }) < The current line is highlighted with a match using "PopupSelected", or "PmenuSel" if that is not defined. Use {options} to change the properties. Should at least set "callback" to a function that handles the selected item. + Example: > + func ColorSelected(id, result) + " use a:result + endfunc + call popup_menu(['red', 'green', 'blue'], #{ + \ callback: 'ColorSelected', + \ }) popup_move({id}, {options}) *popup_move()* @@ -433,16 +442,17 @@ popup_setoptions({id}, {options}) *popup_setoptions()* borderhighlight callback close - drag - resize cursorline + drag filter firstline flip highlight + mapping mask moved padding + resize scrollbar scrollbarhighlight thumbhighlight @@ -615,6 +625,9 @@ The second argument of |popup_create()| is a dictionary with options: Default is zero, except for |popup_menu()|. filter A callback that can filter typed characters, see |popup-filter|. + mapping Allow for key mapping. When FALSE and the popup is + visible and has a filter callback key mapping is + disabled. Default value is TRUE. callback A callback that is called when the popup closes, e.g. when using |popup_filter_menu()|, see |popup-callback|. @@ -671,8 +684,11 @@ key as a string, e.g.: > endif return 0 endfunc - -Currently the key is what results after any mapping. This may change... +< *popup-mapping* +Normally the key is what results after any mapping, since the keys pass on as +normal input if the filter does not use it. If the filter consumes all the +keys, set the "mapping" property to zero so that mappings do not get in the +way. This is default for |popup_menu()| and |popup_dialog()|. Some common key actions: x close the popup (see note below) @@ -703,6 +719,11 @@ the second argument of `popup_close()`. If the popup is force-closed, e.g. because the cursor moved or CTRL-C was pressed, the number -1 is passed to the callback. +Example: > + func SelectedColor(id, result) + echo 'choice made: ' .. a:result + endfunc + POPUP SCROLLBAR *popup-scrollbar* diff --git a/src/getchar.c b/src/getchar.c index fe1cc7e2e..4a3587c3f 100644 --- a/src/getchar.c +++ b/src/getchar.c @@ -1575,6 +1575,9 @@ vgetc(void) #if defined(FEAT_XIM) && defined(FEAT_GUI_GTK) || im_is_preediting() #endif +#if defined(FEAT_TEXT_PROP) + || popup_no_mapping() +#endif ) { // no mapping after modifier has been read diff --git a/src/popupwin.c b/src/popupwin.c index 4ca6d9fdf..28ad48cfc 100644 --- a/src/popupwin.c +++ b/src/popupwin.c @@ -800,6 +800,15 @@ apply_general_options(win_T *wp, dict_T *dict) set_callback(&wp->w_filter_cb, &callback); } } + di = dict_find(dict, (char_u *)"mapping", -1); + if (di != NULL) + { + nr = dict_get_number(dict, (char_u *)"mapping"); + if (nr) + wp->w_popup_flags |= POPF_MAPPING; + else + wp->w_popup_flags &= ~POPF_MAPPING; + } di = dict_find(dict, (char_u *)"callback", -1); if (di != NULL) @@ -1413,7 +1422,7 @@ popup_create(typval_T *argvars, typval_T *rettv, create_type_T type) if (rettv != NULL) rettv->vval.v_number = wp->w_id; wp->w_popup_pos = POPPOS_TOPLEFT; - wp->w_popup_flags = POPF_IS_POPUP; + wp->w_popup_flags = POPF_IS_POPUP | POPF_MAPPING; if (buf != NULL) { @@ -1561,6 +1570,7 @@ popup_create(typval_T *argvars, typval_T *rettv, create_type_T type) wp->w_popup_pos = POPPOS_CENTER; wp->w_zindex = POPUPWIN_DIALOG_ZINDEX; wp->w_popup_flags |= POPF_DRAG; + wp->w_popup_flags &= ~POPF_MAPPING; for (i = 0; i < 4; ++i) { wp->w_popup_border[i] = 1; @@ -2502,6 +2512,25 @@ popup_do_filter(int c) } /* + * Return TRUE if there is a popup visible with a filter callback and the + * "mapping" property off. + */ + int +popup_no_mapping(void) +{ + int round; + win_T *wp; + + for (round = 1; round <= 2; ++round) + for (wp = round == 1 ? first_popupwin : curtab->tp_first_popupwin; + wp != NULL; wp = wp->w_next) + if (wp->w_filter_cb.cb_name != NULL + && (wp->w_popup_flags & (POPF_HIDDEN | POPF_MAPPING)) == 0) + return TRUE; + return FALSE; +} + +/* * Called when the cursor moved: check if any popup needs to be closed if the * cursor moved far enough. */ diff --git a/src/proto/popupwin.pro b/src/proto/popupwin.pro index b964fc0dd..f1d0d2b52 100644 --- a/src/proto/popupwin.pro +++ b/src/proto/popupwin.pro @@ -38,6 +38,7 @@ int error_if_popup_window(void); void popup_reset_handled(void); win_T *find_next_popup(int lowest); int popup_do_filter(int c); +int popup_no_mapping(void); void popup_check_cursor_pos(void); void may_update_popup_mask(int type); void update_popups(void (*win_update)(win_T *wp)); diff --git a/src/testdir/test_popupwin.vim b/src/testdir/test_popupwin.vim index d4b98aee7..e5d16314b 100644 --- a/src/testdir/test_popupwin.vim +++ b/src/testdir/test_popupwin.vim @@ -657,6 +657,7 @@ func Test_popup_invalid_arguments() call assert_fails('call popup_create("text", #{mask: ["asdf"]})', 'E475:') call popup_clear() call assert_fails('call popup_create("text", #{mask: test_null_list()})', 'E475:') + call assert_fails('call popup_create("text", #{mapping: []})', 'E745:') call popup_clear() endfunc @@ -1203,6 +1204,8 @@ func Test_popup_menu() let s:cb_winid = a:id let s:cb_res = a:res endfunc + " mapping won't be used in popup + map j k let winid = ShowMenu(" ", 1) let winid = ShowMenu("j \<CR>", 2) @@ -1215,6 +1218,7 @@ func Test_popup_menu() let winid = ShowMenu("\<C-C>", -1) delfunc QuitCallback + unmap j endfunc func Test_popup_menu_screenshot() @@ -2194,6 +2198,9 @@ func Test_previewpopup() call term_sendkeys(buf, "/another\<CR>\<C-W>}") call VerifyScreenDump(buf, 'Test_popupwin_previewpopup_4', {}) + call term_sendkeys(buf, ":cd ..\<CR>:\<CR>") + call VerifyScreenDump(buf, 'Test_popupwin_previewpopup_5', {}) + call StopVimInTerminal(buf) call delete('Xtags') call delete('Xtagfile') diff --git a/src/version.c b/src/version.c index ec67fe406..b2c4416ae 100644 --- a/src/version.c +++ b/src/version.c @@ -774,6 +774,8 @@ static char *(features[]) = static int included_patches[] = { /* Add new patch number below this line */ /**/ + 1799, +/**/ 1798, /**/ 1797, @@ -621,6 +621,7 @@ extern int (*dyn_libintl_wputenv)(const wchar_t *envstring); #define POPF_ON_CMDLINE 0x10 // popup overlaps command line #define POPF_DRAG 0x20 // popup can be moved by dragging #define POPF_RESIZE 0x40 // popup can be resized by dragging +#define POPF_MAPPING 0x80 // mapping keys #ifdef FEAT_TEXT_PROP # define WIN_IS_POPUP(wp) ((wp)->w_popup_flags != 0) |