]> granicus.if.org Git - vim/commitdiff
patch 8.0.1384: not enough quickfix help; confusing winid v8.0.1384
authorBram Moolenaar <Bram@vim.org>
Sun, 10 Dec 2017 14:26:15 +0000 (15:26 +0100)
committerBram Moolenaar <Bram@vim.org>
Sun, 10 Dec 2017 14:26:15 +0000 (15:26 +0100)
Problem:    Not enough quickfix help; confusing winid.
Solution:   Add more examples in the help. When the quickfix window is not
            present, return zero for getqflist() with 'winid'. Add more tests
            for jumping to quickfix list entries. (Yegappan Lakshmanan, closes
            #2427)

runtime/doc/eval.txt
runtime/doc/quickfix.txt
src/quickfix.c
src/testdir/test_quickfix.vim
src/version.c

index 4d524679d33941e5cb62a64259ff8f217f73f8b2..93e818a44295d9f063a902a53b75d2b2be397e55 100644 (file)
@@ -1,4 +1,4 @@
-*eval.txt*     For Vim version 8.0.  Last change: 2017 Nov 24
+*eval.txt*     For Vim version 8.0.  Last change: 2017 Dec 09
 
 
                  VIM REFERENCE MANUAL    by Bram Moolenaar
@@ -2031,7 +2031,7 @@ assert_true({actual} [, {msg}])   none    assert {actual} is true
 asin({expr})                   Float   arc sine of {expr}
 atan({expr})                   Float   arc tangent of {expr}
 atan2({expr1}, {expr2})                Float   arc tangent of {expr1} / {expr2}
-balloon_show({msg})            none    show {msg} inside the balloon
+balloon_show({expr})           none    show {expr} inside the balloon
 balloon_split({msg})           List    split {msg} as used for a balloon
 browse({save}, {title}, {initdir}, {default})
                                String  put up a file requester
@@ -3056,12 +3056,16 @@ ch_open({address} [, {options}])                                *ch_open()*
 ch_read({handle} [, {options}])                                        *ch_read()*
                Read from {handle} and return the received message.
                {handle} can be a Channel or a Job that has a Channel.
+               For a NL channel this waits for a NL to arrive, except when
+               there is nothing more to read (channel was closed).
                See |channel-more|.
                {only available when compiled with the |+channel| feature}
 
 ch_readraw({handle} [, {options}])                     *ch_readraw()*
                Like ch_read() but for a JS and JSON channel does not decode
-               the message.  See |channel-more|.
+               the message.  For a NL channel it does not block waiting for
+               the NL to arrive, but otherwise works like ch_read().
+               See |channel-more|.
                {only available when compiled with the |+channel| feature}
 
 ch_sendexpr({handle}, {expr} [, {options}])                    *ch_sendexpr()*
@@ -4679,9 +4683,10 @@ getqflist([{what}])                                      *getqflist()*
                                the last quickfix list
                        size    number of entries in the quickfix list
                        title   get the list title
-                       winid   get the |window-ID| (if opened)
+                       winid   get the quickfix |window-ID|
                        all     all of the above quickfix properties
-               Non-string items in {what} are ignored.
+               Non-string items in {what} are ignored. To get the value of a
+               particular item, set it to one.
                If "nr" is not present then the current quickfix list is used.
                If both "nr" and a non-zero "id" are specified, then the list
                specified by "id" is used.
@@ -4702,7 +4707,7 @@ getqflist([{what}])                                       *getqflist()*
                        nr      quickfix list number
                        size    number of entries in the quickfix list
                        title   quickfix list title text
-                       winid   quickfix |window-ID| (if opened)
+                       winid   quickfix |window-ID|. If not present, set to 0
 
                Examples: >
                        :echo getqflist({'all': 1})
@@ -8793,8 +8798,8 @@ writefile({list}, {fname} [, {flags}])
                the file.  This flushes the file to disk, if possible.  This
                takes more time but avoids losing the file if the system
                crashes.
-               When {flags} does not contain "S" or "s" then fsync is called
-               if the 'fsync' option is set.
+               When {flags} does not contain "S" or "s" then fsync() is
+               called if the 'fsync' option is set.
                When {flags} contains "S" then fsync() is not called, even
                when 'fsync' is set.
 
index cfbfe4c856f56d34dd5b4e2d512882f4544293cf..ff66582a00bc24e4c1f293861d9a8178f76bf5a0 100644 (file)
@@ -341,6 +341,50 @@ use this code: >
        au QuickfixCmdPost make call QfMakeConv()
 Another option is using 'makeencoding'.
 
+                                                       *quickfix-title*
+Every quickfix and location list has a title. By default the title is set to
+the command that created the list. The |getqflist()| and |getloclist()|
+functions can be used to get the title of a quickfix and a location list
+respectively. The |setqflist()| and |setloclist()| functions can be used to
+modify the title of a quickfix and location list respectively. Examples: >
+       call setqflist([], 'a', {'title' : 'Cmd output'})
+       echo getqflist({'title' : 1})
+       call setloclist(3, [], 'a', {'title' : 'Cmd output'})
+       echo getloclist(3, {'title' : 1})
+<
+                                                       *quickfix-size*
+You can get the number of entries (size) in a quickfix and a location list
+using the |getqflist()| and |getloclist()| functions respectively. Examples: >
+       echo getqflist({'size' : 1})
+       echo getloclist(5, {'size' : 1})
+<
+                                                       *quickfix-context*
+Any Vim type can be associated as a context with a quickfix or location list.
+The |setqflist()| and the |setloclist()| functions can be used to associate a
+context with a quickfix and a location list respectively. The |getqflist()|
+and the |getloclist()| functions can be used to retrieve the context of a
+quickifx and a location list respectively. This is useful for a Vim plugin
+dealing with multiple quickfix/location lists.
+Examples: >
+
+       let somectx = {'name' : 'Vim', 'type' : 'Editor'}
+       call setqflist([], 'a', {'context' : somectx})
+       echo getqflist({'context' : 1})
+
+       let newctx = ['red', 'green', 'blue']
+       call setloclist(2, [], 'a', {'id' : qfid, 'context' : newctx})
+       echo getloclist(2, {'id' : qfid, 'context' : 1})
+<
+                                                       *quickfix-parse*
+You can parse a list of lines using 'erroformat' without creating or modifying
+a quickfix list using the |getqflist()| function. Examples: >
+       echo getqflist({'lines' : ["F1:10:Line10", "F2:20:Line20"]})
+       echo getqflist({'lines' : systemlist('grep -Hn quickfix *')})
+This returns a dictionary where the 'items' key contains the list of quickfix
+entries parsed from lines. The following shows how to use a custom
+'errorformat' to parse the lines without modifying the 'erroformat' option: >
+       echo getqflist({'efm' : '%f#%l#%m', 'lines' : ['F1#10#Line']})
+<
 
 EXECUTE A COMMAND IN ALL THE BUFFERS IN QUICKFIX OR LOCATION LIST:
                                                        *:cdo*
@@ -542,6 +586,13 @@ In all of the above cases, if the location list for the selected window is not
 yet set, then it is set to the location list displayed in the location list
 window.
 
+                                                       *quickfix-window-ID*
+You can use the |getqflist()| and |getloclist()| functions to obtain the
+window ID of the quickfix window and location list window respectively (if
+present).  Examples: >
+       echo getqflist({'winid' : 1}).winid
+       echo getloclist(2, {'winid' : 1}).winid
+<
 =============================================================================
 3. Using more than one list of errors                  *quickfix-error-lists*
 
@@ -586,6 +637,14 @@ list, one newer list is overwritten.  This is especially useful if you are
 browsing with ":grep" |grep|.  If you want to keep the more recent error
 lists, use ":cnewer 99" first.
 
+To get the number of lists in the quickfix and location list stack, you can
+use the |getqflist()| and |getloclist()| functions respectively with the list
+number set to the special value '$'. Examples: >
+       echo getqflist({'nr' : '$'}).nr
+       echo getloclist(3, {'nr' : '$'}).nr
+To get the number of the current list in the stack: >
+       echo getqflist({'nr' : 0}).nr
+<
 =============================================================================
 4. Using :make                                         *:make_makeprg*
 
index 0e488f130c9380650ae4a26097a98c36834c6c67..fbf8a9490ef04693656d423643a4c3a402c003b4 100644 (file)
@@ -4949,9 +4949,12 @@ qf_get_properties(win_T *wp, dict_T *what, dict_T *retdict)
     if ((status == OK) && (flags & QF_GETLIST_WINID))
     {
        win_T   *win;
+       int     win_id = 0;
+
        win = qf_find_win(qi);
        if (win != NULL)
-           status = dict_add_nr_str(retdict, "winid", win->w_id, NULL);
+           win_id = win->w_id;
+       status = dict_add_nr_str(retdict, "winid", win_id, NULL);
     }
     if ((status == OK) && (flags & QF_GETLIST_ITEMS))
     {
index 84db18ca07575d3458438cf75181c945d1aaba2a..61633cef88550c1a52b2ee740d7d2f14a692bb12 100644 (file)
@@ -28,7 +28,7 @@ func s:setup_commands(cchar)
     command! -count -nargs=* -bang Xprev <mods><count>cprev<bang> <args>
     command! -nargs=* -bang Xfirst <mods>cfirst<bang> <args>
     command! -nargs=* -bang Xlast <mods>clast<bang> <args>
-    command! -nargs=* -bang Xnfile <mods>cnfile<bang> <args>
+    command! -nargs=* -bang -range Xnfile <mods><count>cnfile<bang> <args>
     command! -nargs=* -bang Xpfile <mods>cpfile<bang> <args>
     command! -nargs=* Xexpr <mods>cexpr <args>
     command! -range -nargs=* Xvimgrep <mods><count>vimgrep <args>
@@ -36,6 +36,7 @@ func s:setup_commands(cchar)
     command! -nargs=* Xgrep <mods> grep <args>
     command! -nargs=* Xgrepadd <mods> grepadd <args>
     command! -nargs=* Xhelpgrep helpgrep <args>
+    command! -nargs=0 -count Xcc <count>cc
     let g:Xgetlist = function('getqflist')
     let g:Xsetlist = function('setqflist')
     call setqflist([], 'f')
@@ -60,7 +61,7 @@ func s:setup_commands(cchar)
     command! -count -nargs=* -bang Xprev <mods><count>lprev<bang> <args>
     command! -nargs=* -bang Xfirst <mods>lfirst<bang> <args>
     command! -nargs=* -bang Xlast <mods>llast<bang> <args>
-    command! -nargs=* -bang Xnfile <mods>lnfile<bang> <args>
+    command! -nargs=* -bang -range Xnfile <mods><count>lnfile<bang> <args>
     command! -nargs=* -bang Xpfile <mods>lpfile<bang> <args>
     command! -nargs=* Xexpr <mods>lexpr <args>
     command! -range -nargs=* Xvimgrep <mods><count>lvimgrep <args>
@@ -68,6 +69,7 @@ func s:setup_commands(cchar)
     command! -nargs=* Xgrep <mods> lgrep <args>
     command! -nargs=* Xgrepadd <mods> lgrepadd <args>
     command! -nargs=* Xhelpgrep lhelpgrep <args>
+    command! -nargs=0 -count Xcc <count>ll
     let g:Xgetlist = function('getloclist', [0])
     let g:Xsetlist = function('setloclist', [0])
     call setloclist(0, [], 'f')
@@ -382,12 +384,18 @@ endfunc
 func Xtest_browse(cchar)
   call s:setup_commands(a:cchar)
 
+  call g:Xsetlist([], 'f')
   " Jumping to first or next location list entry without any error should
   " result in failure
-  if a:cchar == 'l'
-      call assert_fails('lfirst', 'E776:')
-      call assert_fails('lnext', 'E776:')
+  if a:cchar == 'c'
+    let err = 'E42:'
+  else
+    let err = 'E776:'
   endif
+  call assert_fails('Xnext', err)
+  call assert_fails('Xprev', err)
+  call assert_fails('Xnfile', err)
+  call assert_fails('Xpfile', err)
 
   call s:create_test_file('Xqftestfile1')
   call s:create_test_file('Xqftestfile2')
@@ -408,6 +416,12 @@ func Xtest_browse(cchar)
   Xpfile
   call assert_equal('Xqftestfile1', bufname('%'))
   call assert_equal(6, line('.'))
+  5Xcc
+  call assert_equal(5, g:Xgetlist({'idx':0}).idx)
+  2Xcc
+  call assert_equal(2, g:Xgetlist({'idx':0}).idx)
+  10Xcc
+  call assert_equal(6, g:Xgetlist({'idx':0}).idx)
   Xlast
   Xprev
   call assert_equal('Xqftestfile2', bufname('%'))
@@ -425,6 +439,23 @@ func Xtest_browse(cchar)
   call assert_equal('Xqftestfile1', bufname('%'))
   call assert_equal(5, line('.'))
 
+  " Jumping to an error from the error window using cc command
+  Xgetexpr ['Xqftestfile1:5:Line5',
+               \ 'Xqftestfile1:6:Line6',
+               \ 'Xqftestfile2:10:Line10',
+               \ 'Xqftestfile2:11:Line11']
+  Xopen
+  10Xcc
+  call assert_equal(11, line('.'))
+  call assert_equal('Xqftestfile2', bufname('%'))
+
+  " Jumping to an error from the error window (when only the error window is
+  " present)
+  Xopen | only
+  Xlast 1
+  call assert_equal(5, line('.'))
+  call assert_equal('Xqftestfile1', bufname('%'))
+
   Xexpr ""
   call assert_fails('Xnext', 'E42:')
 
@@ -1497,13 +1528,18 @@ func Test_switchbuf()
   set switchbuf=usetab
   tabedit Xqftestfile1
   tabedit Xqftestfile2
+  tabedit Xqftestfile3
   tabfirst
   cfirst | cnext
   call assert_equal(2, tabpagenr())
   2cnext
   call assert_equal(3, tabpagenr())
-  2cnext
-  call assert_equal(3, tabpagenr())
+  6cnext
+  call assert_equal(4, tabpagenr())
+  2cpfile
+  call assert_equal(2, tabpagenr())
+  2cnfile
+  call assert_equal(4, tabpagenr())
   tabfirst | tabonly | enew
 
   set switchbuf=split
@@ -2320,7 +2356,7 @@ func XfreeTests(cchar)
   Xclose
 endfunc
 
-" Tests for the quickifx free functionality
+" Tests for the quickfix free functionality
 func Test_qf_free()
   call XfreeTests('c')
   call XfreeTests('l')
@@ -2747,3 +2783,100 @@ func Test_qf_id()
   call Xqfid_tests('c')
   call Xqfid_tests('l')
 endfunc
+
+func Xqfjump_tests(cchar)
+  call s:setup_commands(a:cchar)
+
+  call writefile(["Line1\tFoo", "Line2"], 'F1')
+  call writefile(["Line1\tBar", "Line2"], 'F2')
+  call writefile(["Line1\tBaz", "Line2"], 'F3')
+
+  call g:Xsetlist([], 'f')
+
+  " Tests for
+  "   Jumping to a line using a pattern
+  "   Jumping to a column greater than the last column in a line
+  "   Jumping to a line greater than the last line in the file
+  let l = []
+  for i in range(1, 7)
+    call add(l, {})
+  endfor
+  let l[0].filename='F1'
+  let l[0].pattern='Line1'
+  let l[1].filename='F2'
+  let l[1].pattern='Line1'
+  let l[2].filename='F3'
+  let l[2].pattern='Line1'
+  let l[3].filename='F3'
+  let l[3].lnum=1
+  let l[3].col=9
+  let l[3].vcol=1
+  let l[4].filename='F3'
+  let l[4].lnum=99
+  let l[5].filename='F3'
+  let l[5].lnum=1
+  let l[5].col=99
+  let l[5].vcol=1
+  let l[6].filename='F3'
+  let l[6].pattern='abcxyz'
+
+  call g:Xsetlist([], ' ', {'items' : l})
+  Xopen | only
+  2Xnext
+  call assert_equal(3, g:Xgetlist({'idx' : 0}).idx)
+  call assert_equal('F3', bufname('%'))
+  Xnext
+  call assert_equal(7, col('.'))
+  Xnext
+  call assert_equal(2, line('.'))
+  Xnext
+  call assert_equal(9, col('.'))
+  2
+  Xnext
+  call assert_equal(2, line('.'))
+
+  if a:cchar == 'l'
+    " When jumping to a location list entry in the location list window and
+    " no usable windows are available, then a new window should be opened.
+    enew! | new | only
+    call g:Xsetlist([], 'f')
+    setlocal buftype=nofile
+    new
+    call g:Xsetlist([], ' ', {'lines' : ['F1:1:1:Line1', 'F1:2:2:Line2', 'F2:1:1:Line1', 'F2:2:2:Line2', 'F3:1:1:Line1', 'F3:2:2:Line2']})
+    Xopen
+    let winid = win_getid()
+    wincmd p
+    close
+    call win_gotoid(winid)
+    Xnext
+    call assert_equal(3, winnr('$'))
+    call assert_equal(1, winnr())
+    call assert_equal(2, line('.'))
+
+    " When jumping to an entry in the location list window and the window
+    " associated with the location list is not present and a window containing
+    " the file is already present, then that window should be used.
+    close
+    belowright new
+    call g:Xsetlist([], 'f')
+    edit F3
+    call win_gotoid(winid)
+    Xlast
+    call assert_equal(3, winnr())
+    call assert_equal(6, g:Xgetlist({'size' : 1}).size)
+    call assert_equal(winid, g:Xgetlist({'winid' : 1}).winid)
+  endif
+
+  " Cleanup
+  enew!
+  new | only
+
+  call delete('F1')
+  call delete('F2')
+  call delete('F3')
+endfunc
+
+func Test_qfjump()
+  call Xqfjump_tests('c')
+  call Xqfjump_tests('l')
+endfunc
index 05b1a4033460528b286b23f705e375d1c17d6c0b..de535e0eeeed86999bb05ffceafc1b862a19b1fa 100644 (file)
@@ -771,6 +771,8 @@ static char *(features[]) =
 
 static int included_patches[] =
 {   /* Add new patch number below this line */
+/**/
+    1384,
 /**/
     1383,
 /**/