Skip to content

Commit 1147e1c

Browse files
committed
take parent nodes into account when keeping expanded/collapsed state
1 parent 87ecf1f commit 1147e1c

File tree

2 files changed

+38
-12
lines changed

2 files changed

+38
-12
lines changed

vscode-extensions/vscode-spring-boot/lib/explorer/nodes.ts

Lines changed: 31 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ import { Location } from "vscode-languageclient";
33
import { LsStereoTypedNode } from "./structure-tree-manager";
44

55
export class SpringNode {
6-
constructor(readonly children: SpringNode[]) {}
6+
constructor(public children: SpringNode[], private parent?: SpringNode) {}
77

88
getTreeItem(savedState?: TreeItemCollapsibleState): TreeItem {
99
const defaultState = savedState !== undefined ? savedState : TreeItemCollapsibleState.Collapsed;
@@ -17,11 +17,27 @@ export class SpringNode {
1717
getNodeId(): string {
1818
return "<base-node>";
1919
}
20+
21+
protected getParentPath(): string {
22+
if (!this.parent) {
23+
return "";
24+
}
25+
26+
const parentText = this.parent.getNodeText();
27+
// Recursively get the full path of all ancestors up to the root
28+
const ancestorPath = this.parent.getParentPath();
29+
30+
return ancestorPath ? `${ancestorPath}/${parentText}` : parentText;
31+
}
32+
33+
protected getNodeText(): string {
34+
return "<node>";
35+
}
2036
}
2137

2238
export class StereotypedNode extends SpringNode {
23-
constructor(private n: LsStereoTypedNode, children: SpringNode[]) {
24-
super(children);
39+
constructor(private n: LsStereoTypedNode, children: SpringNode[], parent?: SpringNode) {
40+
super(children, parent);
2541
}
2642

2743
getTreeItem(savedState?: TreeItemCollapsibleState): TreeItem {
@@ -49,16 +65,23 @@ export class StereotypedNode extends SpringNode {
4965
}
5066

5167
getNodeId(): string {
52-
// Create a unique identifier based on node attributes
53-
// Use text, icon, and location as identifying factors
68+
// Create a unique identifier based on node attributes, excluding icon
69+
// Include parent path in the computation for better uniqueness
5470
const textId = this.n.attributes.text || '';
55-
const iconId = this.n.attributes.icon || '';
5671
const locationId = this.n.attributes.location ?
5772
`${this.n.attributes.location.uri}:${this.n.attributes.location.range.start.line}:${this.n.attributes.location.range.start.character}` : '';
5873
const referenceId = this.n.attributes.reference ? String(this.n.attributes.reference) : '';
5974

60-
// Create a stable ID that can be used to match nodes across refreshes
61-
return `${textId}|${iconId}|${locationId}|${referenceId}`.replace(/\|+$/, ''); // Remove trailing separators
75+
// Build the node-specific part of the ID (without icon)
76+
const nodeSpecificId = `${textId}|${locationId}|${referenceId}`.replace(/\|+$/, ''); // Remove trailing separators
77+
78+
// Include parent path for better uniqueness
79+
const parentPath = this.getParentPath();
80+
return parentPath ? `${parentPath}/${nodeSpecificId}` : nodeSpecificId;
81+
}
82+
83+
protected getNodeText(): string {
84+
return this.n.attributes.text || '';
6285
}
6386

6487
getReferenceValue(): any {

vscode-extensions/vscode-spring-boot/lib/explorer/structure-tree-manager.ts

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -25,12 +25,15 @@ export class StructureManager {
2525
});
2626
}
2727

28-
private parseNode(json: any): SpringNode | undefined {
29-
return new StereotypedNode(json as LsStereoTypedNode, this.parseArray(json.children));
28+
private parseNode(json: any, parent?: SpringNode): SpringNode | undefined {
29+
const node = new StereotypedNode(json as LsStereoTypedNode, [], parent);
30+
// Parse children after creating the node so we can pass it as parent
31+
node.children.push(...this.parseArray(json.children, node));
32+
return node;
3033
}
3134

32-
private parseArray(json: any): SpringNode[] {
33-
return Array.isArray(json) ? (json as []).map(j => this.parseNode(j)).filter(e => !!e) : [];
35+
private parseArray(json: any, parent?: SpringNode): SpringNode[] {
36+
return Array.isArray(json) ? (json as []).map(j => this.parseNode(j, parent)).filter(e => !!e) : [];
3437
}
3538

3639
public get onDidChange(): Event<SpringNode | undefined> {

0 commit comments

Comments
 (0)