Dostosowywanie zachowania edytora przy użyciu konfiguracji języka

Niestandardową składnię specyficzną dla języka można zaimplementować w edytorze programu Visual Studio przy użyciu usługi Language Configuration w celu włączenia operacji składni specyficznych dla języka. W porównaniu z używaniem serwera językowego użycie konfiguracji języka może zwiększyć wydajność, ponieważ wszystkie jego operacje są lokalne.

Co to jest konfiguracja języka

Program Visual Studio oferuje inteligentne funkcje edycji dla różnych języków programowania za pośrednictwem rozszerzeń języka. Usługa Language Configuration uzupełnia serwery korzystające z protokołu LSP (Language Server Protocol) i udostępnia dane deklaratywne, które umożliwiają edytorowi programu Visual Studio podejmowanie decyzji dotyczących formatowania, kolorowania i uzupełniania bez opóźnień w podejmowaniu zapytania asynchronicznego na serwerze LSP. Funkcje języka deklaratywnego są definiowane w plikach konfiguracji. Na przykład rozszerzenia HTML, CSS i typescript-basic połączone z programem Visual Studio oferują podzestaw następujących funkcji języka deklaratywnego:

  • wyróżnianie składni
  • Uzupełnianie fragmentu kodu
  • Dopasowywanie nawiasów
  • Autoklosowanie nawiasów kwadratowych
  • Przełączanie komentarza
  • Autoindentation (Autoindentation)

Program Visual Studio zapewnia możliwość definiowania konfiguracji języka dla dowolnego języka programowania. Plik konfiguracji języka steruje podstawowymi funkcjami edycji, takimi jak przełączanie komentarzy i dopasowywanie nawiasów i otaczające.

Korzystanie z konfiguracji języka pomaga w:

  • Synchroniczna praca nad wpisywaniem przez użytkownika
  • Prostota: Krótkie pliki JSON z wyrażeniami regularnymi są łatwiejsze do utrzymania niż złożony algorytm
  • Przenośność: nie wymagaj ani minimalnych zmian między programem Visual Studio Code i programem Visual Studio

Ponadto pliki konfiguracji języka umożliwiają łatwe rozszerzenie programu Visual Studio w celu obsługi niektórych podstawowych funkcji refaktoryzacji za pomocą łatwego do odczytania pliku JSON.

Dodawanie obsługi konfiguracji języka do rozszerzenia programu Visual Studio

Istnieją trzy części dotyczące dodawania obsługi konfiguracji języka do rozszerzenia programu Visual Studio:

  1. Tworzenie projektu VSIX
  2. Tworzenie pliku konfiguracji języka
  3. Dodawanie pliku gramatycznego
  4. Aktualizowanie pliku pkgdef

Możesz zapoznać się z przykładowym roboczym przykładem konfiguracji języka.

Tworzenie projektu VSIX

Aby utworzyć rozszerzenie usługi językowej przy użyciu konfiguracji języka, najpierw upewnij się, że masz zainstalowane obciążenie programistyczne rozszerzenia programu Visual Studio dla wystąpienia programu VS.

Następnie utwórz nowy projekt VSIX, przechodząc do pozycji Plik>nowy projekt, wyszukaj ciąg "vsix" i wyszukaj projekt VSIX:

Screenshot showing how to create a VSIX project.

Tworzenie pliku konfiguracji języka

Podczas tworzenia własnego pliku konfiguracji języka można wybrać aspekty do dołączenia w pliku JSON. Możesz na przykład wybrać obsługę przełączania komentarzy, automatycznego udostępniania nawiasów klamrowych lub dowolnej kombinacji dostępnych funkcji opisanych w tej sekcji.

Aby dodać obsługę rozszerzenia, należy najpierw utworzyć plik konfiguracji języka. Nazwa pliku musi być zgodna ze standardem: użyj łączników, aby oddzielić wyrazy w nazwie pliku i upewnij się, że kończy się language-configuration.jsonna .

Poniższy kod przedstawia przykładowy plik konfiguracji języka.

