Home > database >  VSCode language extension: can a language be embedded into another through code?
VSCode language extension: can a language be embedded into another through code?

Time:04-04

The extension adds support for Renpy language, a language very similar to Python. In this language, it's possible to embed Python code in different ways.

Single line statement:

define e = Character("Eileen", who_color="#c8ffc8")
default sidebar = False
$ sampleFunction("Eileen", 1.0)

To embed python inside single-line statements, I use the following TextMate Grammar pattern:

        {
          "comment": "Match begin and end of python one line statements",
          "name": "meta.embedded.python.line",
          "begin": "(?<=(\\$|define|default)\\s)",
          "end": "\\R$",
          "patterns": [{ "include": "source.python" }]
        }

In this case, I can know when a statement ends.

Python block:

python:
    def foo():
        return "bar"

These blocks can be nested within other language blocks, for example:

init:
    image movie = Movie()

    python:
        povname = ""
        pov = DynamicCharacter("povname", color=(255, 0, 0, 255))

    $ ectc = Character('Eileen', color=(200, 255, 200, 255))

In the case of the block, since it's delimited by indentation, I can't determine where it ends. If these blocks couldn't be nested, I could capture the end with a regular expression, e.g. ^(?=\S), since it can be nested I can't detect when it ends.

I tried to add the TextMate scope source.python via the SemanticTokenProvider, but it seems that it's not possible to add a textmate scope using the SemanticTokensBuilder. Also tried with TextMate patterns but have not succeeded.

I would like to find a way to make the contents of Python blocks have the source.python TextMate scope, regardless of whether it's nested or not.

CodePudding user response:

If there is always a line after the block that has the same indent as the word python: you could try

{
  "begin": "^(\\s*)(python:)",
  "end": "^\\1(?=\S)",
  "beginCaptures": { "2": { "name": "keyword.other" } },
  "patterns": [{ "include": "source.python" }]
}
  • Related