🚀 VS Code で で入手しましょう!

カスタムエディター API

カスタムエディターを使用すると、拡張機能は、特定のリソースに対して VS Code の標準テキストエディターの代わりに使用される、完全にカスタマイズ可能な読み取り/書き込みエディターを作成できます。これらは、次のような幅広いユースケースに対応できます。

  • シェーダーや 3D モデルなどのアセットを VS Code で直接プレビューする。
  • Markdown や XAML などの言語用の WYSIWYG エディターを作成する。
  • CSV、JSON、XML などのデータファイルに対して、代替のビジュアルレンダリングを提供する。
  • バイナリファイルまたはテキストファイル用の完全にカスタマイズ可能な編集エクスペリエンスを構築する。

このドキュメントでは、カスタムエディター API の概要と、カスタムエディターを実装するための基本について説明します。2 種類のカスタムエディターとその違い、およびユースケースに適したタイプについて見ていきます。次に、これらのカスタムエディタータイプごとに、適切に動作するカスタムエディターを構築するための基本について説明します。

カスタムエディターは強力な新しい拡張機能ポイントですが、基本的なカスタムエディターの実装は実際にはそれほど難しくありません。それでも、初めての VS Code 拡張機能を開発している場合は、VS Code API の基本に慣れるまで、カスタムエディターに飛び込むのを控えることを検討してください。カスタムエディターは、webview やテキストドキュメントなど、多くの VS Code の概念に基づいて構築されているため、これらの新しいアイデアをすべて同時に学習すると、少し圧倒されるかもしれません。

しかし、準備ができていて、これから構築するクールなカスタムエディターについて考えているなら、始めましょう!ドキュメントに沿って進み、カスタムエディター API がどのように連携するかを確認できるように、カスタムエディター拡張機能のサンプルを必ずダウンロードしてください。

VS Code API の使用

カスタムエディター API の基本

カスタムエディターは、特定のリソースに対して VS Code の標準テキストエディターの代わりとして表示される代替ビューです。カスタムエディターには、ユーザーが操作するビューと、拡張機能が基になるリソースと対話するために使用するドキュメントモデルの 2 つの部分があります。

カスタムエディターのビュー側は、webview を使用して実装されています。これにより、標準の HTML、CSS、および JavaScript を使用してカスタムエディターのユーザーインターフェイスを構築できます。Webview は VS Code API に直接アクセスできませんが、メッセージをやり取りすることで拡張機能と通信できます。Webview とその最適な使用方法の詳細については、webview のドキュメントを参照してください。

カスタムエディターのもう一方の部分は、ドキュメントモデルです。このモデルは、拡張機能が作業しているリソース(ファイル)を理解する方法です。CustomTextEditorProvider は、VS Code の標準 TextDocument をドキュメントモデルとして使用し、ファイルへのすべての変更は VS Code の標準テキスト編集 API を使用して表現されます。一方、CustomReadonlyEditorProviderCustomEditorProvider を使用すると、独自のドキュメントモデルを提供できるため、テキスト以外のファイル形式に使用できます。

カスタムエディターはリソースごとに単一のドキュメントモデルを持ちますが、このドキュメントのエディターインスタンス(ビュー)は複数存在する可能性があります。たとえば、CustomTextEditorProvider を持つファイルを開き、[表示] > [エディターを分割] コマンドを実行することを想像してください。この場合でも、ワークスペースにはリソースのコピーが 1 つしかないため、TextDocument は 1 つだけですが、そのリソースには 2 つの webview があります。

CustomEditorCustomTextEditor の比較

カスタムエディターには、カスタムテキストエディターとカスタムエディターの 2 つのクラスがあります。これらの主な違いは、ドキュメントモデルの定義方法です。

