37 File Dialogs and Contextual Actions

VSCode extensions can not only read or write files in the background but also interact with the user via native dialogs. This chapter shows how to use file dialogs to select files or define save locations – and how to combine them with contextual information such as the active editor or the selected file.


37.1 Opening Files via Dialog

The showOpenDialog command opens a system-native file-open dialog:

const files = await vscode.window.showOpenDialog({
    canSelectFiles: true,
    canSelectFolders: false,
    canSelectMany: false,
    openLabel: "Select file",
    filters: {
        "Text files": ["txt", "md"]
    }
});

if (!files || files.length === 0) {
    vscode.window.showInformationMessage("No file selected.");
    return;
}

const selectedFile = files[0];
vscode.window.showInformationMessage(`Selected: ${selectedFile.fsPath}`);

The return value is an array of Uri objects – even with canSelectMany: false. Always check for undefined and empty selection.


37.2 Choosing Save Location via Dialog

With showSaveDialog, the user can specify a target for content to be saved:

const target = await vscode.window.showSaveDialog({
    defaultUri: vscode.Uri.file("/tmp/new_file.txt"),
    saveLabel: "Save as"
});

if (!target) {
    vscode.window.showWarningMessage("Save cancelled.");
    return;
}

const text = "Example content for saved file.";
const content = new TextEncoder().encode(text);
await vscode.workspace.fs.writeFile(target, content);

vscode.window.showInformationMessage(`File saved to ${target.fsPath}`);

Tip: Set defaultUri relative to a workspace folder, if available.


37.3 Contextual Actions: Active Editor

Many operations should refer to the file currently being edited or the cursor position. Example:

const editor = vscode.window.activeTextEditor;
if (!editor) {
    vscode.window.showErrorMessage("No editor opened.");
    return;
}

const docUri = editor.document.uri;
const workspaceFolder = vscode.workspace.getWorkspaceFolder(docUri);
const targetPath = vscode.Uri.joinPath(workspaceFolder!.uri, "output.txt");

const content = `Selected text:\n${editor.document.getText(editor.selection)}`;
await vscode.workspace.fs.writeFile(targetPath, new TextEncoder().encode(content));

This saves the current text selection to a new file in the same project.


37.4 Actions in the Explorer Context

When a command is triggered from the context menu in the file explorer, it can receive a Uri parameter directly:

vscode.commands.registerCommand("example.explorerAction", async (resourceUri: vscode.Uri) => {
    const content = `Action on file: ${resourceUri.fsPath}`;
    vscode.window.showInformationMessage(content);
});

A corresponding context entry in package.json is required:

"contributes": {
  "commands": [
    {
      "command": "example.explorerAction",
      "title": "Action in Explorer",
      "category": "Example"
    }
  ],
  "menus": {
    "explorer/context": [
      {
        "command": "example.explorerAction",
        "when": "resourceLangId == typescript",
        "group": "navigation"
      }
    ]
  }
}

This makes the command appear in the right-click menu of .ts files.


37.5 Best Practices

Die folgende Übersetzung ist technisch präzise und übernimmt alle Markdown- und Code-Strukturen unverändert: