diff --git a/.changeset/configurable-treeview-root.md b/.changeset/configurable-treeview-root.md new file mode 100644 index 00000000000..488c72fec8a --- /dev/null +++ b/.changeset/configurable-treeview-root.md @@ -0,0 +1,11 @@ +--- +'@mermaid-js/mermaid': minor +--- + +feat: add configurable root node for treeView diagrams + +Added `config.treeView.root` option to control treeView root node behavior: + +- Default: Shows "/" root node +- String: Custom label for root node +- false: Hides root node completely diff --git a/cypress/integration/rendering/treeView/treeView.spec.ts b/cypress/integration/rendering/treeView/treeView.spec.ts index 5e6901964fb..9c9e3782600 100644 --- a/cypress/integration/rendering/treeView/treeView.spec.ts +++ b/cypress/integration/rendering/treeView/treeView.spec.ts @@ -72,4 +72,45 @@ treeView-beta ` ); }); + + it('should render treeView with default root "/" when no config is provided', () => { + imgSnapshotTest( + `treeView-beta + "file1.ts"` + ); + }); + + it('should render treeView with custom root label', () => { + imgSnapshotTest( + ` +--- +config: + treeView: + root: "My Project" +--- +treeView-beta + "folder1" + "file1.js" + "file2.ts" + "file7.ts" + ` + ); + }); + + it('should render treeView without root node when root is false', () => { + imgSnapshotTest( + ` +--- +config: + treeView: + root: false +--- +treeView-beta + "folder1" + "file1.js" + "file2.ts" + "file7.ts" + ` + ); + }); }); diff --git a/packages/mermaid/src/config.type.ts b/packages/mermaid/src/config.type.ts index 242be718371..873f61de713 100644 --- a/packages/mermaid/src/config.type.ts +++ b/packages/mermaid/src/config.type.ts @@ -1713,6 +1713,14 @@ export interface TreeViewDiagramConfig extends BaseDiagramConfig { * Thickness of the line */ lineThickness?: number; + /** + * Root node configuration for treeView diagrams. + * - string: Custom label for the root node + * - false: Hide the root node completely + * - undefined: Show default root node "/" + * + */ + root?: string | boolean | null; } /** * The object containing configurations specific for radar diagrams. diff --git a/packages/mermaid/src/diagrams/treeView/db.ts b/packages/mermaid/src/diagrams/treeView/db.ts index db18b948c5d..9624c0eb588 100644 --- a/packages/mermaid/src/diagrams/treeView/db.ts +++ b/packages/mermaid/src/diagrams/treeView/db.ts @@ -3,7 +3,6 @@ import type { TreeViewDB, Node } from './types.js'; import { getConfig as getCommonConfig } from '../../config.js'; import DEFAULT_CONFIG from '../../defaultConfig.js'; import { - clear as commonClear, getAccDescription, getAccTitle, getDiagramTitle, @@ -31,9 +30,15 @@ const state = new ImperativeState(() => ({ ], })); -const clear = () => { - state.reset(); - commonClear(); +const updateRootName = (config: Required) => { + const root = state.records.stack[0]; + if (config.root === false) { + root.name = ''; + } else if (typeof config.root === 'string') { + root.name = config.root; + } else { + root.name = '/'; + } }; const getRoot = () => { @@ -45,7 +50,9 @@ const getCount = () => state.records.cnt; const defaultConfig: Required = DEFAULT_CONFIG.treeView; const getConfig = (): Required => { - return cleanAndMerge(defaultConfig, getCommonConfig().treeView); + const config = cleanAndMerge(defaultConfig, getCommonConfig().treeView); + updateRootName(config); + return config; }; const addNode = (level: number, name: string) => { @@ -63,10 +70,12 @@ const addNode = (level: number, name: string) => { }; const db: TreeViewDB = { - clear, addNode, getRoot, getCount, + clear: () => { + state.reset(); + }, getConfig, getAccTitle, getAccDescription, diff --git a/packages/mermaid/src/diagrams/treeView/renderer.ts b/packages/mermaid/src/diagrams/treeView/renderer.ts index 150f765b763..af9c72b5446 100644 --- a/packages/mermaid/src/diagrams/treeView/renderer.ts +++ b/packages/mermaid/src/diagrams/treeView/renderer.ts @@ -79,6 +79,14 @@ const drawTree = ( }; const processNode = (node: Node, depth = 0) => { + // Skip rendering root node if root is false or name is empty + if (depth === 0 && (config.root === false || node.name === '')) { + node.children.forEach((child) => { + processNode(child, depth); + }); + return; + } + drawNode(elem, node, config, depth); node.children.forEach((child) => { processNode(child, depth + 1); diff --git a/packages/mermaid/src/diagrams/treeView/types.ts b/packages/mermaid/src/diagrams/treeView/types.ts index 43a7f4e6da3..09498deb939 100644 --- a/packages/mermaid/src/diagrams/treeView/types.ts +++ b/packages/mermaid/src/diagrams/treeView/types.ts @@ -21,6 +21,7 @@ export interface TreeViewDB extends DiagramDBBase { addNode: (level: number, name: string) => void; getRoot: () => Node; getCount: () => number; + clear: () => void; } export interface TreeViewDiagramStyles { diff --git a/packages/mermaid/src/schemas/config.schema.yaml b/packages/mermaid/src/schemas/config.schema.yaml index 1248d4ce6c7..75e15b550c7 100644 --- a/packages/mermaid/src/schemas/config.schema.yaml +++ b/packages/mermaid/src/schemas/config.schema.yaml @@ -2420,6 +2420,14 @@ $defs: # JSON Schema definition (maybe we should move these to a separate file) type: number minimum: 0 default: 1 + root: + description: | + Root node configuration for treeView diagrams. + - string: Custom label for the root node + - false: Hide the root node completely + - undefined: Show default root node "/" + type: [string, boolean, 'null'] + default: 'null' RadarDiagramConfig: title: Radar Diagram Config