Mercurial > vim
changeset 25006:496221916885 v8.2.3040
patch 8.2.3040: GUI: dropping files not tested
Commit: https://github.com/vim/vim/commit/18d46587b985923ef4b90b19a0cf37a094607fec
Author: Yegappan Lakshmanan <yegappan@yahoo.com>
Date: Wed Jun 23 20:46:52 2021 +0200
patch 8.2.3040: GUI: dropping files not tested
Problem: GUI: dropping files not tested.
Solution: Add test_gui_drop_files() and tests. (Yegappan Lakshmanan,
closes #8434)
author | Bram Moolenaar <Bram@vim.org> |
---|---|
date | Wed, 23 Jun 2021 21:00:03 +0200 |
parents | 791ae2f86aa4 |
children | e7ade92e9674 |
files | runtime/doc/eval.txt runtime/doc/testing.txt runtime/doc/usr_41.txt src/evalfunc.c src/gui.c src/proto/testing.pro src/testdir/test_gui.vim src/testing.c src/version.c |
diffstat | 9 files changed, 174 insertions(+), 5 deletions(-) [+] |
line wrap: on
line diff
--- a/runtime/doc/eval.txt +++ b/runtime/doc/eval.txt @@ -3022,6 +3022,8 @@ test_feedinput({string}) none add key se test_garbagecollect_now() none free memory right now for testing test_garbagecollect_soon() none free memory soon for testing test_getvalue({string}) any get value of an internal variable +test_gui_drop_files({list}, {row}, {col}, {mods}) + none drop a list of files in a window test_gui_mouse_event({button}, {row}, {col}, {repeated}, {mods}) none add a mouse event to the input buffer test_ignore_error({expr}) none ignore a specific error
--- a/runtime/doc/testing.txt +++ b/runtime/doc/testing.txt @@ -79,10 +79,23 @@ test_getvalue({name}) *test_getvalue Can also be used as a |method|: > GetName()->test_getvalue() < + *test_gui_drop_files()* +test_gui_drop_files({list}, {row}, {col}, {mods}) + Drop one or more files in {list} in the window at {row}, {col}. + This function only works when the GUI is running. + + The supported values for {mods} are: + 0x4 Shift + 0x8 Alt + 0x10 Ctrl + The files are added to the argument list and the first file in + {list} is edited in the window. See |drag-n-drop| for more + information. + *test_gui_mouse_event()* test_gui_mouse_event({button}, {row}, {col}, {multiclick}, {modifiers}) - Inject a mouse button click event. This function works only - when GUI is running. + Inject a mouse button click event. This function only works + when the GUI is running. The supported values for {button} are: 0 right mouse button 1 middle mouse button @@ -92,7 +105,9 @@ test_gui_mouse_event({button}, {row}, {c 5 scroll wheel up 6 scroll wheel left 7 scroll wheel right - {row} and {col} specify the location of the mouse click. + {row} and {col} specify the location of the mouse click. The + first row of the Vim window is 1 and the last row is 'lines'. + The maximum value of {col} is 'columns'. To inject a multiclick event, set {multiclick} to 1. The supported values for {modifiers} are: 4 shift is pressed
--- a/runtime/doc/usr_41.txt +++ b/runtime/doc/usr_41.txt @@ -1021,6 +1021,7 @@ Testing: *test-functions* test_garbagecollect_now() free memory right now test_garbagecollect_soon() set a flag to free memory soon test_getvalue() get value of an internal variable + test_gui_drop_files() drop file(s) in a window test_gui_mouse_event() add a GUI mouse event to the input buffer test_ignore_error() ignore a specific error message test_null_blob() return a null Blob
--- a/src/evalfunc.c +++ b/src/evalfunc.c @@ -1700,6 +1700,8 @@ static funcentry_T global_functions[] = ret_void, f_test_garbagecollect_soon}, {"test_getvalue", 1, 1, FEARG_1, NULL, ret_number, f_test_getvalue}, + {"test_gui_drop_files", 4, 4, 0, NULL, + ret_void, f_test_gui_drop_files}, {"test_gui_mouse_event", 5, 5, 0, NULL, ret_void, f_test_gui_mouse_event}, {"test_ignore_error", 1, 1, FEARG_1, NULL,
--- a/src/gui.c +++ b/src/gui.c @@ -5567,6 +5567,7 @@ gui_handle_drop( { vim_free(fnames[0]); vim_free(fnames); + vim_free(p); } else handle_drop(count, fnames, (modifiers & MOUSE_CTRL) != 0,
--- a/src/proto/testing.pro +++ b/src/proto/testing.pro @@ -36,4 +36,5 @@ void f_test_scrollbar(typval_T *argvars, void f_test_setmouse(typval_T *argvars, typval_T *rettv); void f_test_gui_mouse_event(typval_T *argvars, typval_T *rettv); void f_test_settime(typval_T *argvars, typval_T *rettv); +void f_test_gui_drop_files(typval_T *argvars, typval_T *rettv); /* vim: set ft=c : */
--- a/src/testdir/test_gui.vim +++ b/src/testdir/test_gui.vim @@ -1158,4 +1158,93 @@ func Test_gui_tablabel_tooltip() let &lines = save_lines endfunc +" Test for dropping files into a window in GUI +func DropFilesInCmdLine() + call feedkeys(":\"", 'L') + call test_gui_drop_files(['a.c', 'b.c'], &lines, 1, 0) + call feedkeys("\<CR>", 'L') +endfunc + +func Test_gui_drop_files() + call assert_fails('call test_gui_drop_files(1, 1, 1, 0)', 'E474:') + call assert_fails('call test_gui_drop_files(["x"], "", 1, 0)', 'E474:') + call assert_fails('call test_gui_drop_files(["x"], 1, "", 0)', 'E474:') + call assert_fails('call test_gui_drop_files(["x"], 1, 1, "")', 'E474:') + + %bw! + %argdelete + call test_gui_drop_files([], 1, 1, 0) + call assert_equal([], argv()) + call test_gui_drop_files([1, 2], 1, 1, 0) + call assert_equal([], argv()) + + call test_gui_drop_files(['a.c', 'b.c'], 1, 1, 0) + call assert_equal(['a.c', 'b.c'], argv()) + %bw! + %argdelete + call test_gui_drop_files([], 1, 1, 0) + call assert_equal([], argv()) + %bw! + " if the buffer in the window is modified, then the file should be opened in + " a new window + set modified + call test_gui_drop_files(['x.c', 'y.c'], 1, 1, 0) + call assert_equal(['x.c', 'y.c'], argv()) + call assert_equal(2, winnr('$')) + call assert_equal('x.c', bufname(winbufnr(1))) + %bw! + %argdelete + " if Ctrl is pressed, then the file should be opened in a new window + call test_gui_drop_files(['s.py', 't.py'], 1, 1, 0x10) + call assert_equal(['s.py', 't.py'], argv()) + call assert_equal(2, winnr('$')) + call assert_equal('s.py', bufname(winbufnr(1))) + %bw! + %argdelete + " drop the files in a non-current window + belowright new + call test_gui_drop_files(['a.py', 'b.py'], 1, 1, 0) + call assert_equal(['a.py', 'b.py'], argv()) + call assert_equal(2, winnr('$')) + call assert_equal(1, winnr()) + call assert_equal('a.py', bufname(winbufnr(1))) + %bw! + %argdelete + " pressing shift when dropping files should change directory + let save_cwd = getcwd() + call mkdir('Xdir1') + call writefile([], 'Xdir1/Xfile1') + call writefile([], 'Xdir1/Xfile2') + call test_gui_drop_files(['Xdir1/Xfile1', 'Xdir1/Xfile2'], 1, 1, 0x4) + call assert_equal('Xdir1', fnamemodify(getcwd(), ':t')) + call assert_equal('Xfile1', @%) + call chdir(save_cwd) + " pressing shift when dropping directory and files should change directory + call test_gui_drop_files(['Xdir1', 'Xdir1/Xfile2'], 1, 1, 0x4) + call assert_equal('Xdir1', fnamemodify(getcwd(), ':t')) + call assert_equal('Xdir1', fnamemodify(@%, ':t')) + call chdir(save_cwd) + %bw! + %argdelete + " dropping a directory should edit it + call test_gui_drop_files(['Xdir1'], 1, 1, 0) + call assert_equal('Xdir1', @%) + %bw! + %argdelete + " dropping only a directory name with Shift should ignore it + call test_gui_drop_files(['Xdir1'], 1, 1, 0x4) + call assert_equal('', @%) + %bw! + %argdelete + call delete('Xdir1', 'rf') + " drop files in the command line. The GUI drop files adds the file names to + " the low level input buffer. So need to use a cmdline map and feedkeys() + " with 'Lx!' to process it in this function itself. + cnoremap <expr> <buffer> <F4> DropFilesInCmdLine() + call feedkeys(":\"\<F4>\<CR>", 'xt') + call feedkeys('k', 'Lx!') + call assert_equal('"a.c b.c', @:) + cunmap <buffer> <F4> +endfunc + " vim: shiftwidth=2 sts=2 expandtab
--- a/src/testing.c +++ b/src/testing.c @@ -1224,7 +1224,7 @@ f_test_setmouse(typval_T *argvars, typva void f_test_gui_mouse_event(typval_T *argvars UNUSED, typval_T *rettv UNUSED) { -#ifdef FEAT_GUI +# ifdef FEAT_GUI int button; int row; int col; @@ -1248,7 +1248,7 @@ f_test_gui_mouse_event(typval_T *argvars mods = tv_get_number(&argvars[4]); gui_send_mouse_event(button, TEXT_X(col - 1), TEXT_Y(row - 1), repeated_click, mods); -#endif +# endif } void @@ -1257,5 +1257,61 @@ f_test_settime(typval_T *argvars, typval time_for_testing = (time_t)tv_get_number(&argvars[0]); } + void +f_test_gui_drop_files(typval_T *argvars UNUSED, typval_T *rettv UNUSED) +{ +# ifdef FEAT_GUI + int row; + int col; + int_u mods; + char_u **fnames; + int count = 0; + list_T *l; + listitem_T *li; + + if (argvars[0].v_type != VAR_LIST + || (argvars[1].v_type) != VAR_NUMBER + || (argvars[2].v_type) != VAR_NUMBER + || (argvars[3].v_type) != VAR_NUMBER) + { + emsg(_(e_invarg)); + return; + } + + row = tv_get_number(&argvars[1]); + col = tv_get_number(&argvars[2]); + mods = tv_get_number(&argvars[3]); + + l = argvars[0].vval.v_list; + if (list_len(l) == 0) + return; + + fnames = ALLOC_MULT(char_u *, list_len(l)); + if (fnames == NULL) + return; + + FOR_ALL_LIST_ITEMS(l, li) + { + // ignore non-string items + if (li->li_tv.v_type != VAR_STRING) + continue; + + fnames[count] = vim_strsave(li->li_tv.vval.v_string); + if (fnames[count] == NULL) + { + while (--count >= 0) + vim_free(fnames[count]); + vim_free(fnames); + return; + } + count++; + } + + if (count > 0) + gui_handle_drop(TEXT_X(col - 1), TEXT_Y(row - 1), mods, fnames, count); + else + vim_free(fnames); +# endif +} #endif // defined(FEAT_EVAL)