{
    "comments": {
      "lineComment": "***",
      "blockComment": ["{*", "*}"]
    },
    "brackets": [
      ["@", "@"],
      ["#", "#"],
      ["$", "$"],
      ["(", ")"]
    ],
    "autoClosingPairs": [
      { "open": "{", "close": "}" },
      { "open": "@", "close": "@" },
      { "open": "#", "close": "#" },
      { "open": "$", "close": "$" },
      { "open": "(", "close": ")" },
      { "open": "'", "close": "'", "notIn": ["string", "comment"] },
      { "open": "\"", "close": "\"", "notIn": ["string"] },
    ],
    "autoCloseBefore": ";:.,=}])>` \n\t",
    "surroundingPairs": [
      ["@", "@"],
      ["#", "#"],
      ["$", "$"],
      ["[", "]"],
      ["(", ")"],
      ["'", "'"],
      ["\"", "\""],
      ["`", "`"]
    ],
    "wordPattern": "(-?\\d*\\.\\d\\w*)|([^\\`\\~\\!\\@\\#\\%\\^\\&\\*\\(\\)\\-\\=\\+\\[\\{\\]\\}\\\\\\|\\;\\:\\'\\\"\\,\\.\\<\\>\\/\\?\\s]+)",
    "indentationRules": {
      "increaseIndentPattern": "^((?!\\/\\/).)*(\\{[^}\"'`]*|\\([^)\"'`]*|\\[[^\\]\"'`]*)$",
      "decreaseIndentPattern": "^((?!.*?\\/\\*).*\\*/)?\\s*[\\)\\}\\]].*$"
    }
  }

Ustawienia konfiguracji

W poniższych sekcjach opisano ustawienia dostępne w pliku konfiguracji języka.

Przełączanie komentarza

Pliki konfiguracji języka oferują dwa polecenia umożliwiające przełączanie komentarzy. Przełącz komentarz wiersza i przełącz komentarz blokowy. Możesz określić comments.blockComment i comments.lineComment kontrolować sposób, w jaki program Visual Studio powinien komentować wiersze/bloki.

{
  "comments": {
    "lineComment": "//",
    "blockComment": ["/*", "*/"]
  }
}

To ustawienie wpływa na zachowanie edytora tekstów programu Visual Studio po naciśnięciu klawiszy Ctrl K, Ctrl++C.

Definicja nawiasów kwadratowych

Po przeniesieniu kursora do nawiasu zdefiniowanego w tym miejscu program Visual Studio wyróżni ten nawias wraz z dopasowaną parą.

{
  "brackets": [["{", "}"], ["[", "]"], ["(", ")"]]
}

Odpowiednie ustawienie w oknie dialogowym Opcje narzędzi Programu Visual Studio w Edytorze tekstów, Ogólne, Wyświetlanie jest pole wyboru Włącz kolorowanie par nawiasów klamrowych.>

Autoklosowanie

Podczas wpisywania programu 'Visual Studio tworzy parę pojedynczych cudzysłowów i umieszcza kursor w środku: '|'. Ta sekcja definiuje takie pary.

{
  "autoClosingPairs": [
    { "open": "{", "close": "}" },
    { "open": "[", "close": "]" },
    { "open": "(", "close": ")" },
    { "open": "'", "close": "'", "notIn": ["string", "comment"] },
    { "open": "\"", "close": "\"", "notIn": ["string"] },
    { "open": "`", "close": "`", "notIn": ["string", "comment"] },
    { "open": "/**", "close": " */", "notIn": ["string"] }
  ]
}

Klucz notIn wyłącza tę funkcję w niektórych zakresach kodu. Na przykład podczas pisania następującego kodu:

// ES6's Template String
`ES6's Template String`;

Pojedynczy cudzysłów nie jest automatycznielosowany.

Pary, które nie wymagają notIn właściwości, mogą również używać prostszej składni:

{
  "autoClosingPairs": [ ["{", "}"], ["[", "]"] ]
}
Autoklosowanie przed

Domyślnie program Visual Studio autokloses paruje tylko wtedy, gdy po kursorze znajduje się biały znak. Dlatego podczas wpisywania { następującego kodu JSX nie będzie można uzyskać autoclose:

const Component = () =>
  <div className={>
                  ^ Does not get autoclosed by default
  </div>

Jednak ta definicja zastępuje to zachowanie:

{
  "autoCloseBefore": ";:.,=}])>` \n\t"
}

Teraz, gdy wprowadzisz bezpośrednio { przed >poleceniem , program Visual Studio automatycznie udostępnia go za pomocą polecenia }.

Autosurrounding

Po wybraniu zakresu w programie Visual Studio i wprowadzeniu nawiasu otwierającego program Visual Studio otacza wybraną zawartość parą nawiasów kwadratowych. Ta funkcja jest nazywana autosurrounding, a tutaj można zdefiniować pary autosurrounding dla określonego języka:

{
  "surroundingPairs": [
    ["{", "}"],
    ["[", "]"],
    ["(", ")"],
    ["'", "'"],
    ["\"", "\""],
    ["`", "`"]
  ]
}

Odpowiednie ustawienie w opcjach narzędzi Programu Visual Studio znajduje się w Edytorze tekstów, Ogólne, Wyświetl pole wyboru Automatycznie otacza zaznaczenie podczas wpisywania cudzysłowów lub nawiasów kwadratowych.>

Wzorzec programu Word

wordPattern definiuje to, co jest uważane za słowo w języku programowania. Funkcje sugestii kodu używają tego ustawienia, aby określić granice wyrazów, jeśli wordPattern jest ustawiona.

{
  "wordPattern": "(-?\\d*\\.\\d\\w*)|([^\\`\\~\\!\\@\\#\\%\\^\\&\\*\\(\\)\\-\\=\\+\\[\\{\\]\\}\\\\\\|\\;\\:\\'\\\"\\,\\.\\<\\>\\/\\?\\s]+)"
}

Reguły wcięcia

indentationRulesdefiniuje sposób dostosowywania wcięcia bieżącego wiersza lub następnego wiersza podczas pisania, wklejania i przenoszenia wierszy lub formatowania tekstu za pomocą klawiszy Ctrl+K, Ctrl+D (Formatuj dokument) i Ctrl K, Ctrl++F (Formatowanie zaznaczenia).

{
  "indentationRules": {
    "increaseIndentPattern": "^((?!\\/\\/).)*(\\{[^}\"'`]*|\\([^)\"'`]*|\\[[^\\]\"'`]*)$",
    "decreaseIndentPattern": "^((?!.*?\\/\\*).*\\*/)?\\s*[\\)\\}\\]].*$"
  }
}

Na przykład dopasuje wartość if (true) { , a następnie po naciśnięciu klawisza Enter po otwartym nawiasie {kwadratowym edytor automatycznie wcięcie raz, a kod zakończy się następująco:increaseIndentPattern

if (true) {
  console.log();

Oprócz increaseIndentPattern elementów i decreaseIndentPatteristnieją dwie inne reguły wcięcia:

  • indentNextLinePattern - Jeśli wiersz pasuje do tego wzorca, tylko następny wiersz po nim powinien zostać wcięcie raz.
  • unIndentedLinePattern — Jeśli wiersz pasuje do tego wzorca, jego wcięcie nie powinno zostać zmienione i nie powinno być oceniane względem innych reguł.

Jeśli nie ma ustawionej reguły wcięcia dla języka programowania, edytor wcięcie po zakończeniu wiersza z otwartym nawiasem i niezidenty podczas wpisywania nawiasu zamykającego. Nawias w tym miejscu jest definiowany przez bracketselement .

Naciśnięcie klawisza Enter

onEnterRules Definiuje listę reguł do oceny, gdy klawisz Enter jest naciskany w edytorze.

{
  "onEnterRules": [{
    "beforeText": "^\\s*(?:def|class|for|if|elif|else|while|try|with|finally|except|async).*?:\\s*$",
    "action": { "indent": "indent" }
  }]
}

Po naciśnięciu klawisza Enter tekst przed lub po jednym wierszu nad kursorem jest sprawdzany względem następujących właściwości:

  • beforeText (obowiązkowe). Wyrażenie regularne, które pasuje do tekstu przed kursorem (ograniczone do bieżącego wiersza).
  • afterText. Wyrażenie regularne zgodne z tekstem po kursorze (ograniczone do bieżącego wiersza).
  • previousLineText. Wyrażenie regularne, które pasuje do tekstu w jednym wierszu nad kursorem.

Jeśli wszystkie określone właściwości są zgodne, reguła jest uważana za zgodną i nie są oceniane dalej onEnterRules . Element onEnterRule może określać następujące akcje:

  • indent (obowiązkowe). Jeden z none, indent, outdent, indentOutdent.
    • none oznacza, że nowy wiersz dziedziczy wcięcie bieżącego wiersza.
    • indent oznacza, że nowy wiersz jest wcięcie względem bieżącego wiersza.
    • outdent oznacza, że nowy wiersz jest niezidentyfikowany względem bieżącego wiersza.
    • indentOutdent oznacza, że wstawione są dwa nowe wiersze, jedno wcięcie i drugie niezidentyfikowane.
  • appendText. Ciąg, który jest dołączany po nowym wierszu i po wcięcie.
  • removeText. Liczba znaków do usunięcia z wcięcia nowego wiersza.

Ustawienia właściwości

W projekcie rozszerzenia upewnij się, że plik language-configuration.json ma następujące ustawienia właściwości:

Build Action = Content
Include in VSIX = True
Copy to output = Copy always 

(opcjonalnie) Dodawanie pliku gramatycznego

Ponadto można dodać plik gramatyki TextMate, aby zapewnić kolorowanie składni dla języka. Gramatyki TextMate są kolekcją ze strukturą wyrażeń regularnych i są zapisywane jako pliki plist (XML) lub JSON. Zobacz Gramatyka języka. Jeśli nie podasz pliku gramatycznego specyficznego dla języka, zostanie użyte wbudowane ustawienie domyślne.

Aby dodać niestandardowe pliki gramatyki lub motywu TextMate, wykonaj następujące kroki:

  1. Utwórz folder o nazwie "Gramatyki" wewnątrz rozszerzenia (lub może to być dowolna wybrana nazwa).

  2. W folderze Gramatyka dołącz dowolne pliki *.tmlanguage, *.plist, *.tmtheme lub *.json, które mają zapewnić niestandardowe kolorowanie.

    Napiwek

    Plik tmtheme definiuje sposób mapowania zakresów na klasyfikacje programu Visual Studio (nazwane klucze kolorów). Aby uzyskać wskazówki, możesz odwołać się do globalnego pliku tmtheme w katalogu %ProgramFiles(x86)%\Microsoft Visual Studio\<version>\<SKU>\Common7\IDE\CommonExtensions\Microsoft\TextMate\Starterkit\Themesg .

Tworzenie pliku pkgdef

Następnie utwórz .pkgdef plik. Plik .pkgdef zawiera wszystkie informacje rejestracyjne, które w przeciwnym razie zostaną dodane do rejestru systemowego. Aby uzyskać więcej informacji na temat pkgdef plików, zobacz Rejestrowanie pakietów VSPackages i Co to jest plik pkgdef? I dlaczego?. pkgdef W pliku powinna znajdować się ścieżka do language-configuration.json pliku i ścieżka gramatyki języka. Usługi językowe, takie jak LSP, proszą o typ zawartości edytora i uzyskają je za pośrednictwem konfiguracji języka. Te informacje zawierają analizę specyficzną dla języka na serwerze, która może komunikować się z narzędziami programistycznymi. Gdy usługa językowa nie istnieje, aparat konfiguracji języka wraca do gramatyki TextMate. Plik .pkgdef powinien wyglądać następująco:

[$RootKey$\TextMate\Repositories]
"AspNetCoreRazor="$PackageFolder$\Grammars

// Defines where the language configuration file for a given
// grammar name is (value of the ScopeName tag in the tmlanguage file).
[$RootKey$\TextMate\LanguageConfiguration\GrammarMapping]
"text.aspnetcorerazor"="$PackageFolder$\language-configuration.json"

// Defines where the language configuration file for a given
// language name is (partial value of the content type name).
[$RootKey$\TextMate\LanguageConfiguration\ContentTypeMapping]
"RazorLSP"="$PackageFolder$\language-configuration.json"

[$RootKey$\TextMate\LanguageConfiguration\GrammarMapping]
"text.html.basic"="$PackageFolder$\html-language-configuration.json"
"source.js"="$PackageFolder$\javascript-language-configuration.json"
"source.css"="$PackageFolder$\css-language-configuration.json"
"source.cs"="$PackageFolder$\csharp-language-configuration.json

Upewnij się, że właściwości pkgdef pliku są ustawione w następujący sposób:

Build Action = Content
Include in VSIX = True
Copy to output = Copy always 

Aby udostępnić informacje o konfiguracji języka dla programu Visual Studio, dołącz language-configuration plik do pakietu VSIX. Dołączenie tego pliku oznacza, że jest dostarczany z rozszerzeniem programu Visual Studio. Plik informuje program Visual Studio, że konfiguracja języka jest dostępna do użycia. Aby dodać plik, zmodyfikuj vsixmanifest plik , aby dodać plik def PKGDEF, na przykład:

<Asset Type="Microsoft.VisualStudio.VsPackage" Path="Test.pkgdef"/>