2

次の 3 セットのハイライト グループと構文の一致を検討してください。

hi  Foo     ctermfg=black   ctermbg=red     guifg=black     guibg=red
hi  Filler  ctermfg=black   ctermbg=green   guifg=black     guibg=green
hi  Bar     ctermfg=black   ctermbg=blue    guifg=black     guibg=blue
syn match   Foo     "foo"       nextgroup=Filler
syn match   Filler  "\_s*"      nextgroup=Bar       contained
syn match   Bar     "bar"                           contained

hi  Baz     ctermfg=black   ctermbg=cyan    guifg=black     guibg=cyan
hi  Qux     ctermfg=black   ctermbg=yellow  guifg=black     guibg=yellow
syn match   Baz     "baz\_s*"   nextgroup=Qux
syn match   Qux     "qux"                           contained

hi  Abc     ctermfg=black   ctermbg=magenta guifg=black     guibg=magenta
hi  Xyz     ctermfg=black   ctermbg=white   guifg=black     guibg=white
syn match   Abc     "abc"       nextgroup=Xyz       skipwhite   skipnl
syn match   Xyz     "xyz"                           contained

Filler;の後にBarのみ一致します。Foo同様に、Quxの後のみBaz、およびXyzの後のみAbc。次の例では:set list、明確にするために、 とが末尾に空白がない限り一致しない方法Fillerを示しています。BarFooFoo

このBaz Qux例では、 が改行に一致することを検証していますが、が と に分割されている\_s場合、これが機能しないのはなぜですか? からのこの引用は関連しています:BazFooFiller:help syn-skipnl

「skipnl」が存在する場合、次の行で nextgroup と一致する場合があります。これは、現在のアイテムが現在の行の最後で終了する場合にのみ発生します! 「skipnl」が存在しない場合、nextgroup は同じ行の現在の項目の後にのみ見つかります。

Abc Xyz例は、完全に使用する場合と使用しskipwhite skipnlない\_s場合で、どちらの場合にも一致します。これはEOL、「同じ行の現在の項目の後」とは見なされないということですか? 確かに、次の行の一部になることはできませんか? \_sこれは、通常の検索または同じ行\nで文字が一致するという事実と矛盾しているようです。EOL

4

1 に答える 1

2

の直前で一致が終了した場合、も指定されていない限り\nnextgroup引数は無視されます。skipnlnextgroup\n

与えられた例では、最初のFoo一致は直前に終了\nし、Fooを指定していないためskipnl、Vim は との一致を試みませんFiller。他の空白の導入によりFiller、2 番目の一致の後に一致することが可能にFooなり、Fillerが含まれているため\n、を指定Barせずに一致することもできます。Fillerskipnl

関連するコードは次のsrc/syntax.cとおりです。

/* nextgroup ends at end of line, unless "skipnl" or "skipempty" present */
if (current_next_list != NULL
        && syn_getcurline()[current_col + 1] == NUL
        && !(current_next_flags & (HL_SKIPNL | HL_SKIPEMPTY)))
    current_next_list = NULL;

/* handle next_list, unless at end of line and no "skipnl" or
 * "skipempty" */
current_next_list = cur_si->si_next_list;
current_next_flags = cur_si->si_flags;
if (!(current_next_flags & (HL_SKIPNL | HL_SKIPEMPTY))
        && syn_getcurline()[current_col] == NUL)
    current_next_list = NULL;
于 2013-08-09T14:01:54.867 に答える