import { fn } from "https://deno.land/x/ddu_vim@v4.0.0/deps.ts";
const { searchcount } = fn;
Get or update the last search count, like what is displayed without the "S" flag in 'shortmess'. This works even if 'shortmess' does contain the "S" flag.
This returns a Dictionary
. The dictionary is empty if the
previous pattern was not set and "pattern" was not specified.
key type meaning
current Number
current position of match;
0 if the cursor position is
before the first match
exact_match Boolean
1 if "current" is matched on
"pos", otherwise 0
total Number
total count of matches found
incomplete Number
0: search was fully completed
1: recomputing was timed out
2: max count exceeded
For {options} see further down.
To get the last search count when n
or N
was pressed, call
this function with recompute: 0
. This sometimes returns
wrong information because n
and N
's maximum count is 99.
If it exceeded 99 the result must be max count + 1 (100). If
you want to get correct information, specify recompute: 1
:
" result == maxcount + 1 (100) when many matches
let result = searchcount(#{recompute: 0})
" Below returns correct result (recompute defaults
" to 1)
let result = searchcount()
The function is useful to add the count to 'statusline':
function! LastSearchCount() abort
let result = searchcount(#{recompute: 0})
if empty(result)
return ''
endif
if result.incomplete ==# 1 " timed out
return printf(' /%s [?/??]', @/)
elseif result.incomplete ==# 2 " max count exceeded
if result.total > result.maxcount &&
\ result.current > result.maxcount
return printf(' /%s [>%d/>%d]', @/,
\ result.current, result.total)
elseif result.total > result.maxcount
return printf(' /%s [%d/>%d]', @/,
\ result.current, result.total)
endif
endif
return printf(' /%s [%d/%d]', @/,
\ result.current, result.total)
endfunction
let &statusline ..= '%{LastSearchCount()}'
" Or if you want to show the count only when
" 'hlsearch' was on
" let &statusline ..=
" \ '%{v:hlsearch ? LastSearchCount() : ""}'
You can also update the search count, which can be useful in a
CursorMoved
or CursorMovedI
autocommand:
autocmd CursorMoved,CursorMovedI *
\ let s:searchcount_timer = timer_start(
\ 200, function('s:update_searchcount'))
function! s:update_searchcount(timer) abort
if a:timer ==# s:searchcount_timer
call searchcount(#{
\ recompute: 1, maxcount: 0, timeout: 100})
redrawstatus
endif
endfunction
This can also be used to count matched texts with specified pattern in the current buffer using "pattern":
" Count '\<foo\>' in this buffer
" (Note that it also updates search count)
let result = searchcount(#{pattern: '\<foo\>'})
" To restore old search count by old pattern,
" search again
call searchcount()
{options} must be a Dictionary
. It can contain:
key type meaning
recompute Boolean
if TRUE
, recompute the count
like n
or N
was executed.
otherwise returns the last
computed result (when n
or
N
was used when "S" is not
in 'shortmess', or this
function was called).
(default: TRUE
)
pattern String
recompute if this was given
and different with @/
.
this works as same as the
below command is executed
before calling this function
let @/ = pattern
(default: `@/`)
timeout Number
0 or negative number is no
timeout. timeout milliseconds
for recomputing the result
(default: 0)
maxcount Number
0 or negative number is no
limit. max count of matched
text while recomputing the
result. if search exceeded
total count, "total" value
becomes maxcount + 1
(default: 99)
pos List
[lnum, col, off]
value
when recomputing the result.
this changes "current" result
value. see cursor()
,
getpos()
(default: cursor's position)
Can also be used as a method
:
GetSearchOpts()->searchcount()