]> git.ipfire.org Git - thirdparty/vim.git/commitdiff
patch 8.1.1402: "timer" option of popup windows not supported v8.1.1402
authorBram Moolenaar <Bram@vim.org>
Sun, 26 May 2019 18:10:06 +0000 (20:10 +0200)
committerBram Moolenaar <Bram@vim.org>
Sun, 26 May 2019 18:10:06 +0000 (20:10 +0200)
Problem:    "timer" option of popup windows not supported.
Solution:   Implement the "timer" option. (Yasuhiro Matsumoto, closes #4439)

runtime/doc/popup.txt
src/popupwin.c
src/structs.h
src/testdir/test_popupwin.vim
src/version.c
src/window.c

index 8d3619acf7ce40a3386dfd15c4c735ed63582aff..af51885e4eee0740f3c715b8ba4d0669195672db 100644 (file)
@@ -142,7 +142,7 @@ popup_notification({text}, {options})                        *popup_notification()*
                                \ 'tab': -1,
                                \ 'zindex': 200,
                                \ 'highlight': 'WarningMsg',
-                               \ 'border: [],
+                               \ 'border': [],
                                \ })
 <              Use {options} to change the properties.
 
@@ -339,7 +339,6 @@ The second argument of |popup_create()| is a dictionary with options:
        zindex          priority for the popup, default 50
        time            time in milliseconds after which the popup will close;
                        when omitted |popup_close()| must be used.
-                       {not implemented yet}
        moved           "cell": close the popup if the cursor moved at least
                        one screen cell; "word" allows for moving within
                        |<cword>|, "WORD" allows for moving within |<cWORD>|,
index 5439c64b4eba4424e8eccb0441010376e43a5c5f..f08f784353a8b94cd04323f7a1f175939aaa7756 100644 (file)
     static void
 apply_options(win_T *wp, buf_T *buf UNUSED, dict_T *dict)
 {
+    int            nr;
+
     wp->w_maxwidth = dict_get_number(dict, (char_u *)"maxwidth");
     wp->w_maxheight = dict_get_number(dict, (char_u *)"maxheight");
     wp->w_winrow = dict_get_number(dict, (char_u *)"line");
     wp->w_wincol = dict_get_number(dict, (char_u *)"col");
     wp->w_zindex = dict_get_number(dict, (char_u *)"zindex");
+
+    // Add timer to close the popup after some time.
+    nr = dict_get_number(dict, (char_u *)"time");
+    if (nr > 0)
+    {
+       char_u      cbbuf[50];
+       char_u      *ptr = cbbuf;
+       typval_T    tv;
+
+       vim_snprintf((char *)cbbuf, sizeof(cbbuf),
+                                          "{_ -> popup_close(%d)}", wp->w_id);
+       if (get_lambda_tv(&ptr, &tv, TRUE) == OK)
+       {
+           wp->w_popup_timer = create_timer(nr, 0);
+           wp->w_popup_timer->tr_callback =
+                                 vim_strsave(partial_name(tv.vval.v_partial));
+           func_ref(wp->w_popup_timer->tr_callback);
+           wp->w_popup_timer->tr_partial = tv.vval.v_partial;
+       }
+    }
+
 }
 
 /*
@@ -177,6 +200,15 @@ f_popup_close(typval_T *argvars, typval_T *rettv UNUSED)
     popup_close(nr);
 }
 
+    static void
+popup_undisplay(win_T *wp)
+{
+    if (wp->w_winrow + wp->w_height >= cmdline_row)
+       clear_cmdline = TRUE;
+    win_free_popup(wp);
+    redraw_all_later(NOT_VALID);
+}
+
 /*
  * Close a popup window by Window-id.
  */
@@ -195,8 +227,7 @@ popup_close(int id)
                first_popupwin = wp->w_next;
            else
                prev->w_next = wp->w_next;
-           win_free_popup(wp);
-           redraw_all_later(NOT_VALID);
+           popup_undisplay(wp);
            return;
        }
 
@@ -222,8 +253,7 @@ popup_close_tabpage(tabpage_T *tp, int id)
                *root = wp->w_next;
            else
                prev->w_next = wp->w_next;
-           win_free_popup(wp);
-           redraw_all_later(NOT_VALID);
+           popup_undisplay(wp);
            return;
        }
 }
index e424830f352763dd4fc0dce53ce40543173f8a43..7ead00ceacc29929e1b9d037eddfaad00ad36728 100644 (file)
@@ -1941,6 +1941,24 @@ typedef struct {
 } syn_time_T;
 #endif
 
