import * as _angular_core from '@angular/core'; import { Signal, TemplateRef } from '@angular/core'; import { SdButton } from '@sdcorejs/angular/components/button'; import { SdIconSet } from '@sdcorejs/angular/modules/icon'; import { SdUnwrapSignal } from '@sdcorejs/angular/utilities/models'; import { Color } from '@sdcorejs/utils/models'; type SdTreeDataSource = TItem[] | Signal | (() => TItem[] | Promise); type SdTreeLoadType = 'static' | 'lazy'; type SdTreeOption = SdTreeStaticOption | SdTreeLazyOption; type SdTreeItem = SdTreeItemStatic | SdTreeItemLazy; type SdTreeItemByLoadType = TLoadType extends 'lazy' ? SdTreeItemLazy : SdTreeItemStatic; interface SdTreeItemBase { /** Stable node id used for expansion, selection, filtering ancestry, and auto-id generation. */ id: string; /** Text shown by the default tree row. Custom templates can still read `item` / `treeItem`. */ label: string; /** * Optional node icon override. * - Branch without `icon`: tree renders the default folder icon (`folder` / `folder_open`). * - Leaf without `icon`: tree renders no icon. * This replaces the old `leafIcon` split. One field is enough because each node decides its own icon. */ icon?: string | null; /** Consumer payload. Commands, selection callbacks, and `$implicit` template context receive this value. */ data: T; /** Initial expansion state for this node. Component state wins after the user toggles. */ expanded?: boolean; } interface SdTreeItemStatic extends SdTreeItemBase { /** Static-mode children. Lazy mode does not use this field. */ children?: SdTreeItemStatic[]; /** `hasChildren` belongs to lazy mode only; static mode derives branches from `children`. */ hasChildren?: never; } interface SdTreeItemLazy extends SdTreeItemBase { /** Lazy-mode hint. Set `false` for known leaf nodes that do not need `onExpandChildren`. */ hasChildren?: boolean; /** `children` belongs to static mode only; lazy loaded children are cached inside the component. */ children?: never; } interface SdTreeBaseOption { maxDepth?: number; indentSize?: number; } interface SdTreeStaticOption extends SdTreeBaseOption { loadType: 'static'; /** Expand all (`true`), none (`false`), or root levels where `level < number`. */ defaultExpanded?: boolean | number; } interface SdTreeLazyOption extends SdTreeBaseOption { loadType: 'lazy'; /** * Called once when a lazy node is first expanded. Return wrapped `SdTreeItemLazy` children, * not raw data, so each child has a stable id/label/icon contract. */ onExpandChildren: (item: SdTreeItemLazy) => Promise[]> | SdTreeItemLazy[]; } interface SdTreeCommand { key: string; title: string | ((item: T) => string); icon?: string | ((item: T) => string | undefined | null); color?: Color; fontSet?: SdIconSet; disabled?: boolean | ((item: T) => boolean); hidden?: boolean | ((item: T) => boolean); click: (item: T) => void; } interface SdTreeSelectorOption { visible?: boolean; /** Keep at most one loaded node selected. Takes precedence over cascade. */ single?: boolean; /** Select nodes independently or cascade selection through loaded descendants. */ cascade?: 'independent' | 'descendants'; actions?: SdTreeSelectionAction[]; message?: string | ((selectedItems: T[]) => string); disabled?: (item: T, selectedItems: T[]) => boolean; } interface SdTreeSelectionAction { icon?: string; fontSet?: SdUnwrapSignal; tooltip?: SdUnwrapSignal; title?: SdUnwrapSignal; color?: SdUnwrapSignal; type?: SdUnwrapSignal; hidden?: boolean | ((selectedItems: T[]) => boolean); click: (selectedItems: T[]) => void; } interface SdTreeComponentOptionBase = SdTreeItem> { autoId?: string | null; /** Root nodes can be an array, a signal, a sync loader, or an async loader. Call `reload()` to rerun loader sources. */ items: SdTreeDataSource; selectedItems?: T[] | null; selector?: SdTreeSelectorOption | null; commands?: SdTreeCommand[] | null; itemTemplate?: SdTreeItemTemplate | null; selectable?: boolean; onSelectedItemsChange?: (items: T[]) => void; onSelect?: (event: SdTreeSelectionEvent) => void; onExpand?: (event: SdTreeToggleEvent) => void; onCollapse?: (event: SdTreeToggleEvent) => void; } interface SdTreeStaticComponentOption extends SdTreeComponentOptionBase> { /** Static tree is the default when `tree` is omitted. */ tree?: SdTreeStaticOption; } interface SdTreeLazyComponentOption extends SdTreeComponentOptionBase> { tree: SdTreeLazyOption; } type SdTreeComponentOption = SdTreeStaticComponentOption | SdTreeLazyComponentOption; interface SdTreeNode { /** Wrapped tree item containing id/label/icon/data plus mode-specific tree metadata. */ treeItem: SdTreeItem; /** Raw consumer payload. Kept as a shortcut because most callbacks operate on data, not wrapper metadata. */ data: T; id: string; label: string; level: number; parent: SdTreeNode | null; children: SdTreeNode[]; hasChildren: boolean; isExpanded: boolean; isLoading: boolean; loadError?: unknown; } interface SdTreeItemContext { $implicit: T; item: T; treeItem: SdTreeItem; node: SdTreeNode; level: number; expanded: boolean; selected: boolean; loading: boolean; loadError?: unknown; hasChildren: boolean; isLeaf: boolean; toggle: () => void; select: () => void; retry: () => void; } type SdTreeItemTemplate = TemplateRef>; interface SdTreeSelectionEvent { item: T; selected: boolean; selectedItems: T[]; } interface SdTreeToggleEvent { item: T; expanded: boolean; node: SdTreeNode; } interface SdTreeLoadErrorEvent { item?: T; error: unknown; } declare class SdTreeItemDefDirective { static ngTemplateContextGuard(_dir: SdTreeItemDefDirective, ctx: unknown): ctx is SdTreeItemContext; readonly templateRef: TemplateRef>; static ɵfac: _angular_core.ɵɵFactoryDeclaration, never>; static ɵdir: _angular_core.ɵɵDirectiveDeclaration, "[sdTreeItemDef]", never, {}, {}, never, never, true, never>; } type SdTreeAutoIdPart = 'row' | 'toggle' | 'checkbox' | 'icon' | 'label' | 'command'; interface SdTreeNodeAutoIds { row?: string; toggle?: string; checkbox?: string; icon?: string; label?: string; command?: string; } interface SdTreeViewCommand { key: string; command: SdTreeCommand; title: string; icon: string; color: SdTreeCommand['color']; fontSet: SdTreeCommand['fontSet']; disabled: boolean; autoId?: string; defaultColor: boolean; } interface SdTreeViewNode extends SdTreeNode { icon?: string; selected: boolean; selectionDisabled: boolean; selectionIndeterminate: boolean; toggleDisabled: boolean; toggleLabel: string; ariaExpanded: boolean | null; autoIds: SdTreeNodeAutoIds; commands: SdTreeViewCommand[]; context: SdTreeItemContext; tabIndex: 0 | -1; } interface SdTreeSelectionActionView { action: SdTreeSelectionAction; autoId: string | null; } declare class SdTree { #private; readonly autoIdInput: _angular_core.InputSignal; readonly option: _angular_core.InputSignal | undefined>; /** Migration bridge. New usage should put the data source in `option.items`. */ readonly items: _angular_core.InputSignal> | undefined>; /** Migration bridge. New usage should put static/lazy config in `option.tree`. */ readonly tree: _angular_core.InputSignal | undefined>; readonly selectedItemsInput: _angular_core.InputSignal; readonly commands: _angular_core.InputSignal[] | null | undefined>; readonly selectable: _angular_core.InputSignalWithTransform; readonly selector: _angular_core.InputSignal | null | undefined>; readonly itemTemplate: _angular_core.InputSignal> | null | undefined>; readonly selectedItemsChange: _angular_core.OutputEmitterRef; readonly selectChange: _angular_core.OutputEmitterRef>; readonly expandChange: _angular_core.OutputEmitterRef>; readonly collapseChange: _angular_core.OutputEmitterRef>; readonly loadError: _angular_core.OutputEmitterRef>; readonly itemDef: _angular_core.Signal | undefined>; readonly resolvedItemsSource: _angular_core.Signal>>; readonly resolvedTree: _angular_core.Signal>; readonly resolvedSelector: _angular_core.Signal | null | undefined>; readonly resolvedCommands: _angular_core.Signal[]>; readonly resolvedSelectable: _angular_core.Signal; readonly autoId: _angular_core.Signal; readonly resolvedItemTemplate: _angular_core.Signal> | undefined>; readonly indentSize: _angular_core.Signal; readonly rootLoading: _angular_core.WritableSignal; readonly rootError: _angular_core.WritableSignal; readonly activeNodeId: _angular_core.WritableSignal; readonly normalizedFilterText: _angular_core.Signal; readonly selectionVisible: _angular_core.Signal; readonly selectedIdSet: _angular_core.Signal>; readonly rootNodes: _angular_core.Signal[]>; readonly visibleNodes: _angular_core.Signal[]>; readonly selectedItems: _angular_core.Signal; readonly selectedCount: _angular_core.Signal; readonly selectionMessage: _angular_core.Signal; readonly visibleSelectionActions: _angular_core.Signal[]>; readonly selectionActionViews: _angular_core.Signal[]>; readonly clearSelectionAutoId: _angular_core.Signal; /** * Template-facing row model. Expensive/variable values are resolved once per * signal recomputation so the HTML does not call helper methods for every CD pass. */ readonly visibleViewNodes: _angular_core.Signal[]>; readonly trackByNode: (_index: number, node: SdTreeNode) => string; constructor(); reload(): void; filter(searchText: string | undefined | null): void; isSelected(node: SdTreeNode): boolean; nodeIcon(node: SdTreeNode): string | undefined; visibleCommands(node: SdTreeNode): SdTreeCommand[]; isSelectionDisabled(node: SdTreeNode): boolean; commandTitle(command: SdTreeCommand, item: T): string; commandIcon(command: SdTreeCommand, item: T): string; isCommandDisabled(command: SdTreeCommand, item: T): boolean; toggle(node: SdTreeNode, event?: Event): Promise; toggleSelection(node: SdTreeNode, event?: Event): void; clearSelection(): void; onSelectionAction(action: SdTreeSelectionAction): void; retry(): void; retryNode(node: SdTreeNode, event?: Event): void; errorMessage(error: unknown): string; onRowFocus(node: SdTreeNode): void; onRowKeydown(node: SdTreeNode, event: KeyboardEvent): void; createContext(node: SdTreeNode): SdTreeItemContext; nodeAutoId(node: SdTreeNode, part: SdTreeAutoIdPart): string | undefined; commandAutoId(node: SdTreeNode, command: SdTreeCommand): string | undefined; static ɵfac: _angular_core.ɵɵFactoryDeclaration, never>; static ɵcmp: _angular_core.ɵɵComponentDeclaration, "sd-tree", never, { "autoIdInput": { "alias": "autoId"; "required": false; "isSignal": true; }; "option": { "alias": "option"; "required": false; "isSignal": true; }; "items": { "alias": "items"; "required": false; "isSignal": true; }; "tree": { "alias": "tree"; "required": false; "isSignal": true; }; "selectedItemsInput": { "alias": "selectedItems"; "required": false; "isSignal": true; }; "commands": { "alias": "commands"; "required": false; "isSignal": true; }; "selectable": { "alias": "selectable"; "required": false; "isSignal": true; }; "selector": { "alias": "selector"; "required": false; "isSignal": true; }; "itemTemplate": { "alias": "itemTemplate"; "required": false; "isSignal": true; }; }, { "selectedItemsChange": "selectedItemsChange"; "selectChange": "selectChange"; "expandChange": "expandChange"; "collapseChange": "collapseChange"; "loadError": "loadError"; }, ["itemDef"], never, true, never>; } export { SdTree, SdTreeItemDefDirective }; export type { SdTreeAutoIdPart, SdTreeBaseOption, SdTreeCommand, SdTreeComponentOption, SdTreeComponentOptionBase, SdTreeDataSource, SdTreeItem, SdTreeItemBase, SdTreeItemByLoadType, SdTreeItemContext, SdTreeItemLazy, SdTreeItemStatic, SdTreeItemTemplate, SdTreeLazyComponentOption, SdTreeLazyOption, SdTreeLoadErrorEvent, SdTreeLoadType, SdTreeNode, SdTreeNodeAutoIds, SdTreeOption, SdTreeSelectionAction, SdTreeSelectionActionView, SdTreeSelectionEvent, SdTreeSelectorOption, SdTreeStaticComponentOption, SdTreeStaticOption, SdTreeToggleEvent, SdTreeViewCommand, SdTreeViewNode };