Mise en surbrillance de Vim Markdown (liste d'éléments et conflits de bloc de code)
Question
Je décide d'en apprendre davantage sur vim et sa coloration syntaxique. En utilisant des exemples pour d’autres, je crée mon propre fichier de syntaxe pour Markdown. J'ai vu mkd.vim un problème qui se pose également. Mon problème se situe entre les éléments de la liste et la mise en surbrillance des blocs de code.
Code Bloc définition :
- la première ligne est vide
- la deuxième ligne commence par au moins 4 espaces ou 1 onglet
- le bloc est terminé avec une ligne vide
Exemple:
Regular text
this is code, monospaced and left untouched by markdown
another line of code
Regular Text
Syntaxe My Vim pour le bloc de code:
syn match mkdCodeBlock /\(\s\{4,}\|\t\{1,}\).*\n/ contained nextgroup=mkdCodeBlock
hi link mkdCodeBlock comment
Élément de la liste de désordre définition :
- la première ligne est vide
- la deuxième ligne commence par un [- + *] suivi d'un espace
- la liste est terminée avec une ligne vide puis une ligne normale (non listée)
- entre les éléments de ligne, un nombre quelconque de lignes vides peut être ajouté
- une sous-liste est spécifiée par retrait (4 espaces ou 1 tabulation)
- une ligne de texte normal après un élément de la liste est incluse en tant que suite de cet élément de la liste
Exemple:
Regular text
- item 1
- sub item 1
- sub item 2
- item 2
this is part of item 2
so is this
- item 3, still in the same list
- sub item 1
- sub item 2
Regular text, list ends above
Syntaxe My Vim pour la définition d'élément de liste unorder (je ne souligne que [- + *]
):
syn region mkdListItem start=/\s*[-*+]\s\+/ matchgroup=pdcListText end=".*" contained nextgroup=mkdListItem,mkdListSkipNL contains=@Spell skipnl
syn match mkdListSkipNL /\s*\n/ contained nextgroup=mkdListItem,mkdListSkipNL skipnl
hi link mkdListItem operator
Je ne parviens pas à mettre en surbrillance les deux dernières règles de liste et un bloc de code.
Ceci est un exemple qui rompt ma coloration syntaxique:
Regular text
- Item 1
- Item 2
part of item 2
- these 2 line should be highlighted as a list item
- but they are highlighted as a code block
Je ne sais pas comment faire en sorte que la surbrillance fonctionne comme je le veux aussi
Vous avez oublié d'ajouter un " global " règle de syntaxe utilisée dans les deux règles énumérées ci-dessous. C’est pour s’assurer qu’ils commencent par une ligne blanche.
syn match mkdBlankLine /^\s*\n/ nextgroup=mkdCodeBlock,mkdListItem transparent
Autre remarque: j'aurais dû être plus clair. Dans mon fichier de syntaxe, les règles de liste apparaissent avant les règles de devis de bloc
La solution
Assurez-vous simplement que la définition de mkdListItem se situe après la définition de mkdCodeBlock, comme ceci:
syn match mkdCodeBlock /\(\s\{4,}\|\t\{1,}\).*\n/ contained nextgroup=mkdCodeBlock
hi link mkdCodeBlock comment
syn region mkdListItem start=/\s*[-*+]\s\+/ matchgroup=pdcListText end=".*" contained nextgroup=mkdListItem,mkdListSkipNL contains=@Spell skipnl
syn match mkdListSkipNL /\s*\n/ contained nextgroup=mkdListItem,mkdListSkipNL skipnl
hi link mkdListItem operator
syn match mkdBlankLine /^\s*\n/ nextgroup=mkdCodeBlock,mkdListItem transparent
La documentation de Vim indique dans : help: syn-define
:
"Dans le cas où plusieurs éléments correspondent à la même position, celui qui était défini DERNIÈRE gagne. Ainsi, vous pouvez remplacer les éléments de syntaxe précédemment définis par en utilisant un élément qui correspond au même texte. Mais un mot-clé va toujours avant un match ou région. Et un mot clé avec la casse correspondante va toujours avant un mot-clé avec casse ignorée. "
Autres conseils
hcs42 était correct. Je me souviens avoir lu cette section à présent, mais je l’avais oubliée jusqu’à ce que hcs24 me l’ait rappelé.
Voici ma syntaxe mise à jour (quelques autres modifications) qui fonctionne:
""""""""""""""""""""""""""""""""""""""" " Code Blocks: " Indent with at least 4 space or 1 tab " This rule must appear for mkdListItem, or highlighting gets messed up syn match mkdCodeBlock /\(\s\{4,}\|\t\{1,}\).*\n/ contained nextgroup=mkdCodeBlock """"""""""""""""""""""""""""""""""""""" " Lists: " These first two rules need to be first or the highlighting will be " incorrect " Continue a list on the current line or next line syn match mkdListCont /\s*[^-+*].*/ contained nextgroup=mkdListCont,mkdListItem,mkdListSkipNL contains=@Spell skipnl transparent " Skip empty lines syn match mkdListSkipNL /\s*\n/ contained nextgroup=mkdListItem,mkdListSkipNL " Unorder list syn match mkdListItem /\s*[-*+]\s\+/ contained nextgroup=mkdListSkipNL,mkdListCont skipnl
Tao Zhyn, cela couvre peut-être vos cas d'utilisation mais pas la syntaxe Markdown. Dans Markdown, un élément de la liste pourrait contenir un bloc de code. Vous pouvez consulter ma solution ici
.TL; DR; le problème est que vim ne vous permet pas de dire quelque chose comme: un bloc qui a la même indentation que son conteneur + 4 espaces . La seule solution que j'ai trouvée consiste à générer des règles pour chaque type de bloc pouvant figurer dans une liste d'éléments pour chaque niveau d'indentation (en fait, je supporte un niveau d'indentation de 42 mais c'est un nombre arbitraire)
J'ai donc markdownCodeBlockInListItemAtLevel1 qui doit être contenu dans un markdownListItemAtLevel1 et qui doit comporter au moins 8 espaces de début doit être contenu dans un markdownListItemAtLevel1 et doit comporter au moins 10 espaces de début, ...Je sais que quelques années ont passé, mais peut-être que quelqu'un trouverait cette réponse utile, car toute syntaxe basée sur l'indentation souffre du même problème