mirror of
https://github.com/neovim/neovim.git
synced 2025-10-15 22:36:09 +00:00
vim-patch:8.2.2606: strchars() defaults to counting composing characters
Problem: strchars() defaults to counting composing characters.
Solution: Add strcharlen() which ignores composing characters.
70ce8a1561
Use docs from latest Vim instead.
Co-authored-by: Bram Moolenaar <Bram@vim.org>
This commit is contained in:
@@ -376,6 +376,7 @@ return {
|
||||
str2float={args=1, base=1},
|
||||
str2list={args={1, 2}, base=1},
|
||||
str2nr={args={1, 3}, base=1},
|
||||
strcharlen={args=1, base=1},
|
||||
strcharpart={args={2, 3}, base=1},
|
||||
strchars={args={1, 2}, base=1},
|
||||
strdisplaywidth={args={1, 2}, base=1},
|
||||
|
@@ -8447,13 +8447,30 @@ static void f_strlen(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
|
||||
rettv->vval.v_number = (varnumber_T)strlen(tv_get_string(&argvars[0]));
|
||||
}
|
||||
|
||||
static void strchar_common(typval_T *argvars, typval_T *rettv, bool skipcc)
|
||||
{
|
||||
const char *s = tv_get_string(&argvars[0]);
|
||||
varnumber_T len = 0;
|
||||
int (*func_mb_ptr2char_adv)(const char_u **pp);
|
||||
|
||||
func_mb_ptr2char_adv = skipcc ? mb_ptr2char_adv : mb_cptr2char_adv;
|
||||
while (*s != NUL) {
|
||||
func_mb_ptr2char_adv((const char_u **)&s);
|
||||
len++;
|
||||
}
|
||||
rettv->vval.v_number = len;
|
||||
}
|
||||
|
||||
/// "strcharlen()" function
|
||||
static void f_strcharlen(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
|
||||
{
|
||||
strchar_common(argvars, rettv, true);
|
||||
}
|
||||
|
||||
/// "strchars()" function
|
||||
static void f_strchars(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
|
||||
{
|
||||
const char *s = tv_get_string(&argvars[0]);
|
||||
int skipcc = false;
|
||||
varnumber_T len = 0;
|
||||
int (*func_mb_ptr2char_adv)(const char_u **pp);
|
||||
|
||||
if (argvars[1].v_type != VAR_UNKNOWN) {
|
||||
skipcc = (int)tv_get_bool(&argvars[1]);
|
||||
@@ -8461,12 +8478,7 @@ static void f_strchars(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
|
||||
if (skipcc < 0 || skipcc > 1) {
|
||||
semsg(_(e_using_number_as_bool_nr), skipcc);
|
||||
} else {
|
||||
func_mb_ptr2char_adv = skipcc ? mb_ptr2char_adv : mb_cptr2char_adv;
|
||||
while (*s != NUL) {
|
||||
func_mb_ptr2char_adv((const char_u **)&s);
|
||||
len++;
|
||||
}
|
||||
rettv->vval.v_number = len;
|
||||
strchar_common(argvars, rettv, skipcc);
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -12,7 +12,7 @@ func Test_visual_block_insert()
|
||||
bwipeout!
|
||||
endfunc
|
||||
|
||||
" Test for built-in function strchars()
|
||||
" Test for built-in functions strchars() and strcharlen()
|
||||
func Test_strchars()
|
||||
let inp = ["a", "あいa", "A\u20dd", "A\u20dd\u20dd", "\u20dd"]
|
||||
let exp = [[1, 1, 1], [3, 3, 3], [2, 2, 1], [3, 3, 1], [1, 1, 1]]
|
||||
@@ -21,6 +21,13 @@ func Test_strchars()
|
||||
call assert_equal(exp[i][1], inp[i]->strchars(0))
|
||||
call assert_equal(exp[i][2], strchars(inp[i], 1))
|
||||
endfor
|
||||
|
||||
let exp = [1, 3, 1, 1, 1]
|
||||
for i in range(len(inp))
|
||||
call assert_equal(exp[i], inp[i]->strcharlen())
|
||||
call assert_equal(exp[i], strcharlen(inp[i]))
|
||||
endfor
|
||||
|
||||
call assert_fails("let v=strchars('abc', [])", 'E745:')
|
||||
call assert_fails("let v=strchars('abc', 2)", 'E1023:')
|
||||
endfunc
|
||||
|
Reference in New Issue
Block a user