123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150 |
- import { merge, clone as lodashClone, find, map } from 'lodash';
- import Logger from '@douyinfe/semi-foundation/utils/Logger';
- import { numbers } from '@douyinfe/semi-foundation/table/constants';
- import { cloneDeep } from '../_utils';
- import { TableComponents, Virtualized } from './interface';
- import { getColumnKey } from '@douyinfe/semi-foundation/table/utils';
- let scrollbarVerticalSize: number,
- scrollbarHorizontalSize: number;
- // Measure scrollbar width for padding body during modal show/hide
- const scrollbarMeasure = {
- position: 'absolute',
- top: '-9999px',
- width: '50px',
- height: '50px',
- };
- /**
- * @param {'vertical'|'horizontal'} [direction]
- * @returns {number}
- */
- export function measureScrollbar(direction = 'vertical') {
- if (typeof document === 'undefined' || typeof window === 'undefined') {
- return 0;
- }
- const isVertical = direction === 'vertical';
- if (isVertical && scrollbarVerticalSize) {
- return scrollbarVerticalSize;
- } else if (!isVertical && scrollbarHorizontalSize) {
- return scrollbarHorizontalSize;
- }
- const scrollDiv = document.createElement('div');
- Object.keys(scrollbarMeasure).forEach(scrollProp => {
- scrollDiv.style[scrollProp] = scrollbarMeasure[scrollProp];
- });
- // Append related overflow style
- if (isVertical) {
- scrollDiv.style.overflowY = 'scroll';
- } else {
- scrollDiv.style.overflowX = 'scroll';
- }
- document.body.appendChild(scrollDiv);
- let size = 0;
- if (isVertical) {
- // clientWidth is the inner width (excluding borders and scrollbars)
- // offsetWidth is the outer width (including padding and borders)
- size = scrollDiv.offsetWidth - scrollDiv.clientWidth;
- scrollbarVerticalSize = size;
- } else {
- size = scrollDiv.offsetHeight - scrollDiv.clientHeight;
- scrollbarHorizontalSize = size;
- }
- document.body.removeChild(scrollDiv);
- // console.log(size);
- return size;
- }
- export function amendTableWidth(tableWidth: number) {
- return typeof tableWidth === 'number' ?
- tableWidth -
- numbers.DEFAULT_CELL_PADDING_LEFT -
- numbers.DEFAULT_CELL_PADDING_RIGHT -
- numbers.DEFAULT_CELL_BORDER_WIDTH_LEFT -
- numbers.DEFAULT_CELL_BORDER_WIDTH_RIGHT -
- measureScrollbar('vertical') :
- undefined;
- }
- /**
- * The user can pass a component to define the rendering method of each level of the table
- * This function merges the components passed in by the user with the default components
- * @param {Object} components
- * @param {Boolean|Object} virtualized
- * @returns
- */
- export function mergeComponents(components: TableComponents, virtualized: Virtualized) {
- return merge(
- {},
- {
- table: 'table',
- header: {
- outer: 'table',
- wrapper: 'thead',
- row: 'tr',
- cell: 'th',
- },
- body: virtualized ?
- {
- outer: 'div',
- wrapper: 'div',
- row: 'div',
- cell: 'div',
- colgroup: {
- wrapper: 'div',
- col: 'div',
- },
- } :
- {
- outer: 'table',
- wrapper: 'tbody',
- row: 'tr',
- cell: 'td',
- colgroup: {
- wrapper: 'colgroup',
- col: 'col',
- },
- },
- footer: {
- wrapper: 'tfoot',
- row: 'tr',
- cell: 'td',
- },
- },
- components
- );
- }
- export const logger = new Logger('[@douyinfe/semi-ui Table]');
- export function mergeColumns(oldColumns: any[] = [], newColumns: any[] = [], keyPropNames: any[] = null, deep = true) {
- const finalColumns: any[] = [];
- const clone = deep ? cloneDeep : lodashClone;
- map(newColumns, newColumn => {
- newColumn = { ...newColumn };
- const key = getColumnKey(newColumn, keyPropNames);
- const oldColumn = key != null && find(oldColumns, item => getColumnKey(item, keyPropNames) === key);
- if (oldColumn) {
- finalColumns.push(
- clone({
- ...oldColumn,
- ...newColumn,
- })
- );
- } else {
- finalColumns.push(clone(newColumn));
- }
- });
- return finalColumns;
- }
- export { cloneDeep };
|