+typedef struct timer_S timer_T;
+struct timer_S
+{
+    long       tr_id;
+#ifdef FEAT_TIMERS
+    timer_T    *tr_next;
+    timer_T    *tr_prev;
+    proftime_T tr_due;             /* when the callback is to be invoked */
+    char       tr_firing;          /* when TRUE callback is being called */
+    char       tr_paused;          /* when TRUE callback is not invoked */
+    int                tr_repeat;          /* number of times to repeat, -1 forever */
+    long       tr_interval;        /* msec */
+    char_u     *tr_callback;       /* allocated */
+    partial_T  *tr_partial;
+    int                tr_emsg_count;
+#endif
+};
+
 #ifdef FEAT_CRYPT
 /*
  * Structure to hold the type of encryption and the state of encryption or
@@ -2856,6 +2874,7 @@ struct window_S
     int                w_zindex;
     int                w_maxheight;        // "maxheight" for popup window
     int                w_maxwidth;         // "maxwidth" for popup window
+    timer_T    *w_popup_timer;     // timer for closing popup window
 #endif
 
 
@@ -3434,24 +3453,6 @@ struct js_reader
 };
 typedef struct js_reader js_read_T;
 
-typedef struct timer_S timer_T;
-struct timer_S
-{
-    long       tr_id;
-#ifdef FEAT_TIMERS
-    timer_T    *tr_next;
-    timer_T    *tr_prev;
-    proftime_T tr_due;             /* when the callback is to be invoked */
-    char       tr_firing;          /* when TRUE callback is being called */
-    char       tr_paused;          /* when TRUE callback is not invoked */
-    int                tr_repeat;          /* number of times to repeat, -1 forever */
-    long       tr_interval;        /* msec */
-    char_u     *tr_callback;       /* allocated */
-    partial_T  *tr_partial;
-    int                tr_emsg_count;
-#endif
-};
-
 /* Maximum number of commands from + or -c arguments. */
 #define MAX_ARG_CMDS 10
 
index e79c03d201c7f999098e2ff4527e205ec40174ef..0f48cbd9a5ac55c82775344be6e81f634de468c6 100644 (file)
@@ -37,3 +37,37 @@ func Test_simple_popup()
   call StopVimInTerminal(buf)
   call delete('XtestPopup')
 endfunc
+
+func Test_popup_time()
+  topleft vnew
+  call setline(1, 'hello')
+
+  call popup_create('world', {
+       \ 'line': 1,
+       \ 'col': 1,
+       \ 'time': 500,
+       \})
+  redraw
+  let line = join(map(range(1, 5), 'screenstring(1, v:val)'), '')
+  call assert_equal('world', line)
+
+  sleep 700m
+  let line = join(map(range(1, 5), 'screenstring(1, v:val)'), '')
+  call assert_equal('hello', line)
+
+  call popup_create('on the command line', {
+       \ 'line': &lines,
+       \ 'col': 10,
+       \ 'time': 500,
+       \})
+  redraw
+  let line = join(map(range(1, 30), 'screenstring(&lines, v:val)'), '')
+  call assert_match('.*on the command line.*', line)
+
+  sleep 700m
+  redraw
+  let line = join(map(range(1, 30), 'screenstring(&lines, v:val)'), '')
+  call assert_notmatch('.*on the command line.*', line)
+
+  bwipe!
+endfunc
index 940ac1440ec4b6c9ce140913a62fc8145d065008..f974b6b771ec5393a5c5139dd97509c00b54bd38 100644 (file)
@@ -767,6 +767,8 @@ static char *(features[]) =
 
 static int included_patches[] =
 {   /* Add new patch number below this line */
+/**/
+    1402,
 /**/
     1401,
 /**/
index bc8dac0b47efc4f0d0b6bd3071b0b769c5e8e86d..2cd35a4cbd6643e1b3ee51a3e0e475099237f11b 100644 (file)
@@ -3670,12 +3670,8 @@ free_tabpage(tabpage_T *tp)
     diff_clear(tp);
 # endif
 # ifdef FEAT_TEXT_PROP
-    {
-       win_T *wp;
-
-       while (tp->tp_first_popupwin != NULL)
-           popup_close_tabpage(tp, tp->tp_first_popupwin->w_id);
-    }
+    while (tp->tp_first_popupwin != NULL)
+       popup_close_tabpage(tp, tp->tp_first_popupwin->w_id);
 #endif
     for (idx = 0; idx < SNAP_COUNT; ++idx)
        clear_snapshot(tp, idx);
@@ -4871,6 +4867,8 @@ win_unlisted(win_T *wp)
 win_free_popup(win_T *win)
 {
     win_close_buffer(win, TRUE, FALSE);
+    if (win->w_popup_timer != NULL)
+       stop_timer(win->w_popup_timer);
     vim_free(win->w_frame);
     win_free(win, NULL);
 }