diff --git a/packages/vtable/examples/debug/issue-5117-auto-height-real-height.ts b/packages/vtable/examples/debug/issue-5117-auto-height-real-height.ts new file mode 100644 index 0000000000..c9384317c9 --- /dev/null +++ b/packages/vtable/examples/debug/issue-5117-auto-height-real-height.ts @@ -0,0 +1,70 @@ +import * as VTable from '../../src'; + +const CONTAINER_ID = 'vTable'; + +const records = Array.from({ length: 60 }, (_, index) => ({ + id: index + 1, + name: `row-${index + 1}`, + desc: + index % 3 === 0 + ? 'long text long text long text long text long text long text long text long text long text' + : 'short' +})); + +export function createTable() { + const container = document.getElementById(CONTAINER_ID)!; + document.getElementById('issue5117Toolbar')?.remove(); + container.style.width = '760px'; + container.style.height = '420px'; + + const toolbar = document.createElement('div'); + toolbar.id = 'issue5117Toolbar'; + toolbar.style.cssText = 'height: 48px; font-size: 12px; display: flex; gap: 12px; align-items: center;'; + toolbar.innerHTML = ` + + + `; + container.before(toolbar); + + const realHeights: Array = []; + const minRowHeight = 64; + const tableInstance = new VTable.ListTable({ + container, + records, + columns: [ + { field: 'id', title: 'ID', width: 80 }, + { field: 'name', title: 'Name', width: 120 }, + { + field: 'desc', + title: 'Description', + width: 280, + style: { + autoWrapText: true + } + } + ], + widthMode: 'standard', + heightMode: 'autoHeight', + customComputeRowHeight: ({ row, realHeight }) => { + realHeights[row] = realHeight; + return Math.max(realHeight ?? 0, minRowHeight); + } + }); + + const check = () => { + const bodyRow = tableInstance.columnHeaderLevelCount; + const realHeight = realHeights[bodyRow]; + const rowHeight = tableInstance.getRowHeight(bodyRow); + const pass = typeof realHeight === 'number' && rowHeight === Math.max(realHeight, minRowHeight); + const state = document.getElementById('issue5117State')!; + state.textContent = `${pass ? 'PASS' : 'FAIL'} | realHeight=${realHeight} rowHeight=${rowHeight}`; + return { pass, realHeight, rowHeight }; + }; + + document.getElementById('issue5117Check')!.addEventListener('click', check); + + window.tableInstance = tableInstance; + (window as any).issue5117Check = check; + + setTimeout(check, 0); +} diff --git a/packages/vtable/examples/menu.ts b/packages/vtable/examples/menu.ts index 13b2c16107..0287f9b0ec 100644 --- a/packages/vtable/examples/menu.ts +++ b/packages/vtable/examples/menu.ts @@ -34,6 +34,10 @@ export const menus = [ path: 'debug', name: 'issue-5114' }, + { + path: 'debug', + name: 'issue-5117-auto-height-real-height' + }, { path: 'debug', name: 'issue-5146' diff --git a/packages/vtable/src/scenegraph/layout/compute-row-height.ts b/packages/vtable/src/scenegraph/layout/compute-row-height.ts index 067ce3f2fb..dade83a49b 100644 --- a/packages/vtable/src/scenegraph/layout/compute-row-height.ts +++ b/packages/vtable/src/scenegraph/layout/compute-row-height.ts @@ -352,6 +352,16 @@ export function computeRowsHeight( } export function computeRowHeight(row: number, startCol: number, endCol: number, table: BaseTableAPI): number { + return computeRowHeightInternal(row, startCol, endCol, table, true); +} + +function computeRowHeightInternal( + row: number, + startCol: number, + endCol: number, + table: BaseTableAPI, + enableCustomCompute: boolean +): number { const isAllRowsAuto = table.isAutoRowHeight(row) || (table.heightMode === 'adaptive' && table.options.autoHeightInAdaptiveMode !== false); if (!isAllRowsAuto && table.getDefaultRowHeight(row) !== 'auto') { @@ -359,16 +369,32 @@ export function computeRowHeight(row: number, startCol: number, endCol: number, } let maxHeight; - if (table.options.customComputeRowHeight) { - const customRowHeight = table.options.customComputeRowHeight({ + if (enableCustomCompute && table.options.customComputeRowHeight) { + let realHeight: number; + let hasRealHeight = false; + const getRealHeight = () => { + if (!hasRealHeight) { + realHeight = computeRowHeightInternal(row, startCol, endCol, table, false); + hasRealHeight = true; + } + return realHeight; + }; + const computeArgs = { row, table + } as Parameters>[0]; + Object.defineProperty(computeArgs, 'realHeight', { + get: getRealHeight, + enumerable: false, + configurable: true }); + const customRowHeight = table.options.customComputeRowHeight(computeArgs); if (typeof customRowHeight === 'number') { return customRowHeight; - } else if (customRowHeight !== 'auto') { - return table.getDefaultRowHeight(row) as number; + } else if (customRowHeight === 'auto') { + return getRealHeight(); } + return table.getDefaultRowHeight(row) as number; } if (table.internalProps.rowHeightConfig) { const rowHeightConfig = table.internalProps.rowHeightConfig.find((item: { key: number }) => item.key === row); diff --git a/packages/vtable/src/ts-types/base-table.ts b/packages/vtable/src/ts-types/base-table.ts index 5433438e5c..f898856f68 100644 --- a/packages/vtable/src/ts-types/base-table.ts +++ b/packages/vtable/src/ts-types/base-table.ts @@ -694,7 +694,11 @@ export interface BaseTableConstructorOptions { renderOption?: any; formatCopyValue?: (value: string) => string; - customComputeRowHeight?: (computeArgs: { row: number; table: BaseTableAPI }) => number | 'auto' | undefined; + customComputeRowHeight?: (computeArgs: { + row: number; + table: BaseTableAPI; + realHeight?: number; + }) => number | 'auto' | undefined; /** 当表格出现抖动情况,请排查是否上层dom容器的宽高是小数引起的。如果不能保证是整数,请配置这个配置项为true */ tableSizeAntiJitter?: boolean;