如何刷新基于 vscode.TreeDataProvider 的 TreeView?

How to refresh vscode.TreeDataProvider based TreeView?

最初填充了 TreeView 并实例化了 TreeView。 'refresh' 按钮调用自定义刷新函数来收集更新的数据。此新信息存储在 context.globalState()

ctmInfrastructureProvider.refresh(); 不更新 TreeView。我也添加了事件侦听器。

export class CtmInfrastructureProvider implements vscode.TreeDataProvider<number> {

    private _onDidChangeTreeData: vscode.EventEmitter<number | null> = new vscode.EventEmitter<number | null>();
    readonly onDidChangeTreeData: vscode.Event<number | null> = this._onDidChangeTreeData.event;
.
.
.
    constructor(private context: vscode.ExtensionContext) {
        let ctmInfrastructureCacheTmp: any = context.globalState.get('ctmInfrastructureCache');
        this.refresh();
    }
.
.
.
}

这是我的刷新函数:

let ctmInfrastructureRefreshEntry = vscode.commands.registerCommand(
        'ctm.infrastructure.refreshEntry',
        async () => {           
ctmInfrastructureDicsovery = discoverCtmInfrastructure();                     context.globalState.update('ctmInfrastructureCache',JSON.parse(ctmInfrastructureDicsovery));
ctmInfrastructureProvider.refresh();
        }
    );
    context.subscriptions.push(ctmInfrastructureRefreshEntry);

TreeDataProvider refresh()

    refresh(offset?: number): void {
            this.parseTree();
    }
    private parseTree(): void {
        this.text = this.ctmInfrastructureCache;
        this.tree = json.parseTree(this.ctmInfrastructureCache);
    }

我错过了什么?

您还需要触发更改事件:

    refresh(offset?: number): void {
            this.parseTree();
        this._onDidChangeTreeData.fire();
    }

更新

实际上,我使用的方法与树演示中的方法略有不同:

import { TreeDataProvider, TreeItem, EventEmitter, TextDocument, ProviderResult, Event } from "vscode";
import { AntlrFacade } from "../backend/facade";

export class AntlrTreeDataProvider<T> implements TreeDataProvider<T> {
    protected currentFile: string | undefined;

    private changeEvent = new EventEmitter<void>();

    public constructor(protected backend: AntlrFacade) { }

    public get onDidChangeTreeData(): Event<void> {
        return this.changeEvent.event;
    }

    public refresh(document: TextDocument | undefined): void {
        if (document && document.languageId === "antlr" && document.uri.scheme === "file") {
            this.currentFile = document.fileName;
        } else {
            this.currentFile = undefined;
        }
        this.changeEvent.fire();
    }

    public getTreeItem(element: T): TreeItem {
        return element;
    }

    public getChildren(_element?: T): ProviderResult<T[]> {
        return undefined;
    }
}

取自我的 VS 代码扩展:https://github.com/mike-lischke/vscode-antlr4/blob/master/src/frontend/AntlrTreeDataProvider.ts。如您所见,我改用 EventEmitter,它不需要 fire() 事件的参数。

如果函数正在提供新数据,则刷新工作正常。 示例:

    refresh(offset?: number, context?: vscode.ExtensionContext): void {
        this.ctmInfrastructureCache = "some data";
        this.parseTree();
        if (offset) {
            this._onDidChangeTreeData.fire(offset);
        } else {
            this._onDidChangeTreeData.fire(undefined);
        }

    }