CustomTextEditorProvider は、VS Code の標準 TextDocument をデータモデルとして使用します。CustomTextEditor は、任意のテキストベースのファイルタイプに使用できます。CustomTextEditor は、VS Code がテキストファイルの処理方法をすでに認識しており、保存やホットイグジット用のファイルのバックアップなどの操作を実装できるため、実装が大幅に容易です。

一方、CustomEditorProvider を使用すると、拡張機能は独自のドキュメントモデルを持ち込むことができます。これは、画像などのバイナリ形式に CustomEditor を使用できることを意味しますが、保存やバックアップの実装など、拡張機能がより多くの責任を負うことも意味します。カスタムエディターがプレビュー用のカスタムエディターなど、読み取り専用の場合は、この複雑さの多くを省略できます。

使用するカスタムエディターのタイプを決定しようとする場合、決定は通常簡単です。テキストベースのファイル形式を扱う場合は CustomTextEditorProvider を使用し、バイナリファイル形式の場合は CustomEditorProvider を使用します。

機能拡張ポイント

customEditors 機能拡張ポイントは、拡張機能が提供するカスタムエディターについて VS Code に通知する方法です。たとえば、VS Code は、カスタムエディターがどのタイプのファイルを処理するか、および UI でカスタムエディターを識別する方法を知る必要があります。

これは、カスタムエディター拡張機能のサンプルの基本的な customEditor 機能拡張です。

"contributes": {
  "customEditors": [
    {
      "viewType": "catEdit.catScratch",
      "displayName": "Cat Scratch",
      "selector": [
        {
          "filenamePattern": "*.cscratch"
        }
      ],
      "priority": "default"
    }
  ]
}

