TreeTable
Muestra registros jerárquicos en columnas, con relaciones, expansión y selección explícitas.
- Categoría
- Datos y jerarquía
- Import
@neural-ui/core/tree-table- Selector
neu-tree-table
import { NeuTreeTableComponent } from '@neural-ui/core/tree-table';Jerarquía y expansión
| Tarea | Horas |
|---|---|
Diseño | 24 |
Entrega | 12 |
Claves expandidas: —
Configurador
| Tarea | Horas |
|---|---|
Diseño | 24 |
Investigación | 8 |
Prototipo | 16 |
Entrega | 12 |
El template generado refleja las opciones seleccionadas. La pestaña Código incluye datos, imports y estado.
Los datos estructurados, callbacks y templates se muestran en los ejemplos y en la API.
El código añade las opciones avanzadas cuando difieren del valor predeterminado. Los datos y valores de esta configuración aparecen en el estado del template.
<neu-tree-table
[data]="rows()"
[columns]="columns()"
[rowKey]="rowKey"
[hierarchy]="hierarchy"
[labels]="labels()"
[appearance]='{
"density": "normal",
"borders": "rows",
"striped": false,
"stickyHeader": false,
"responsive": "contained-scroll"
}'
[hierarchyOptions]='{
"treeColumnId": "name",
"indentSize": 20
}'
[expandedKeys]="expanded()"
(expandedKeysChange)="expanded.set($event.next)"
[selection]="selection()"
[selectionOptions]='{
"mode": "single",
"indicator": "radio",
"selectOnRowClick": true,
"allowClear": false
}'
(selectionChange)="selection.set($event.next)"
[query]="query()"
(queryChange)="query.set($event)"
[filterOptions]='{
"surfaces": [],
"globalFields": [],
"predicates": {},
"debounceMs": 0,
"commit": "immediate"
}'
[exportOptions]="{ formats: ['csv'], defaultFilename: 'work-plan' }"
/>Estos valores corresponden a la vista previa actual. Los handlers, imports de Core y templates completos están en Código.
import { signal } from '@angular/core';
export const rows = signal([
{
"id": "design",
"name": "Diseño",
"hours": 24
},
{
"id": "research",
"name": "Investigación",
"hours": 8
},
{
"id": "prototype",
"name": "Prototipo",
"hours": 16
},
{
"id": "delivery",
"name": "Entrega",
"hours": 12
}
]);
export const columns = signal([
{
"id": "name",
"field": "name",
"header": "Tarea"
},
{
"id": "hours",
"field": "hours",
"header": "Horas"
}
]);
export const rowKey = () => { /* Handler in the complete example. */ };
export const hierarchy = {
"hierarchyRevision": 1,
"queryRevision": 0,
"roots": {
"status": "loaded",
"keys": [
"design",
"delivery"
],
"relationRevision": 1,
"appliedRequestId": null,
"total": 2,
"completeness": "complete"
},
"children": [
{
"parentKey": "design",
"relation": {
"status": "loaded",
"keys": [
"research",
"prototype"
],
"relationRevision": 1,
"appliedRequestId": null,
"total": 2,
"completeness": "complete"
}
},
{
"parentKey": "research",
"relation": {
"status": "loaded",
"keys": [],
"relationRevision": 1,
"appliedRequestId": null,
"total": 0,
"completeness": "complete"
}
},
{
"parentKey": "prototype",
"relation": {
"status": "loaded",
"keys": [],
"relationRevision": 1,
"appliedRequestId": null,
"total": 0,
"completeness": "complete"
}
},
{
"parentKey": "delivery",
"relation": {
"status": "loaded",
"keys": [],
"relationRevision": 1,
"appliedRequestId": null,
"total": 0,
"completeness": "complete"
}
}
]
};
export const labels = signal({
"ariaLabel": "Plan de trabajo",
"empty": "No hay tareas",
"error": "No se han podido cargar las tareas",
"loading": "Cargando tareas",
"pagination": "Paginación",
"retry": "Reintentar",
"selection": "Seleccionar tarea",
"expand": "Expandir",
"collapse": "Contraer"
});
export const expanded = signal([
"design"
]);
export const selection = signal({
"kind": "keys",
"keys": [
"design"
]
});
export const query = signal({
"page": 0,
"pageSize": 25,
"search": "",
"sort": [],
"filters": null
});Estos inputs requieren un modelo o función, no un checkbox. Modifica el campo del mismo nombre en el componente de Código y enlázalo al template; los datos que ya usa esta vista previa se muestran en el estado anterior.
columns · readonly NeuTreeTableColumn<T, F>[]En Código: define columns con este tipo y utiliza [columns]="columns" (o columns() si es una signal).
data · readonly T[]En Código: define data con este tipo y utiliza [data]="data" (o data() si es una signal).
editingOptions · NeuTreeTableEditingOptions<T, K, F>En Código: define editingOptions con este tipo y utiliza [editingOptions]="editingOptions" (o editingOptions() si es una signal).
editState · NeuTreeTableEditState<K>En Código: define editState con este tipo y utiliza [editState]="editState" (o editState() si es una signal).
exportOptions · NeuTreeTableExportOptionsEn Código: define exportOptions con este tipo y utiliza [exportOptions]="exportOptions" (o exportOptions() si es una signal).
hierarchy · NeuTreeTableHierarchy<K>En Código: define hierarchy con este tipo y utiliza [hierarchy]="hierarchy" (o hierarchy() si es una signal).
interactionOptions · NeuTreeTableInteractionOptionsEn Código: define interactionOptions con este tipo y utiliza [interactionOptions]="interactionOptions" (o interactionOptions() si es una signal).
labels · NeuTreeTableLabelsEn Código: define labels con este tipo y utiliza [labels]="labels" (o labels() si es una signal).
layout · NeuTreeTableLayoutStateEn Código: define layout con este tipo y utiliza [layout]="layout" (o layout() si es una signal).
paginationOptions · NeuTreeTablePaginationOptionsEn Código: define paginationOptions con este tipo y utiliza [paginationOptions]="paginationOptions" (o paginationOptions() si es una signal).
rowKey · (value: T) => KEn Código: define rowKey con este tipo y utiliza [rowKey]="rowKey" (o rowKey() si es una signal).
rowOptions · NeuTreeTableRowOptions<T>En Código: define rowOptions con este tipo y utiliza [rowOptions]="rowOptions" (o rowOptions() si es una signal).
sortOptions · NeuTreeTableSortOptionsEn Código: define sortOptions con este tipo y utiliza [sortOptions]="sortOptions" (o sortOptions() si es una signal).
virtualizationOptions · NeuTreeTableVirtualizationOptionsEn Código: define virtualizationOptions con este tipo y utiliza [virtualizationOptions]="virtualizationOptions" (o virtualizationOptions() si es una signal).
Seleccionar descendientes cargados
| Horas | |
|---|---|
| 24 | |
| 8 | |
| 16 | |
| 12 |
Claves seleccionadas: —
Cargar raíces e hijos
Aplica primero la respuesta de raíces. Después expande Diseño y aplica la respuesta de sus hijos.
| Tarea | Horas |
|---|---|
| No hay tareas | |
Solicitud pendiente: —
Virtualizar filas visibles
| Tarea | Horas |
|---|---|
Tarea 1 | 1 |
Tarea 2 | 2 |
Tarea 3 | 3 |
Tarea 4 | 4 |
Tarea 5 | 5 |
Tarea 6 | 6 |
Tarea 7 | 7 |
Tarea 8 | 8 |
Tarea 9 | 1 |
Tarea 10 | 2 |
Tarea 11 | 3 |
Tarea 12 | 4 |
Tarea 13 | 5 |
Tarea 14 | 6 |
Accesibilidad y teclado
Tecla | Acción |
|---|---|
| Tab / Shift+Tab | Entra y sal del treegrid y de sus controles habilitados. |
| ArrowUp / ArrowDown | Recorre las filas visibles cuando está activa la navegación por filas. |
| ArrowRight / ArrowLeft | Expande o cierra un nodo en la navegación jerárquica. |
| Enter / Space | Activa el control de expansión o selección enfocado. |
API
Inputs
Configura el componente con [propiedad]="valor". Tu aplicación proporciona estos valores; el componente no debe reemplazar el estado que le pasas.
Nombre | Tipo | Por defecto | Uso en el template | Descripción |
|---|---|---|---|---|
appearance | NeuTreeTableAppearance | {
density: 'normal',
borders: 'rows',
striped: false,
stickyHeader: false,
responsive: 'contained-scroll',
} | [appearance] | |
columns | readonly NeuTreeTableColumn<T, F>[] | [] | [columns] | |
data | readonly T[] | [] | [data] | |
dataMode | NeuTreeTableDataMode | 'client' | [dataMode] | |
editingOptions | NeuTreeTableEditingOptions<T, K, F> | { mode: 'none' } | [editingOptions] | |
editState | NeuTreeTableEditState<K> | {
kind: 'none',
} | [editState] | |
expandedKeys | readonly K[] | [] | [expandedKeys] | |
exportOptions | NeuTreeTableExportOptions | {
formats: [],
defaultFilename: 'tree-table',
} | [exportOptions] | |
filterOptions | NeuTreeTableFilterOptions<T, F> | { surfaces: [], globalFields: [], predicates: {}, debounceMs: 0, commit: 'immediate' } | [filterOptions] | |
hierarchy | NeuTreeTableHierarchy<K> | EMPTY_HIERARCHY as NeuTreeTableHierarchy<K>Valor derivado | [hierarchy] | |
hierarchyOptions | NeuTreeTableHierarchyOptions | Obligatorio | [hierarchyOptions] | |
interactionOptions | NeuTreeTableInteractionOptions | {
navigation: 'row',
wrapFocus: false,
announceChanges: false,
contextMenuAction: false,
} | [interactionOptions] | |
labels | NeuTreeTableLabels | {
ariaLabel: 'Tree table',
empty: 'No data',
loading: 'Loading',
error: 'Unable to load tree data',
retry: 'Retry',
expand: 'Expand node',
collapse: 'Collapse node',
selection: 'Selection',
pagination: 'Pagination',
} | [labels] | |
layout | NeuTreeTableLayoutState | {
order: [],
hidden: [],
widths: {},
pinnedStart: [],
pinnedEnd: [],
} | [layout] | |
paginationOptions | NeuTreeTablePaginationOptions | {
enabled: false,
pageSizeOptions: [],
position: 'bottom',
report: 'none',
} | [paginationOptions] | |
query | NeuTreeTableQuery<F> | {
page: 0,
pageSize: 25,
search: '',
sort: [],
filters: null,
} | [query] | |
rowKey | (value: T) => K | Obligatorio | [rowKey] | |
rowOptions | NeuTreeTableRowOptions<T> | {} | [rowOptions] | |
selection | NeuTreeTableSelection<K> | {
kind: 'keys',
keys: [],
} | [selection] | |
selectionOptions | NeuTreeTableSelectionOptions<T> | { mode: 'none' } | [selectionOptions] | |
sortOptions | NeuTreeTableSortOptions | {
mode: 'single',
removable: true,
defaultDirection: 'asc',
resetRootPageOnChange: true,
} | [sortOptions] | |
virtualizationOptions | NeuTreeTableVirtualizationOptions | { enabled: false } | [virtualizationOptions] |
Outputs
Escucha un evento con (evento)="handler($event)". La tabla indica qué datos recibe tu función y cómo utilizarlos.
Nombre | Valor emitido | Uso en el template | Descripción |
|---|---|---|---|
dataRequest | NeuTreeTableDataRequest<K, F> | (dataRequest)="onDataRequest($event)" | |
editCancel | NeuTreeTableEditCancel<T, K> | (editCancel)="onEditCancel($event)" | |
editCommit | NeuTreeTableEditCommit<T, K, F> | (editCommit)="onEditCommit($event)" | |
editStateChange | NeuTreeTableEditChange<K> | (editStateChange)="onEditStateChange($event)" | |
expandedKeysChange | NeuTreeTableExpandedKeysChange<K> | (expandedKeysChange)="onExpandedKeysChange($event)" | |
exportRequest | NeuTreeTableExportRequest<F> | (exportRequest)="onExportRequest($event)" | |
featureError | NeuTreeTableFeatureError | (featureError)="onFeatureError($event)" | |
layoutChange | NeuTreeTableLayoutChange | (layoutChange)="onLayoutChange($event)" | |
queryChange | NeuTreeTableQuery<F> | (queryChange)="onQueryChange($event)" | |
rangeChange | NeuTreeTableRangeChange | (rangeChange)="onRangeChange($event)" | |
rowAction | NeuTreeTableRowAction<T, K> | (rowAction)="onRowAction($event)" | |
selectionChange | NeuTreeTableSelectionChange<T, K> | (selectionChange)="onSelectionChange($event)" |
Templates
ng-content proyecta contenido dentro del componente. Los inputs TemplateRef reciben un template; las directivas ng-template identifican templates con un contexto tipado. Una directiva compartida en el entrypoint no es necesariamente un slot de este componente.
Nombre | Mecanismo | Contrato |
|---|---|---|
NeuTreeTableCaptionDirective | Directiva pública de template | ng-template[neuTreeTableCaption]Contexto utilizado: template.d.ts context.d.ts |
NeuTreeTableCellDirective | Directiva pública de template | ng-template[neuTreeTableCell]Contexto utilizado: template.d.ts context.d.ts |
NeuTreeTableEditorDirective | Directiva pública de template | ng-template[neuTreeTableEditor]Contexto utilizado: template.d.ts context.d.ts |
NeuTreeTableEmptyDirective | Directiva pública de template | ng-template[neuTreeTableEmpty]Contexto utilizado: template.d.ts context.d.ts |
NeuTreeTableErrorDirective | Directiva pública de template | ng-template[neuTreeTableError]Contexto utilizado: template.d.ts context.d.ts |
NeuTreeTableFooterDirective | Directiva pública de template | ng-template[neuTreeTableFooter]Contexto utilizado: template.d.ts context.d.ts |
NeuTreeTableHeaderDirective | Directiva pública de template | ng-template[neuTreeTableHeader]Contexto utilizado: template.d.ts context.d.ts |
NeuTreeTableLoadingDirective | Directiva pública de template | ng-template[neuTreeTableLoading]Contexto utilizado: template.d.ts context.d.ts |
NeuTreeTableNodeDirective | Directiva pública de template | ng-template[neuTreeTableNode]Contexto utilizado: template.d.ts context.d.ts |
NeuTreeTableSummaryDirective | Directiva pública de template | ng-template[neuTreeTableSummary]Contexto utilizado: template.d.ts context.d.ts |
NeuTreeTableToolbarDirective | Directiva pública de template | ng-template[neuTreeTableToolbar]Contexto utilizado: template.d.ts context.d.ts |
Ejemplo de uso
Pulsa el lápiz para editar las horas. Guarda el cambio o cancela desde el editor.
| Tarea | Horas |
|---|---|
Diseño(nivel 0) | 24 h |
Investigación(nivel 1) | 8 h |
Prototipo(nivel 1) | 16 h |
Entrega(nivel 0) | 12 h |
| Horas planificadas | |
Tareas disponibles: 4 | |
Métodos públicos
Nombre | Contrato |
|---|---|
export | export(request: NeuTreeTableExportRequest<F>): Promise<NeuTreeTableExportOutcome>;Exporta los datos visibles, cargados o seleccionados. Comprueba el resultado y gestiona las solicitudes delegadas en tu aplicación. example.ts |
focus | focus(target: NeuTreeTableFocusTarget<K>): void;Enfoca un nodo, una celda o el primer o último nodo visible. No expande los padres cerrados. example.ts |
retryData | retryData(target: NeuTreeTableRetryTarget<K>): void;Reintenta cargar las raíces o los hijos de un padre. La aplicación gestiona el dataRequest resultante. example.ts |
scrollTo | scrollTo(target: NeuTreeTableScrollTarget<K>): void;Desplaza la tabla hasta un nodo, un índice de fila o una posición en píxeles. Indica el tipo de destino explícitamente. example.ts |
Public Types
Abre un tipo para consultar su definición y los campos de sus interfaces.
import type { NeuTreeRelation } from '@neural-ui/core/tree-table';
import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeChildRelation } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeChildRelation<K extends NeuTreeTableKey> {
readonly parentKey: K;
readonly relation: NeuTreeRelation<K>;
}import type { NeuTreeValueAccessor } from '@neural-ui/core/tree-table';
import type { NeuTreeEditColumn } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeEditColumn<T, F extends string> {
readonly field: F;
readonly read?: NeuTreeValueAccessor<T>;
readonly write?: (value: T, candidate: unknown) => T;
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeErrorRelation } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeErrorRelation<K extends NeuTreeTableKey> {
readonly appliedRequestId: number | null;
readonly error: unknown;
readonly keys: readonly K[];
readonly relationRevision: number;
readonly status: 'error';
readonly total: number | null;
}import type { NeuTreeFilterConstraint } from '@neural-ui/core/tree-table';
import type { NeuTreeValueAccessor } from '@neural-ui/core/tree-table';
import type { NeuTreeFilterColumn } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeFilterColumn<T, F extends string> {
readonly defaultRule: NeuTreeFilterConstraint<F>['rule'];
readonly field: F;
readonly rules: readonly NeuTreeFilterConstraint<F>['rule'][];
readonly value?: NeuTreeValueAccessor<T>;
}import type { NeuTreeFilterConstraint } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeFilterConstraint<F extends string> {
readonly field: F;
readonly kind: 'condition';
readonly rule: 'equals' | 'notEquals' | 'contains' | 'notContains' | 'startsWith' | 'endsWith' | 'lessThan' | 'lessThanOrEqual' | 'greaterThan' | 'greaterThanOrEqual' | 'between' | 'in' | 'notIn' | 'isNull' | 'isNotNull' | 'isEmpty' | 'isNotEmpty';
readonly value: unknown;
}import type { NeuTreeFilterConstraint } from '@neural-ui/core/tree-table';
import type { NeuTreeFilterGroup } from '@neural-ui/core/tree-table';
import type { NeuTreeFilterExpression } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeFilterExpression<F extends string> = NeuTreeFilterConstraint<F> | NeuTreeFilterGroup<F>;import type { NeuTreeFilterExpression } from '@neural-ui/core/tree-table';
import type { NeuTreeFilterOperator } from '@neural-ui/core/tree-table';
import type { NeuTreeFilterGroup } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeFilterGroup<F extends string> {
readonly children: readonly NeuTreeFilterExpression<F>[];
readonly kind: 'group';
readonly operator: NeuTreeFilterOperator;
}import type { NeuTreeFilterOperator } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeFilterOperator = 'and' | 'or';import type { NeuTreeFilterPredicateContext } from '@neural-ui/core/tree-table';
import type { NeuTreeFilterPredicate } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeFilterPredicate<T, F extends string> = (context: NeuTreeFilterPredicateContext<T, F>) => boolean;import type { NeuTreeFilterPredicateContext } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeFilterPredicateContext<T, F extends string> {
readonly candidate: unknown;
readonly field: F;
readonly filterValue: unknown;
readonly value: T;
}import type { NeuTreeFilterSurface } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeFilterSurface = 'row' | 'menu' | 'builder';import type { NeuTreeRelationCompleteness } from '@neural-ui/core/tree-table';
import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeLoadedRelation } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeLoadedRelation<K extends NeuTreeTableKey> {
readonly appliedRequestId: number | null;
readonly completeness: NeuTreeRelationCompleteness;
readonly keys: readonly K[];
readonly relationRevision: number;
readonly status: 'loaded';
readonly total: number | null;
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeLoadingRelation } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeLoadingRelation<K extends NeuTreeTableKey> {
readonly appliedRequestId: number;
readonly keys: readonly K[];
readonly relationRevision: number;
readonly status: 'loading';
readonly total: number | null;
}import type { NeuTreeErrorRelation } from '@neural-ui/core/tree-table';
import type { NeuTreeLoadedRelation } from '@neural-ui/core/tree-table';
import type { NeuTreeLoadingRelation } from '@neural-ui/core/tree-table';
import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeUnloadedRelation } from '@neural-ui/core/tree-table';
import type { NeuTreeRelation } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeRelation<K extends NeuTreeTableKey> = NeuTreeUnloadedRelation<K> | NeuTreeLoadingRelation<K> | NeuTreeErrorRelation<K> | NeuTreeLoadedRelation<K>;import type { NeuTreeRelationCompleteness } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeRelationCompleteness = 'partial' | 'complete';import type { NeuTreeRelationStatus } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeRelationStatus = 'unloaded' | 'loading' | 'error' | 'loaded';import type { NeuTreeValueAccessor } from '@neural-ui/core/tree-table';
import type { NeuTreeSortColumn } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeSortColumn<T, F extends string> {
readonly compare?: (left: T, right: T) => number;
readonly field: F;
readonly value?: NeuTreeValueAccessor<T>;
}import type { NeuTreeSortDirection } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeSortDirection = 'asc' | 'desc';import type { NeuTreeSortDirection } from '@neural-ui/core/tree-table';
import type { NeuTreeSortEntry } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeSortEntry<F extends string> {
readonly direction: NeuTreeSortDirection;
readonly field: F;
}import type { NeuTreeTableAppearance } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableAppearance {
readonly borders: 'none' | 'rows' | 'cells';
readonly density: 'compact' | 'normal' | 'relaxed';
readonly responsive: 'contained-scroll' | 'stacked';
readonly stickyHeader: boolean;
readonly striped: boolean;
}import type { NeuTreeTableColumn } from '@neural-ui/core/tree-table';
import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableNodeContext } from '@neural-ui/core/tree-table';
import type { NeuTreeTableCellContext } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableCellContext<T, K extends NeuTreeTableKey, F extends string> extends NeuTreeTableNodeContext<T, K> {
readonly column: NeuTreeTableColumn<T, F>;
readonly columnIndex: number;
readonly logicalIndex: number;
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableRequestBase } from '@neural-ui/core/tree-table';
import type { NeuTreeTableChildrenRequest } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableChildrenRequest<K extends NeuTreeTableKey, F extends string> extends NeuTreeTableRequestBase<F> {
readonly kind: 'children';
readonly parentKey: K;
readonly reason: 'expand' | 'query' | 'retry';
readonly relationRevision: number;
}import type { NeuTreeEditColumn } from '@neural-ui/core/tree-table';
import type { NeuTreeFilterColumn } from '@neural-ui/core/tree-table';
import type { NeuTreeSortColumn } from '@neural-ui/core/tree-table';
import type { NeuTreeValueAccessor } from '@neural-ui/core/tree-table';
import type { NeuTreeTableColumn } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableColumn<T, F extends string> {
readonly align?: 'start' | 'center' | 'end';
readonly edit?: NeuTreeEditColumn<T, F>;
readonly field?: F;
readonly filter?: NeuTreeFilterColumn<T, F>;
readonly header: string;
readonly id: string;
readonly maxWidth?: string;
readonly minWidth?: string;
readonly sort?: NeuTreeSortColumn<T, F>;
readonly value?: NeuTreeValueAccessor<T>;
readonly width?: string;
}import type { NeuTreeTableDataMode } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableDataMode = 'client' | 'remote';import type { NeuTreeTableChildrenRequest } from '@neural-ui/core/tree-table';
import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableRootsRequest } from '@neural-ui/core/tree-table';
import type { NeuTreeTableDataRequest } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableDataRequest<K extends NeuTreeTableKey, F extends string> = NeuTreeTableRootsRequest<F> | NeuTreeTableChildrenRequest<K, F>;import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableEditCancel } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableEditCancel<T, K extends NeuTreeTableKey> {
readonly key: K;
readonly reason: 'escape' | 'gesture' | 'hidden' | 'destroy';
readonly value: T;
}import type { NeuTreeTableEditState } from '@neural-ui/core/tree-table';
import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableEditChange } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableEditChange<K extends NeuTreeTableKey> {
readonly next: NeuTreeTableEditState<K>;
readonly source: 'gesture' | 'keyboard' | 'commit' | 'cancel' | 'hidden';
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableEditCommit } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableEditCommit<T, K extends NeuTreeTableKey, F extends string> {
readonly draft: Readonly<Partial<T>>;
readonly field: F | null;
readonly key: K;
readonly source: 'cell' | 'row';
readonly value: T;
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableEditingOptions } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableEditingOptions<T, K extends NeuTreeTableKey, F extends string> {
readonly mode: 'none' | 'cell' | 'row';
readonly validate?: (context: {
readonly value: T;
readonly key: K;
readonly field: F | null;
readonly draft: Readonly<Partial<T>>;
}) => true | string;
}import type { NeuTreeTableCellContext } from '@neural-ui/core/tree-table';
import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableEditorContext } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableEditorContext<T, K extends NeuTreeTableKey, F extends string> extends NeuTreeTableCellContext<T, K, F> {
readonly cancel: () => void;
readonly commit: () => void;
readonly draftValue: unknown;
readonly field: F | null;
readonly update: (value: unknown) => void;
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableEditState } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableEditState<K extends NeuTreeTableKey> = {
readonly kind: 'none';
} | {
readonly kind: 'cell';
readonly key: K;
readonly columnId: string;
} | {
readonly kind: 'row';
readonly key: K;
};import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableExpandedKeysChange } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableExpandedKeysChange<K extends NeuTreeTableKey> {
readonly changedKey: K;
readonly next: readonly K[];
readonly source: 'toggle' | 'keyboard';
}import type { NeuTreeTableExportOptions } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableExportOptions {
readonly defaultFilename: string;
readonly formats: readonly ('csv' | 'json' | 'xlsx')[];
}import type { NeuTreeTableExportOutcome } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableExportOutcome = {
readonly status: 'downloaded';
readonly filename: string;
readonly rowCount: number;
} | {
readonly status: 'delegated';
} | {
readonly status: 'unsupported';
readonly reason: string;
} | {
readonly status: 'failed';
readonly error: unknown;
};import type { NeuTreeTableQuery } from '@neural-ui/core/tree-table';
import type { NeuTreeTableExportRequest } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableExportRequest<F extends string> {
readonly filename?: string;
readonly format: 'csv' | 'json' | 'xlsx';
readonly query: NeuTreeTableQuery<F>;
readonly scope: 'visible' | 'loaded' | 'selected';
}import type { NeuTreeTableFeatureError } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableFeatureError = {
readonly feature: 'hierarchy';
readonly code: 'cycle' | 'duplicate-key' | 'duplicate-parent' | 'missing-root' | 'missing-node' | 'duplicate-child' | 'orphan' | 'invalid-tree-column';
readonly error: unknown;
} | {
readonly feature: 'advanced-filter' | 'editor' | 'export';
readonly error: unknown;
};import type { NeuTreeFilterPredicate } from '@neural-ui/core/tree-table';
import type { NeuTreeFilterSurface } from '@neural-ui/core/tree-table';
import type { NeuTreeTableFilterOptions } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableFilterOptions<T, F extends string> {
readonly commit: 'immediate' | 'explicit';
readonly debounceMs: number;
readonly equals?: (left: unknown, right: unknown) => boolean;
readonly globalFields: readonly F[];
readonly predicates: Readonly<Record<string, NeuTreeFilterPredicate<T, F>>>;
readonly surfaces: readonly NeuTreeFilterSurface[];
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableFocusTarget } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableFocusTarget<K extends NeuTreeTableKey> = {
readonly kind: 'node';
readonly key: K;
} | {
readonly kind: 'cell';
readonly key: K;
readonly columnId: string;
} | {
readonly kind: 'first' | 'last';
};import type { NeuTreeTableColumn } from '@neural-ui/core/tree-table';
import type { NeuTreeTableHeaderContext } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableHeaderContext<T, F extends string> {
readonly column: NeuTreeTableColumn<T, F>;
readonly columnIndex: number;
}import type { NeuTreeChildRelation } from '@neural-ui/core/tree-table';
import type { NeuTreeRelation } from '@neural-ui/core/tree-table';
import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableHierarchy } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableHierarchy<K extends NeuTreeTableKey> {
readonly children: readonly NeuTreeChildRelation<K>[];
readonly hierarchyRevision: number;
readonly queryRevision: number;
readonly roots: NeuTreeRelation<K>;
}import type { NeuTreeTableHierarchyOptions } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableHierarchyOptions {
readonly indentSize: number;
readonly treeColumnId: string;
}import type { NeuTreeTableInteractionOptions } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableInteractionOptions {
readonly announceChanges: boolean;
readonly contextMenuAction: boolean;
readonly navigation: 'row';
readonly wrapFocus: boolean;
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableKey = string | number;import type { NeuTreeTableLabels } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableLabels {
readonly ariaLabel: string;
readonly collapse: string;
readonly empty: string;
readonly error: string;
readonly expand: string;
readonly loading: string;
readonly pagination: string;
readonly retry: string;
readonly selection: string;
}import type { NeuTreeTableLayoutState } from '@neural-ui/core/tree-table';
import type { NeuTreeTableLayoutChange } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableLayoutChange {
readonly next: NeuTreeTableLayoutState;
readonly source: 'resize' | 'reorder' | 'visibility' | 'pin';
}import type { NeuTreeTableLayoutState } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableLayoutState {
readonly hidden: readonly string[];
readonly order: readonly string[];
readonly pinnedEnd: readonly string[];
readonly pinnedStart: readonly string[];
readonly widths: Readonly<Record<string, string>>;
}import type { NeuTreeRelationStatus } from '@neural-ui/core/tree-table';
import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableNodeContext } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableNodeContext<T, K extends NeuTreeTableKey> {
readonly $implicit: T;
readonly childStatus: NeuTreeRelationStatus;
readonly depth: number;
readonly disabled: boolean;
readonly expanded: boolean;
readonly indeterminate: boolean;
readonly key: K;
readonly parentKey: K | null;
readonly path: readonly K[];
readonly selected: boolean;
readonly siblingCount: number | null;
readonly siblingIndex: number;
readonly toggleExpansion: () => void;
readonly toggleSelection: () => void;
readonly value: T;
}import type { NeuTreeTablePaginationOptions } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTablePaginationOptions {
readonly enabled: boolean;
readonly pageSizeOptions: readonly number[];
readonly position: 'top' | 'bottom' | 'both';
readonly report: 'none' | 'roots';
}import type { NeuTreeFilterExpression } from '@neural-ui/core/tree-table';
import type { NeuTreeSortEntry } from '@neural-ui/core/tree-table';
import type { NeuTreeTableQuery } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableQuery<F extends string> {
readonly filters: NeuTreeFilterExpression<F> | null;
readonly page: number;
readonly pageSize: number;
readonly search: string;
readonly sort: readonly NeuTreeSortEntry<F>[];
}import type { NeuTreeTableRange } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableRange {
readonly end: number;
readonly start: number;
}import type { NeuTreeTableRange } from '@neural-ui/core/tree-table';
import type { NeuTreeTableRangeChange } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableRangeChange {
readonly projectionRevision: number;
readonly reason: 'scroll' | 'resize' | 'programmatic' | 'hierarchy';
readonly render: NeuTreeTableRange;
readonly visible: NeuTreeTableRange;
}import type { NeuTreeTableQuery } from '@neural-ui/core/tree-table';
import type { NeuTreeTableRequestBase } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableRequestBase<F extends string> {
readonly hierarchyRevision: number;
readonly query: NeuTreeTableQuery<F>;
readonly queryRevision: number;
readonly requestId: number;
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableRetryTarget } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableRetryTarget<K extends NeuTreeTableKey> = {
readonly kind: 'roots';
} | {
readonly kind: 'children';
readonly parentKey: K;
};import type { NeuTreeTableRequestBase } from '@neural-ui/core/tree-table';
import type { NeuTreeTableRootsRequest } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableRootsRequest<F extends string> extends NeuTreeTableRequestBase<F> {
readonly kind: 'roots';
readonly reason: 'initial' | 'query' | 'page' | 'retry';
readonly relationRevision: number;
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableRowAction } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableRowAction<T, K extends NeuTreeTableKey> {
readonly key: K;
readonly source: 'click' | 'double-click' | 'keyboard' | 'context-menu';
readonly value: T;
}import type { NeuTreeTableRowOptions } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableRowOptions<T> {
readonly className?: (value: T) => string | readonly string[] | null;
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableScrollTarget } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableScrollTarget<K extends NeuTreeTableKey> = {
readonly kind: 'node';
readonly key: K;
readonly behavior?: ScrollBehavior;
} | {
readonly kind: 'index';
readonly index: number;
readonly behavior?: ScrollBehavior;
} | {
readonly kind: 'offset';
readonly offset: number;
readonly behavior?: ScrollBehavior;
};import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableSelection } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableSelection<K extends NeuTreeTableKey> {
readonly keys: readonly K[];
readonly kind: 'keys';
}import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeTableSelection } from '@neural-ui/core/tree-table';
import type { NeuTreeTableSelectionChange } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableSelectionChange<T, K extends NeuTreeTableKey> {
readonly addedKeys: readonly K[];
readonly loadedValues: readonly T[];
readonly next: NeuTreeTableSelection<K>;
readonly propagation: 'none' | 'loaded-subtree';
readonly removedKeys: readonly K[];
readonly source: 'row' | 'radio' | 'checkbox' | 'keyboard' | 'toggle-all';
}import type { NeuTreeTableSelectionOptions } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableSelectionOptions<T> = {
readonly mode: 'none';
} | {
readonly mode: 'single';
readonly indicator: 'none' | 'radio';
readonly selectOnRowClick: boolean;
readonly allowClear: boolean;
readonly isNodeDisabled?: (value: T) => boolean;
} | {
readonly mode: 'multiple' | 'checkbox';
readonly indicator: 'none' | 'checkbox';
readonly selectOnRowClick: boolean;
readonly modifier: 'replace' | 'platform' | 'toggle';
readonly range: boolean;
readonly propagation: 'none' | 'loaded-subtree';
readonly toggleAllScope: 'visible' | 'loaded';
readonly isNodeDisabled?: (value: T) => boolean;
};import type { NeuTreeSortDirection } from '@neural-ui/core/tree-table';
import type { NeuTreeTableSortOptions } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableSortOptions {
readonly defaultDirection: NeuTreeSortDirection;
readonly mode: 'single' | 'multiple';
readonly removable: boolean;
readonly resetRootPageOnChange: boolean;
}import type { NeuTreeTableStateContext } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableStateContext {
readonly retry: () => void;
}import type { NeuTreeTableTemplateDirective } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeTableTemplateDirective<C> {
readonly templateRef: TemplateRef<C>;
}import type { NeuTreeTableVirtualizationOptions } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeTableVirtualizationOptions = {
readonly enabled: false;
} | {
readonly enabled: true;
readonly itemSize: number;
readonly overscan: number;
};import type { NeuTreeTableKey } from '@neural-ui/core/tree-table';
import type { NeuTreeUnloadedRelation } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export interface NeuTreeUnloadedRelation<K extends NeuTreeTableKey> {
readonly appliedRequestId: number | null;
readonly keys: readonly K[];
readonly relationRevision: number;
readonly status: 'unloaded';
readonly total: number | null;
}import type { NeuTreeValueAccessor } from '@neural-ui/core/tree-table';
// Declaración pública (solo referencia)
export type NeuTreeValueAccessor<T> = (value: T) => unknown;Apariencia y tokens
Tokens específicos
Token | Efecto | Estado / variante | Valor / origen | Alternativa |
|---|---|---|---|---|
--neu-tree-table-cell-block | Relleno vertical base; compact usa el 60% y relaxed el 140%. | Celdas de tabla | 0.625remAlternativa del componente | Sin alias de token |
--neu-tree-table-cell-inline | Relleno horizontal de celda, independiente de la sangría del árbol. | Celdas de tabla | var(--neu-space-3)Alternativa del componente | --neu-space-3 |
--neu-tree-table-selected-background | Fondo de la fila seleccionada, con prioridad sobre las bandas alternas. | Fila seleccionada | color-mix(in srgb, currentColor 9%, transparent)Alternativa del componente | Sin alias de token |
--neu-tree-table-virtual-block-size | Altura del área virtualizada de la jerarquía. | Virtualización | 24remDeclaración raíz | Sin alias de token |
Tokens compartidos utilizados
Sobrescríbelos en un contenedor local para afectar a este ejemplo. Una modificación en :root afecta a los demás componentes que utilizan el mismo token.
Token | Efecto aquí | Otros efectos | Valor / alternativa |
|---|---|---|---|
--neu-border | Bordes normales de controles y celdas | Compartido con otros consumidores de Core; limita el cambio a un ámbito. | rgba(15, 23, 42, 0.08) |
--neu-focus-color | Contorno visible del foco de teclado | Compartido con otros consumidores de Core; limita el cambio a un ámbito. | var(--neu-primary) |
--neu-surface | Superficie principal del campo, cabecera o control | Compartido con otros consumidores de Core; limita el cambio a un ámbito. | #ffffff |
--neu-surface-2 | Superficies secundarias y filas alternas | Compartido con otros consumidores de Core; limita el cambio a un ámbito. | #f1f5f9 |
--neu-text | Color del texto principal y de los iconos que lo heredan | Compartido con otros consumidores de Core; limita el cambio a un ámbito. | #0f172a |
--neu-text-muted | Etiquetas secundarias y contenido de ayuda | Compartido con otros consumidores de Core; limita el cambio a un ámbito. | #475569 |
--neu-space-1 | Separación entre contenido y controles | Compartido con otros consumidores de Core; limita el cambio a un ámbito. | 0.25rem |
--neu-space-3 | Separación entre contenido y controles | Compartido con otros consumidores de Core; limita el cambio a un ámbito. | 0.75rem |