Skip to content

Commit

Permalink
make feature constructor functions that can accept generics
Browse files Browse the repository at this point in the history
  • Loading branch information
KevinVandy committed Jan 11, 2025
1 parent 963b69c commit 232c5ea
Show file tree
Hide file tree
Showing 27 changed files with 1,036 additions and 822 deletions.
148 changes: 148 additions & 0 deletions packages/angular-table/src/angularReactivityFeature.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,148 @@
import { computed, signal } from '@angular/core'
import { toComputed } from './proxy'
import type { Signal } from '@angular/core'
import type {
RowData,
Table,
TableFeature,
TableFeatures,
} from '@tanstack/table-core'

declare module '@tanstack/table-core' {
interface TableOptions_Plugins<
TFeatures extends TableFeatures,
TData extends RowData,
> extends TableOptions_AngularReactivity {}

interface Table_Plugins<
TFeatures extends TableFeatures,
TData extends RowData,
> extends Table_AngularReactivity<TFeatures, TData> {}
}

interface TableOptions_AngularReactivity {
enableExperimentalReactivity?: boolean
}

interface Table_AngularReactivity<
TFeatures extends TableFeatures,
TData extends RowData,
> {
_rootNotifier?: Signal<Table<TFeatures, TData>>
_setRootNotifier?: (signal: Signal<Table<TFeatures, TData>>) => void
}

interface AngularReactivityFeatureConstructors<
TFeatures extends TableFeatures,
TData extends RowData,
> {
TableOptions: TableOptions_AngularReactivity
Table: Table_AngularReactivity<TFeatures, TData>
}

export function constructAngularReactivityFeature<
TFeatures extends TableFeatures,
TData extends RowData,
>(): TableFeature<AngularReactivityFeatureConstructors<TFeatures, TData>> {
return {
getDefaultTableOptions(table) {
return { enableExperimentalReactivity: false }
},
constructTableAPIs: (table) => {
if (!table.options.enableExperimentalReactivity) {
return
}
const rootNotifier = signal<Signal<any> | null>(null)

table._rootNotifier = computed(() => rootNotifier()?.(), {
equal: () => false,
}) as any

table._setRootNotifier = (notifier) => {
rootNotifier.set(notifier)
}

setReactiveProps(table._rootNotifier!, table, {
skipProperty: skipBaseProperties,
})
},

constructCellAPIs(cell) {
if (
!cell._table.options.enableExperimentalReactivity ||
!cell._table._rootNotifier
) {
return
}
setReactiveProps(cell._table._rootNotifier, cell, {
skipProperty: skipBaseProperties,
})
},

constructColumnAPIs(column) {
if (
!column._table.options.enableExperimentalReactivity ||
!column._table._rootNotifier
) {
return
}
setReactiveProps(column._table._rootNotifier, column, {
skipProperty: skipBaseProperties,
})
},

constructHeaderAPIs(header) {
if (
!header._table.options.enableExperimentalReactivity ||
!header._table._rootNotifier
) {
return
}
setReactiveProps(header._table._rootNotifier, header, {
skipProperty: skipBaseProperties,
})
},

constructRowAPIs(row) {
if (
!row._table.options.enableExperimentalReactivity ||
!row._table._rootNotifier
) {
return
}
setReactiveProps(row._table._rootNotifier, row, {
skipProperty: skipBaseProperties,
})
},
}
}

export const angularReactivityFeature = constructAngularReactivityFeature()

function skipBaseProperties(property: string): boolean {
return property.endsWith('Handler') || !property.startsWith('get')
}

export function setReactiveProps(
notifier: Signal<Table<any, any>>,
obj: { [key: string]: any },
options: {
skipProperty: (property: string) => boolean
},
) {
const { skipProperty } = options
for (const property in obj) {
const value = obj[property]
if (typeof value !== 'function') {
continue
}
if (skipProperty(property)) {
continue
}
Object.defineProperty(obj, property, {
enumerable: true,
configurable: false,
value: toComputed(notifier, value, property),
})
}
}
8 changes: 4 additions & 4 deletions packages/angular-table/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
export * from '@tanstack/table-core'

export * from './angularReactivityFeature'
export * from './createTableHelper'
export * from './flex-render'
export * from './proxy'
export * from './lazy-signal-initializer'
export * from './injectTable'
export * from './createTableHelper'
export * from './reactivity'
export * from './lazy-signal-initializer'
export * from './proxy'
4 changes: 2 additions & 2 deletions packages/angular-table/src/injectTable.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import {
} from '@tanstack/table-core'
import { lazyInit } from './lazy-signal-initializer'
import { proxifyTable } from './proxy'
import { reactivityFeature } from './reactivity'
import { angularReactivityFeature } from './angularReactivityFeature'
import type {
RowData,
Table,
Expand All @@ -28,7 +28,7 @@ export function injectTable<
return {
...coreFeatures,
...options()._features,
reactivityFeature,
...angularReactivityFeature,
}
}

Expand Down
138 changes: 0 additions & 138 deletions packages/angular-table/src/reactivity.ts

This file was deleted.

59 changes: 37 additions & 22 deletions packages/table-core/src/core/cells/coreCellsFeature.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,29 +4,44 @@ import {
cell_getValue,
cell_renderValue,
} from './coreCellsFeature.utils'
import type { TableFeature } from '../../types/TableFeatures'
import type { RowData } from '../../types/type-utils'
import type { TableFeature, TableFeatures } from '../../types/TableFeatures'
// import type { Cell_Cell, TableOptions_Cell } from './coreCellsFeature.types'

export const coreCellsFeature: TableFeature<{
// Cell: Cell_Cell<TableFeatures, RowData, CellData>
interface CoreCellsFeatureConstructors<
TFeatures extends TableFeatures,
TData extends RowData,
> {
// Cell: Cell_Cell<TableFeatures, RowData>
// TableOptions: TableOptions_Cell
}> = {
feature: 'coreCellsFeature',
}

constructCellAPIs: (cell) => {
assignAPIs('coreCellsFeature', cell, [
{
fn: () => cell_getValue(cell),
fnName: 'cell_getValue',
},
{
fn: () => cell_renderValue(cell),
fnName: 'cell_renderValue',
},
{
fn: () => cell_getContext(cell),
fnName: 'cell_getContext',
memoDeps: () => [cell],
},
])
},
export function constructCoreCellsFeature<
TFeatures extends TableFeatures,
TData extends RowData,
>(): TableFeature<CoreCellsFeatureConstructors<TFeatures, TData>> {
return {
constructCellAPIs: (cell) => {
assignAPIs('coreCellsFeature', cell, [
{
fn: () => cell_getValue(cell),
fnName: 'cell_getValue',
},
{
fn: () => cell_renderValue(cell),
fnName: 'cell_renderValue',
},
{
fn: () => cell_getContext(cell),
fnName: 'cell_getContext',
memoDeps: () => [cell],
},
])
},
}
}

/**
* The Core Cells feature provides the core cell functionality.
*/
export const coreCellsFeature = constructCoreCellsFeature()
Loading

0 comments on commit 232c5ea

Please sign in to comment.