mirror of
https://github.com/vim/vim
synced 2025-07-16 09:12:00 +00:00
patch 9.1.0418: Cannot move to previous/next rare word
Problem: Cannot move to previous/next rare word (Colin Kennedy) Solution: Add the ]r and [r motions (Christ van Willegen) fixes: #14773 closes: #14780 Signed-off-by: Christ van Willegen - van Noort <github.com@vanwillegen-vannoort.nl> Signed-off-by: Christian Brabandt <cb@256bit.org>
This commit is contained in:
committed by
Christian Brabandt
parent
cf78d0df51
commit
8e4c4c7d87
@ -1,4 +1,4 @@
|
||||
*spell.txt* For Vim version 9.1. Last change: 2024 May 11
|
||||
*spell.txt* For Vim version 9.1. Last change: 2024 May 17
|
||||
|
||||
|
||||
VIM REFERENCE MANUAL by Bram Moolenaar
|
||||
@ -62,6 +62,17 @@ To search for the next misspelled word:
|
||||
*[S*
|
||||
[S Like "]S" but search backwards.
|
||||
|
||||
*]r*
|
||||
]r Move to next "rare" word after the cursor.
|
||||
A count before the command can be used to repeat.
|
||||
'wrapscan' applies.
|
||||
|
||||
*[r*
|
||||
[r Like "]r" but search backwards, find the "rare"
|
||||
word before the cursor. Doesn't recognize words
|
||||
split over two lines, thus may stop at words that are
|
||||
not highlighted as rare.
|
||||
|
||||
|
||||
To add words to your own word list:
|
||||
|
||||
|
@ -5876,6 +5876,7 @@ ZZ editing.txt /*ZZ*
|
||||
[p change.txt /*[p*
|
||||
[pattern] pattern.txt /*[pattern]*
|
||||
[quotex] intro.txt /*[quotex]*
|
||||
[r spell.txt /*[r*
|
||||
[range] cmdline.txt /*[range]*
|
||||
[s spell.txt /*[s*
|
||||
[star motion.txt /*[star*
|
||||
@ -5904,6 +5905,7 @@ ZZ editing.txt /*ZZ*
|
||||
]i tagsrch.txt /*]i*
|
||||
]m motion.txt /*]m*
|
||||
]p change.txt /*]p*
|
||||
]r spell.txt /*]r*
|
||||
]s spell.txt /*]s*
|
||||
]star motion.txt /*]star*
|
||||
]z fold.txt /*]z*
|
||||
|
@ -1,4 +1,4 @@
|
||||
*version9.txt* For Vim version 9.1. Last change: 2024 May 05
|
||||
*version9.txt* For Vim version 9.1. Last change: 2024 May 17
|
||||
|
||||
|
||||
VIM REFERENCE MANUAL by Bram Moolenaar
|
||||
@ -41587,15 +41587,17 @@ Autocommands: ~
|
||||
|
||||
Highlighting: ~
|
||||
|
||||
|hl-MsgArea| highlighting of the Command-line and messages area.
|
||||
|hl-MsgArea| highlighting of the Command-line and messages area
|
||||
|
||||
Commands: ~
|
||||
|
||||
|[r| and |]r| to move the cursor to previous/next rare word
|
||||
|
||||
|
||||
Options: ~
|
||||
|
||||
'winfixbuf' Keep buffer focused in a window
|
||||
't_xo' Terminal uses XON/XOFF handshaking (e.g. vt420).
|
||||
't_xo' Terminal uses XON/XOFF handshaking (e.g. vt420)
|
||||
|
||||
==============================================================================
|
||||
INCOMPATIBLE CHANGES *incompatible-9.2*
|
||||
|
@ -1801,7 +1801,7 @@ win_line(
|
||||
pos = wp->w_cursor;
|
||||
wp->w_cursor.lnum = lnum;
|
||||
wp->w_cursor.col = linecol;
|
||||
len = spell_move_to(wp, FORWARD, TRUE, TRUE, &spell_hlf);
|
||||
len = spell_move_to(wp, FORWARD, SMT_ALL, TRUE, &spell_hlf);
|
||||
|
||||
// spell_move_to() may call ml_get() and make "line" invalid
|
||||
line = ml_get_buf(wp->w_buffer, lnum, FALSE);
|
||||
|
@ -10959,7 +10959,7 @@ f_spellbadword(typval_T *argvars UNUSED, typval_T *rettv)
|
||||
if (argvars[0].v_type == VAR_UNKNOWN)
|
||||
{
|
||||
// Find the start and length of the badly spelled word.
|
||||
len = spell_move_to(curwin, FORWARD, TRUE, TRUE, &attr);
|
||||
len = spell_move_to(curwin, FORWARD, SMT_ALL, TRUE, &attr);
|
||||
if (len != 0)
|
||||
{
|
||||
word = ml_get_cursor();
|
||||
|
@ -5195,7 +5195,7 @@ spell_back_to_badword(void)
|
||||
{
|
||||
pos_T tpos = curwin->w_cursor;
|
||||
|
||||
spell_bad_len = spell_move_to(curwin, BACKWARD, TRUE, TRUE, NULL);
|
||||
spell_bad_len = spell_move_to(curwin, BACKWARD, SMT_ALL, TRUE, NULL);
|
||||
if (curwin->w_cursor.col != tpos.col)
|
||||
start_arrow(&tpos);
|
||||
}
|
||||
|
10
src/normal.c
10
src/normal.c
@ -2593,7 +2593,7 @@ nv_zg_zw(cmdarg_T *cap, int nchar)
|
||||
// off this fails and find_ident_under_cursor() is
|
||||
// used below.
|
||||
emsg_off++;
|
||||
len = spell_move_to(curwin, FORWARD, TRUE, TRUE, NULL);
|
||||
len = spell_move_to(curwin, FORWARD, SMT_ALL, TRUE, NULL);
|
||||
emsg_off--;
|
||||
if (len != 0 && curwin->w_cursor.col <= pos.col)
|
||||
ptr = ml_get_pos(&curwin->w_cursor);
|
||||
@ -4529,13 +4529,15 @@ nv_brackets(cmdarg_T *cap)
|
||||
#endif
|
||||
|
||||
#ifdef FEAT_SPELL
|
||||
// "[s", "[S", "]s" and "]S": move to next spell error.
|
||||
else if (cap->nchar == 's' || cap->nchar == 'S')
|
||||
// "[r", "[s", "[S", "]r", "]s" and "]S": move to next spell error.
|
||||
else if (cap->nchar == 'r' || cap->nchar == 's' || cap->nchar == 'S')
|
||||
{
|
||||
setpcmark();
|
||||
for (n = 0; n < cap->count1; ++n)
|
||||
if (spell_move_to(curwin, cap->cmdchar == ']' ? FORWARD : BACKWARD,
|
||||
cap->nchar == 's' ? TRUE : FALSE, FALSE, NULL) == 0)
|
||||
cap->nchar == 's' ? SMT_ALL :
|
||||
cap->nchar == 'r' ? SMT_RARE :
|
||||
SMT_BAD, FALSE, NULL) == 0)
|
||||
{
|
||||
clearopbeep(cap->oap);
|
||||
break;
|
||||
|
@ -6,7 +6,7 @@ int match_compoundrule(slang_T *slang, char_u *compflags);
|
||||
int valid_word_prefix(int totprefcnt, int arridx, int flags, char_u *word, slang_T *slang, int cond_req);
|
||||
int spell_valid_case(int wordflags, int treeflags);
|
||||
int spell_check_window(win_T *wp);
|
||||
int spell_move_to(win_T *wp, int dir, int allwords, int curline, hlf_T *attrp);
|
||||
int spell_move_to(win_T *wp, int dir, smt_T behaviour, int curline, hlf_T *attrp);
|
||||
void spell_cat_line(char_u *buf, char_u *line, int maxlen);
|
||||
char_u *spell_enc(void);
|
||||
slang_T *slang_alloc(char_u *lang);
|
||||
|
@ -1336,7 +1336,7 @@ no_spell_checking(win_T *wp)
|
||||
spell_move_to(
|
||||
win_T *wp,
|
||||
int dir, // FORWARD or BACKWARD
|
||||
int allwords, // TRUE for "[s"/"]s", FALSE for "[S"/"]S"
|
||||
smt_T behaviour, // Behaviour of the function
|
||||
int curline,
|
||||
hlf_T *attrp) // return: attributes of bad word or NULL
|
||||
// (only when "dir" is FORWARD)
|
||||
@ -1441,7 +1441,9 @@ spell_move_to(
|
||||
if (attr != HLF_COUNT)
|
||||
{
|
||||
// We found a bad word. Check the attribute.
|
||||
if (allwords || attr == HLF_SPB)
|
||||
if (behaviour == SMT_ALL
|
||||
|| (behaviour == SMT_BAD && attr == HLF_SPB)
|
||||
|| (behaviour == SMT_RARE && attr == HLF_SPR))
|
||||
{
|
||||
// When searching forward only accept a bad word after
|
||||
// the cursor.
|
||||
|
@ -512,7 +512,7 @@ spell_suggest(int count)
|
||||
badlen = ml_get_curline_len() - (int)curwin->w_cursor.col;
|
||||
}
|
||||
// Find the start of the badly spelled word.
|
||||
else if (spell_move_to(curwin, FORWARD, TRUE, TRUE, NULL) == 0
|
||||
else if (spell_move_to(curwin, FORWARD, SMT_ALL, TRUE, NULL) == 0
|
||||
|| curwin->w_cursor.col > prev_cursor.col)
|
||||
{
|
||||
// No bad word or it starts after the cursor: use the word under the
|
||||
|
@ -278,6 +278,7 @@ NEW_TESTS = \
|
||||
test_spell \
|
||||
test_spell_utf8 \
|
||||
test_spellfile \
|
||||
test_spellrare \
|
||||
test_startup \
|
||||
test_startup_utf8 \
|
||||
test_stat \
|
||||
@ -521,6 +522,7 @@ NEW_TESTS_RES = \
|
||||
test_spell.res \
|
||||
test_spell_utf8.res \
|
||||
test_spellfile.res \
|
||||
test_spellrare.res \
|
||||
test_startup.res \
|
||||
test_stat.res \
|
||||
test_statusline.res \
|
||||
|
61
src/testdir/test_spellrare.vim
Normal file
61
src/testdir/test_spellrare.vim
Normal file
@ -0,0 +1,61 @@
|
||||
" Test spell checking
|
||||
|
||||
source check.vim
|
||||
CheckFeature spell
|
||||
|
||||
" Test spellbadword() with argument, specifically to move to "rare" words
|
||||
" in normal mode.
|
||||
func Test_spellrareword()
|
||||
set spell
|
||||
|
||||
" Create a small word list to test that spellbadword('...')
|
||||
" can return ['...', 'rare'].
|
||||
let lines =<< trim END
|
||||
foo
|
||||
foobar/?
|
||||
foobara/?
|
||||
END
|
||||
call writefile(lines, 'Xwords', 'D')
|
||||
|
||||
mkspell! Xwords.spl Xwords
|
||||
set spelllang=Xwords.spl
|
||||
call assert_equal(['foobar', 'rare'], spellbadword('foo foobar'))
|
||||
|
||||
new
|
||||
call setline(1, ['foo', '', 'foo bar foo bar foobara foo foo foo foobar', '', 'End'])
|
||||
set spell wrapscan
|
||||
normal ]s
|
||||
call assert_equal('foo', expand('<cword>'))
|
||||
normal ]s
|
||||
call assert_equal('bar', expand('<cword>'))
|
||||
|
||||
normal ]r
|
||||
call assert_equal('foobara', expand('<cword>'))
|
||||
normal ]r
|
||||
call assert_equal('foobar', expand('<cword>'))
|
||||
normal ]r
|
||||
call assert_equal('foobara', expand('<cword>'))
|
||||
normal 2]r
|
||||
call assert_equal('foobara', expand('<cword>'))
|
||||
|
||||
normal [r
|
||||
call assert_equal('foobar', expand('<cword>'))
|
||||
normal [r
|
||||
call assert_equal('foobara', expand('<cword>'))
|
||||
normal [r
|
||||
call assert_equal('foobar', expand('<cword>'))
|
||||
normal 2[r
|
||||
call assert_equal('foobar', expand('<cword>'))
|
||||
|
||||
bwipe!
|
||||
set nospell
|
||||
|
||||
call delete('Xwords.spl')
|
||||
set spelllang&
|
||||
set spell&
|
||||
|
||||
" set 'encoding' to clear the word list
|
||||
set encoding=utf-8
|
||||
endfunc
|
||||
|
||||
" vim: shiftwidth=2 sts=2 expandtab
|
@ -704,6 +704,8 @@ static char *(features[]) =
|
||||
|
||||
static int included_patches[] =
|
||||
{ /* Add new patch number below this line */
|
||||
/**/
|
||||
418,
|
||||
/**/
|
||||
417,
|
||||
/**/
|
||||
|
@ -1529,6 +1529,15 @@ typedef enum
|
||||
'*', '#', '_', '!', '.', 'o', 'q', \
|
||||
'z', 'Z', 'g'}
|
||||
|
||||
/*
|
||||
* Values for behaviour in spell_move_to
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
SMT_ALL = 0 // Move to "all" words
|
||||
, SMT_BAD // Move to "bad" words only
|
||||
, SMT_RARE // Move to "rare" words only
|
||||
} smt_T;
|
||||
/*
|
||||
* Boolean constants
|
||||
*/
|
||||
|
Reference in New Issue
Block a user