customEditors は配列であるため、拡張機能は複数のカスタムエディターを機能拡張できます。カスタムエディターエントリ自体を分解してみましょう。

  • viewType - カスタムエディターの一意の識別子。

    これは、VS Code が package.json のカスタムエディター機能拡張をコード内のカスタムエディター実装に関連付ける方法です。これはすべての拡張機能で一意である必要があるため、"preview" などの汎用的な viewType ではなく、"viewType": "myAmazingExtension.svgPreview" など、拡張機能に固有のものを必ず使用してください。

  • displayName - VS Code の UI でカスタムエディターを識別する名前。

    表示名は、[表示] > [開き直し] ドロップダウンなどの VS Code UI でユーザーに表示されます。

  • selector - カスタムエディターがアクティブになるファイルを指定します。

    selector は、1 つ以上の glob パターンの配列です。これらの glob パターンはファイル名と照合され、カスタムエディターをそれらに使用できるかどうかを判断します。*.png などの filenamePattern は、すべての PNG ファイルに対してカスタムエディターを有効にします。

    **/translations/*.json など、ファイル名またはディレクトリ名に一致する、より具体的なパターンを作成することもできます。

  • priority - (オプション)カスタムエディターを使用するタイミングを指定します。

    priority は、リソースが開かれたときにカスタムエディターを使用するタイミングを制御します。使用可能な値は次のとおりです。

    • "default" - カスタムエディターの selector に一致するすべてのファイルに対してカスタムエディターを使用しようとします。特定のファイルに対して複数のカスタムエディターがある場合、ユーザーは使用するカスタムエディターを選択する必要があります。
    • "option" - デフォルトではカスタムエディターを使用しませんが、ユーザーがカスタムエディターに切り替えたり、デフォルトとして構成したりできるようにします。

カスタムエディターのアクティベーション

ユーザーがカスタムエディターのいずれかを開くと、VS Code は onCustomEditor:VIEW_TYPE アクティベーションイベントを発生させます。アクティベーション中に、拡張機能は registerCustomEditorProvider を呼び出して、予期される viewType を持つカスタムエディターを登録する必要があります。

onCustomEditor は、VS Code がカスタムエディターのインスタンスを作成する必要がある場合にのみ呼び出されることに注意することが重要です。VS Code が、[表示] > [開き直し] コマンドなどを使用して、使用可能なカスタムエディターに関する情報をユーザーに表示しているだけの場合、拡張機能はアクティブになりません。

カスタムテキストエディター

カスタムテキストエディターを使用すると、テキストファイル用のカスタムエディターを作成できます。これは、プレーンな非構造化テキストから、CSV、JSON、または XML まで、あらゆるものに対応できます。カスタムテキストエディターは、VS Code の標準 TextDocument をドキュメントモデルとして使用します。

カスタムエディター拡張機能のサンプルには、猫のひっかきファイル(.cscratch ファイル拡張子で終わる JSON ファイル)用の簡単なカスタムテキストエディターの例が含まれています。カスタムテキストエディターを実装する上で重要な点を見ていきましょう。

カスタムテキストエディターのライフサイクル

VS Code は、カスタムテキストエディターのビューコンポーネント(webview)とモデルコンポーネント(TextDocument)の両方のライフサイクルを処理します。VS Code は、新しいカスタムエディターインスタンスを作成する必要があるときに拡張機能を呼び出し、ユーザーがタブを閉じると、エディターインスタンスとドキュメントモデルをクリーンアップします。

これが実際にどのように機能するかを理解するために、ユーザーがカスタムテキストエディターを開いたとき、およびユーザーがカスタムテキストエディターを閉じたときに、拡張機能の観点から何が起こるかを順を追って説明します。

カスタムテキストエディターを開く

カスタムエディター拡張機能のサンプルを使用して、ユーザーが最初に .cscratch ファイルを開いたときに何が起こるかを次に示します。

  1. VS Code は、onCustomEditor:catCustoms.catScratch アクティベーションイベントを発生させます。

    これにより、拡張機能がまだアクティブ化されていない場合はアクティブ化されます。アクティベーション中に、拡張機能は registerCustomEditorProvider を呼び出すことにより、catCustoms.catScratch 用の CustomTextEditorProvider を拡張機能が登録していることを確認する必要があります。

  2. 次に、VS Code は、登録された CustomTextEditorProvidercatCustoms.catScratch に対して resolveCustomTextEditor を呼び出します。

    このメソッドは、開かれているリソースの TextDocumentWebviewPanel を受け取ります。拡張機能は、この webview パネルの初期 HTML コンテンツを入力する必要があります。

resolveCustomTextEditor が返されると、カスタムエディターがユーザーに表示されます。webview 内に何が描画されるかは、完全に拡張機能次第です。

カスタムエディターを分割した場合でも、カスタムエディターが開かれるたびに同じフローが発生します。カスタムエディターのすべてのインスタンスには独自の WebviewPanel がありますが、複数のカスタムテキストエディターは、同じリソース用である場合は同じ TextDocument を共有します。覚えておいてください。TextDocument はリソースのモデルであり、webview パネルはそのモデルのビューであると考えてください。

カスタムテキストエディターを閉じる

ユーザーがカスタムテキストエディターを閉じると、VS Code は WebviewPanelWebviewPanel.onDidDispose イベントを発生させます。この時点で、拡張機能はそのエディターに関連付けられているリソース(イベントサブスクリプション、ファイルウォッチャーなど)をクリーンアップする必要があります。

特定のリソースの最後​​のカスタムエディターが閉じられると、そのリソースの TextDocument も、それを使用している他のエディターがなく、他の拡張機能がそれを保持していない場合に破棄されます。TextDocument が閉じられたかどうかを確認するには、TextDocument.isClosed プロパティを確認できます。TextDocument が閉じられると、カスタムエディターを使用して同じリソースを開くと、新しい TextDocument が開かれます。

TextDocument との変更の同期

カスタムテキストエディターはドキュメントモデルとして TextDocument を使用するため、カスタムエディターで編集が発生したときは常に TextDocument を更新し、TextDocument が変更されたときはいつでも自身を更新する責任があります。

webview から TextDocument

カスタムテキストエディターでの編集は、ボタンのクリック、テキストの変更、アイテムのドラッグなど、さまざまな形式で行うことができます。ユーザーがカスタムテキストエディター内でファイル自体を編集するたびに、拡張機能は TextDocument を更新する必要があります。猫のひっかき拡張機能がこれを実装する方法を次に示します。

  1. ユーザーが webview の [ひっかき傷を追加] ボタンをクリックします。これにより、webview から拡張機能にメッセージがポストされます。

  2. 拡張機能がメッセージを受信します。次に、ドキュメントの内部モデルを更新します(猫のひっかき傷の例では、JSON に新しいエントリを追加するだけで構成されています)。

  3. 拡張機能は、更新された JSON をドキュメントに書き込む WorkspaceEdit を作成します。この編集は、vscode.workspace.applyEdit を使用して適用されます。

ワークスペースの編集は、ドキュメントを更新するために必要な最小限の変更にとどめてください。また、JSON などの言語を扱っている場合は、拡張機能がユーザーの既存のフォーマット規則(スペースとタブ、インデントサイズなど)を遵守するように努める必要があることに注意してください。

TextDocument から webview へ

TextDocument が変更された場合、拡張機能は、webview がドキュメントの新しい状態を反映していることを確認する必要もあります。TextDocument は、ユーザーによる元に戻す、やり直し、またはファイルの復元などのアクションによって変更される可能性があります。WorkspaceEdit を使用する他の拡張機能、または VS Code のデフォルトのテキストエディターでファイルを開くユーザーによって変更される可能性があります。猫のひっかき傷拡張機能がこれを実装する方法を次に示します。

  1. 拡張機能では、vscode.workspace.onDidChangeTextDocument イベントをサブスクライブします。このイベントは、TextDocument へのすべての変更(カスタムエディターが行った変更を含む!)に対して発生します。

  2. エディターがあるドキュメントの変更が届くと、新しいドキュメントの状態を含むメッセージを webview にポストします。次に、この webview は自身を更新して、更新されたドキュメントをレンダリングします。

カスタムエディターがトリガーするファイル編集はすべて onDidChangeTextDocument を発生させることを覚えておくことが重要です。ユーザーが webview で編集を行い、onDidChangeTextDocument が発生し、webview が更新され、webview が拡張機能で別の更新をトリガーし、onDidChangeTextDocument が発生する、などの更新ループに拡張機能が陥らないようにしてください。

また、JSON や XML などの構造化言語を扱っている場合は、ドキュメントが常に有効な状態であるとは限りません。拡張機能は、エラーを適切に処理できるか、ユーザーが何が間違っていて、それを修正する方法を理解できるようにエラーメッセージを表示する必要があります。

最後に、webview の更新にコストがかかる場合は、webview への更新をデバウンスすることを検討してください。

カスタムエディター

CustomEditorProvider および CustomReadonlyEditorProvider を使用すると、バイナリファイル形式用のカスタムエディターを作成できます。この API を使用すると、ファイルのユーザーへの表示方法、編集方法を完全に制御でき、拡張機能を save やその他のファイル操作にフックできます。繰り返しますが、テキストベースのファイル形式用のエディターを構築する場合は、実装がはるかに簡単な CustomTextEditor を代わりに使用することを強くお勧めします。

カスタムエディター拡張機能のサンプルには、肉球描画ファイル(.pawdraw ファイル拡張子で終わる jpeg ファイル)用の簡単なカスタムバイナリエディターの例が含まれています。バイナリファイル用のカスタムエディターの構築に必要な要素を見ていきましょう。

CustomDocument

カスタムエディターを使用すると、拡張機能は CustomDocument インターフェイスを使用して独自のドキュメントモデルを実装する責任があります。これにより、拡張機能はカスタムエディターと対話するために必要なデータを CustomDocument に自由に保存できますが、保存やホットイグジット用のファイルデータのバックアップなどの基本的なドキュメント操作を拡張機能が実装する必要があることも意味します。

開いているファイルごとに 1 つの CustomDocument があります。ユーザーは、現在のカスタムエディターを分割するなどして、単一のリソースに対して複数のエディターを開くことができますが、それらのすべてのエディターは同じ CustomDocument によってバックアップされます。

カスタムエディターのライフサイクル

supportsMultipleEditorsPerDocument

デフォルトでは、VS Code は、カスタムドキュメントごとに 1 つのエディターのみを許可します。この制限により、複数のカスタムエディターインスタンスを相互に同期することを心配する必要がないため、カスタムエディターを正しく実装することが容易になります。

ただし、拡張機能がサポートできる場合は、同じドキュメントに対して複数のエディターインスタンスを開けるように、カスタムエディターを登録するときに supportsMultipleEditorsPerDocument: true を設定することをお勧めします。これにより、カスタムエディターは VS Code の通常のテキストエディターのように動作するようになります。

カスタムエディターを開く ユーザーが customEditor 機能拡張ポイントに一致するファイルを開くと、VS Code は onCustomEditor アクティベーションイベントを発生させ、提供された viewType 用に登録されたプロバイダーを呼び出します。CustomEditorProvider には、カスタムエディターのドキュメントを提供することと、エディター自体を提供することの 2 つの役割があります。カスタムエディター拡張機能のサンプルcatCustoms.pawDraw エディターで何が起こるかの順序付きリストを次に示します。

  1. VS Code は、onCustomEditor:catCustoms.pawDraw アクティベーションイベントを発生させます。

    これにより、拡張機能がまだアクティブ化されていない場合はアクティブ化されます。また、アクティベーション中に catCustoms.pawDraw 用の CustomReadonlyEditorProvider または CustomEditorProvider を拡張機能が登録していることを確認する必要があります。

  2. VS Code は、catCustoms.pawDraw エディター用に登録された CustomReadonlyEditorProvider または CustomEditorProvideropenCustomDocument を呼び出します。

    ここでは、拡張機能にリソース URI が与えられ、そのリソースの新しい CustomDocument を返す必要があります。これは、拡張機能がそのリソースのドキュメント内部モデルを作成する必要がある時点です。これには、ディスクから初期リソース状態を読み取って解析するか、新しい CustomDocument を初期化することが含まれる場合があります。

    拡張機能は、CustomDocument を実装する新しいクラスを作成することで、このモデルを定義できます。この初期化段階は完全に拡張機能次第であることに注意してください。VS Code は、拡張機能が CustomDocument に保存する追加情報については気にしません。

  3. VS Code は、ステップ 2 の CustomDocument と新しい WebviewPanel を使用して resolveCustomEditor を呼び出します。

    ここでは、拡張機能はカスタムエディターの初期 HTML を入力する必要があります。必要に応じて、後で(たとえばコマンド内などで)参照できるように、WebviewPanel への参照を保持することもできます。

resolveCustomEditor が返されると、カスタムエディターがユーザーに表示されます。

ユーザーがカスタムエディターを使用して別のエディターグループで同じリソースを開いた場合(たとえば、最初のエディターを分割した場合)、拡張機能のジョブは簡略化されます。この場合、VS Code は、最初のエディターが開かれたときに作成した同じ CustomDocument を使用して resolveCustomEditor を呼び出すだけです。

カスタムエディターを閉じる

同じリソースに対してカスタムエディターの 2 つのインスタンスが開いているとします。ユーザーがこれらのエディターを閉じると、VS Code は拡張機能に通知し、拡張機能はエディターに関連付けられているリソースをクリーンアップできます。

最初のエディターインスタンスが閉じられると、VS Code は閉じたエディターの WebviewPanelWebviewPanel.onDidDispose イベントを発生させます。この時点で、拡張機能はその特定のエディターインスタンスに関連付けられているリソースをクリーンアップする必要があります。

2 番目のエディターが閉じられると、VS Code は再び WebviewPanel.onDidDispose を発生させます。ただし、これで CustomDocument に関連付けられているすべてのエディターも閉じました。CustomDocument のエディターがなくなった場合、VS Code はその CustomDocument.dispose を呼び出します。dispose の拡張機能の実装では、ドキュメントに関連付けられているリソースをクリーンアップする必要があります。

ユーザーがカスタムエディターを使用して同じリソースを再度開くと、新しい CustomDocumentopenCustomDocumentresolveCustomEditor フロー全体に戻ります。

読み取り専用カスタムエディター

次のセクションの多くは、編集をサポートするカスタムエディターにのみ適用され、逆説的に聞こえるかもしれませんが、多くのカスタムエディターは編集機能をまったく必要としません。たとえば、画像プレビューについて考えてみてください。または、メモリーダンプの視覚的なレンダリング。どちらもカスタムエディターを使用して実装できますが、どちらも編集可能である必要はありません。そこで CustomReadonlyEditorProvider が登場します。

CustomReadonlyEditorProvider を使用すると、編集をサポートしないカスタムエディターを作成できます。それらはインタラクティブにすることはできますが、元に戻すや保存などの操作はサポートしていません。また、読み取り専用カスタムエディターは、完全に編集可能なカスタムエディターと比較して、実装がはるかに簡単です。

編集可能なカスタムエディターの基本

編集可能なカスタムエディターを使用すると、元に戻す、やり直し、保存、ホットイグジットなどの標準の VS Code 操作にフックできます。これにより、編集可能なカスタムエディターは非常に強力になりますが、適切に実装するには、編集可能なカスタムテキストエディターまたは読み取り専用カスタムエディターを実装するよりもはるかに複雑になります。

編集可能なカスタムエディターは、CustomEditorProvider によって実装されます。このインターフェイスは CustomReadonlyEditorProvider を拡張するため、一連の編集固有の操作とともに、openCustomDocumentresolveCustomEditor などの基本的な操作を実装する必要があります。CustomEditorProvider の編集固有の部分を見ていきましょう。

編集

編集可能なカスタムドキュメントへの変更は、編集によって表現されます。編集は、テキストの変更から、画像の回転、リストの並べ替えまで、あらゆるものにすることができます。VS Code は、編集が何をするかの詳細を完全に拡張機能に任せますが、VS Code は編集が行われるタイミングを知る必要があります。編集は、VS Code がドキュメントをダーティとしてマークする方法であり、これにより、自動保存とバックアップが有効になります。

ユーザーがカスタムエディターのいずれかの webview で編集を行うたびに、拡張機能は CustomEditorProvider から onDidChangeCustomDocument イベントを発生させる必要があります。onDidChangeCustomDocument イベントは、カスタムエディターの実装に応じて、CustomDocumentContentChangeEventCustomDocumentEditEvent の 2 種類のイベントを発生させることができます。

CustomDocumentContentChangeEvent

CustomDocumentContentChangeEvent は、必要最小限の編集です。その唯一の機能は、ドキュメントが編集されたことを VS Code に伝えることです。

拡張機能が onDidChangeCustomDocument から CustomDocumentContentChangeEvent を発生させると、VS Code は関連付けられたドキュメントをダーティとしてマークします。この時点で、ドキュメントがダーティでなくなる唯一の方法は、ユーザーが保存または元に戻すことです。CustomDocumentContentChangeEvent を使用するカスタムエディターは、元に戻す/やり直しをサポートしていません。

CustomDocumentEditEvent

CustomDocumentEditEvent は、元に戻す/やり直しを可能にする、より複雑な編集です。常に CustomDocumentEditEvent を使用してカスタムエディターを実装し、元に戻す/やり直しの実装が不可能な場合にのみ CustomDocumentContentChangeEvent を使用するようにフォールバックする必要があります。

CustomDocumentEditEvent には、次のフィールドがあります。

  • document — 編集対象の CustomDocument
  • label — どのような種類の編集が行われたかを説明するオプションのテキスト(例:「トリミング」、「挿入」、...)
  • undo — 編集を元に戻す必要がある場合に VS Code によって呼び出される関数。
  • redo — 編集をやり直す必要がある場合に VS Code によって呼び出される関数。

拡張機能が onDidChangeCustomDocument から CustomDocumentEditEvent を発生させると、VS Code は関連付けられたドキュメントをダーティとしてマークします。ドキュメントをダーティでなくするには、ユーザーはドキュメントを保存または元に戻すか、ドキュメントの最後に保存された状態まで元に戻す/やり直すことができます。

エディターの undo メソッドと redo メソッドは、特定のエディットを元に戻すか、再適用する必要がある場合に VS Code によって呼び出されます。VS Code は編集の内部スタックを維持するため、拡張機能が 3 つの編集(abc と呼びましょう)で onDidChangeCustomDocument を発生させた場合

onDidChangeCustomDocument(a);
onDidChangeCustomDocument(b);
onDidChangeCustomDocument(c);

ユーザーアクションの次のシーケンスは、これらの呼び出しをもたらします。

undo — c.undo()
undo — b.undo()
redo — b.redo()
redo — c.redo()
redo — no op, no more edits

元に戻す/やり直しを実装するには、拡張機能は、関連付けられたカスタムドキュメントの内部状態を更新するだけでなく、ドキュメントに関連付けられているすべての webview を更新して、ドキュメントの新しい状態を反映するようにする必要があります。単一のリソースに対して複数の webview が存在する可能性があることに注意してください。これらは常に同じドキュメントデータを表示する必要があります。たとえば、画像エディターの複数のインスタンスは常に同じピクセルデータを表示する必要がありますが、各エディターインスタンスが独自のズームレベルと UI 状態を持つことを許可する場合があります。

保存

ユーザーがカスタムエディターを保存すると、拡張機能は、保存されたリソースを現在の状態でディスクに書き込む責任があります。カスタムエディターがこれをどのように行うかは、拡張機能の CustomDocument タイプと、拡張機能が内部で編集を追跡する方法に大きく依存します。

保存の最初のステップは、ディスクに書き込むデータストリームを取得することです。これに対する一般的なアプローチには、次のようなものがあります。

  • リソースの状態を追跡して、すばやくシリアル化できるようにします。

    たとえば、基本的な画像エディターは、ピクセルデータのバッファーを維持する場合があります。

  • 最後に保存してからの編集を再生して、新しいファイルを生成します。

    たとえば、より効率的な画像エディターは、croprotatescale など、最後に保存してからの編集を追跡する場合があります。保存時に、これらの編集をファイルの最後に保存された状態に適用して、新しいファイルを生成します。

  • 保存するファイルデータについて WebviewPanel にカスタムエディターを要求します。

    ただし、カスタムエディターは、表示されていない場合でも保存できることに注意してください。このため、拡張機能の save の実装が WebviewPanel に依存しないようにすることをお勧めします。これが不可能な場合は、webview が非表示の場合でも存続するように WebviewPanelOptions.retainContextWhenHidden 設定を使用できます。retainContextWhenHidden にはかなりのメモリオーバーヘッドがあるため、使用には慎重になってください。

リソースのデータを取得したら、通常は workspace FS API を使用してディスクに書き込みます。FS API は UInt8Array データを受け取り、バイナリファイルとテキストベースのファイルの両方を書き出すことができます。バイナリファイルデータの場合は、バイナリデータを UInt8Array に入れるだけです。テキストファイルデータの場合は、Buffer を使用して文字列を UInt8Array に変換します。

const writeData = Buffer.from('my text data', 'utf8');
vscode.workspace.fs.writeFile(fileUri, writeData);

次のステップ

VS Code の拡張機能の詳細については、次のトピックをお試しください。