【问题标题】:Cloning a sublime text 3 highlighting syntax definition克隆一个 sublime text 3 高亮语法定义
【发布时间】:2014-08-07 14:03:35
【问题描述】:

是否有一个简单的过程可以从现有的导出您自己的自定义 sublime text 3 突出显示定义?

我已经安装了AAAPackageDev,按照有序且略显乏味的tutorial for creating a new highlighting syntax definition 的建议,但我发现克隆一个会让我走得更快。至少,我想了解如何浏览 sublime 附带的默认语法定义。

如果您真的想要完全具体,我希望完成的只是一个原始的突出显示方案,其中我自己定义的一对给定的开始和结束标记之间的任何字符串都会被着色。我自己定义的另一对不同标记之间的任何字符串都会用第二种颜色着色。最好让令牌本身也变灰。

(Ubuntu 14.04)

谢谢!

【问题讨论】:

    标签: sublimetext sublimetext3


    【解决方案1】:

    2015-05-10 更新:Sublime Text 3 build 3084 引入了一种全新的sublime-syntax 格式来编写语法定义。它比 Sublime 从 TextMate 继承的旧系统要好得多。新系统应该很快就会登陆公共 ST3 beta 版本。由于 ST3 是 recommended version of Sublime,我建议使用 new system 而不是下面描述的系统编写任何新的荧光笔。


    这是 Sublime Text 语法高亮的速成课程。

    设置

    首先,正如@lthreed 所指出的,您可以使用PackageResourceViewer 查看Sublime Text 附带的默认包。那些 .tmLanguage 文件都是 plist 格式,阅读和理解起来非常困难。 PackageDev 可以将 plist 文件转换为可读性更高的 JSON 或 YAML 格式。当您通过查看默认包进行学习时,请务必先将其转换为 YAML。请注意,PackageDev 可能无法完美转换它。没关系。您只是将代码用作参考。

    plist 是 Sublime 可以理解的原生格式,但这并不意味着你应该这样写。我强烈建议使用 YAML 编写荧光笔并将其转换为带有 PackageDev 的 plist。不要用 JSON 写它。 JSON 不支持原始字符串。所有的正则表达式都必须双重转义。这绝对是一场噩梦。只需使用 YAML。

    您可以通过打开命令面板(Mac 上为cmd+shift+p)并选择PackageDev: New YAML Syntax Definition 来开始新的语法定义。当您准备好对其进行测试时,打开命令面板并选择PackageDev: Convert (YAML, JSON, PList) to...,PackageDev 会发现您有一个 YAML 文件并想要转换为 plist。转换会获取你的 .YAML-tmLanguage 文件并输出一个 Sublime 可以理解的 .tmLanguage 文件。将该文件放在 /Packages/User 目录中,Sublime 将加载并应用它(您可能需要重新启动)。

    Sublime 语法高亮的工作原理

    您正在编写的语法定义不会直接为文本着色。它将范围名称应用于文本。然后编写 Monokai 和 Solarized 等主题的人会出现并制作将范围名称与颜色相关联的文件。您可以编写自己的范围名称,但您应该坚持使用the official TextMate scope names。这些范围名称对于您匹配的代码可能根本没有任何意义。没关系。只要尽力而为。如果您必须组成范围名称,请使用 TextMate 范围名称作为起点。例如,您可以组成一个名为 string.quoted.triple.xxx 的范围名称,而不是 string.quoted.double.xxx(其中 xxx 是您匹配的语言的文件扩展名)。

    代码示例

    以下是文件扩展名为 .matt 的合成 matt 语言的语法定义。它只有两条规则:一条用于匹配管道分隔的字符串,另一条用于匹配具有更复杂分隔符的字符串。

    # [PackageDev] target_format: plist, ext: tmLanguage
    ---
    name: Mattlang
    scopeName: source.matt
    fileTypes: [matt]
    
    patterns:
    - include: '#pipe-string'
    - include: '#complex-string'
    
    # Rules defined in the repository can reference each other. You can include
    # one rule inside another.
    repository:
      # This is a rule of the begin-end form. The rule matches a string bounded by
      # pipes, such as |hello there|
      pipe-string:
        # The optional 'name' field lets you apply a single scope to everything,
        # including the begin-end pipes. All the scope names must end with .matt
        name: everything.matt
        # We have to escape the pipe character, because it's a special character in
        # the Oniguruma regex syntax (and most other regex engines).
        begin: \|
        # 'beginCaptures' is required if you want the pipes to be colored differently
        beginCaptures:
          # In regex jargon, the begin pipe is 'captured'. Capture group 0 means the
          # entire match, which in this case is just the pipe.
          '0': {name: entire.begin.match.matt}
        # The optional 'contentName' field lets you apply a scope to all the text
        # between (but not including) the begin-end pipes.
        contentName: stuff.between.the.pipes.matt
        patterns:
        # These rules will only be applied to the text *BETWEEN* the pipes. Sublime
        # will go through the rules from top to bottom and try to match the text, so
        # higher rules have a higher "precedence" and will get matched first.
        # Given the text |hello there|, Sublime will see an 'h' character and move
        # through the rules from top to bottom trying to find a rule that starts
        # with 'h'. The #hell rule will match the 'h' and the rest of the
        # characters. The #hell scope name will be applied to the 'hell' text and 
        # Sublime will resume trying to find the next match at the 'o' character.
        # The 'o' character WILL NOT match #hello. You can think of the matched text
        # as being removed from the stream entirely. The point is: order matters.
        - include: '#hell'
        - include: '#hello'
        - end: \|
        endCaptures:
          '0': {name: entire.end.match.matt}
    
      # This is the other form of rule you can define. It's extremely simple --
      # just a scope name and a regex pattern to match. Note that these rules will
      # only match text on the same line, unlike begin-end rules, which can cover
      # multiple lines.
      hell:
        name: some.other.scope.matt
        match: hell
    
      hello:
        name: some.scope.matt
        match: hello
    
      # This rule matches a string that starts with $!! and ends with !!$,
      # e.g. !!$hello there!!$
      complex-string:
        # I've labeled the capture groups.
        #      |---0---|
        #      |--1-||3|
        begin: (!(!))($)
        #        |2|
        beginCaptures:
          '0': {name: full.match.matt}
          '1': {name: both.exclamation.marks.matt}
          '2': {name: second.exclamation.mark.matt}
          '3': {name: dollar.sign.matt}
        # It's ok to leave out the 'patterns' field. Technically, all you really
        # need is a 'begin' field and an 'end' field.
        end: ((!)!)($)
        endCaptures:
          '0': {name: everything.matt}
          '1': {name: both.exclamation.marks.matt}
          '2': {name: first.exclamation.mark.matt}
          '3': {name: dollar.sign.matt}
    

    【讨论】:

      【解决方案2】:

      如果您安装PackageResourceViewer,您可以打开任何内置的压缩​​资源。执行 PackageResourceViewer: Open Resource,然后选择您喜欢的语言。然后选择扩展名为 .tmLanguage 的文件。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2016-09-18
        • 2018-02-23
        • 1970-01-01
        • 2013-02-19
        • 2013-12-21
        • 1970-01-01
        相关资源
        最近更新 更多