Basically we distinguish two kinds of scopes.
meta. scopes are used to create logical units which provide semantical context for completions or plugins.
punctuation … scopes which primarily target syntax highlighting.
About snippet 1 (Python)
The whole import statement is scoped
from .foo import bar
from .foo import (bar as baz)
The second scope
meta.import-list is used to scope only
(bar as baz).
Stacking meta scopes like that is one way to create multiple layers of logical units. This is useful especially if such scopes like
meta.import-lists are used in different contexts.
If only the import list is of interest a selector may look like
meta.import-list, which targets all those regions no matter whether they belong to
meta.statement.import or any other one.
If only certain regions are needed a selector can easily combine those by
(meta.statement.import | meta.statement.whatever) & meta.import-list.
An alternative was to put everything into one scope name, which would then look like
meta.statement.import.import-list. A real life example is
This solution makes general purpose selectors to match all import lists hard. You always need to address
meta.statment.import.import-list, meta.statement.whatever.import-list, ...
Hence it should be used with care and only if the statements structure is very clear.
About snippet 2 (C++)
That’s an older versions of function calls. The
meta.group is a very general scope used to denote all kinds of parenthesed code sections. A selector targeting
meta.function-call meta.group - meta.function-call meta.block could be used to match function call arguments.
More recent syntaxes use
meta.function-call.arguments only or in conjunction with
This makes selectors a bit more straight forward:
meta.function-call.arguments is enough to target function call arguments, while
meta.group if present could be used for general purpose functions if someone wants to match all kinds of parenthesed sections no matter if they are function arguments, or expression groups.
punctuation is the highlighting part, which may be addressed by color schemes to give the parentheses their color. It is part of the scope naming guidelines that the related meta scope of a section should span the opening and closing punctuation. Hence those are stacked.
About snippet 3 Pthon lambda
Here two highlighting scopes
keyword.declaration are stacked because of some kind of backward compatibility considerations with older color schemes.
While the return value of a function in C/C++ like
char may clearly be scoped
storage.type situation is more confuse in dynamically typed syntaxes like python, which just use general keywords like
def to denote function definitions. Those keywords were scoped
storage.type.function in the past.
Same applies to
class keyword. But … in a statement like
class ClassName, what is the type? Is it
ClassName? We came up with
class to be a
keyword.declaration which declares a data type. Same applies to python functions/lambdas. Those keywords are more like declaration keywords than data types. Hence those were changed.
It turned out stacking those is not as backward compatible as desired. The internal ST4 beta comes with a core feature to maintain backward compatibility with older color schemes even if we remove the legacy
storage.type in such constructs. One thing still on the TODO.
Hope, that helps a bit.