index.js 6.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160
  1. import _defineProperty from "@babel/runtime/helpers/esm/defineProperty";
  2. import _objectSpread from "@babel/runtime/helpers/esm/objectSpread2";
  3. import _toConsumableArray from "@babel/runtime/helpers/esm/toConsumableArray";
  4. import _objectWithoutProperties from "@babel/runtime/helpers/esm/objectWithoutProperties";
  5. var _excluded = ["className", "noData", "columns", "flattenColumns", "colWidths", "colGroup", "columCount", "stickyOffsets", "direction", "fixHeader", "stickyTopOffset", "stickyBottomOffset", "stickyClassName", "scrollX", "tableLayout", "onScroll", "children"];
  6. import { useContext } from '@rc-component/context';
  7. import classNames from 'classnames';
  8. import { fillRef } from "rc-util/es/ref";
  9. import * as React from 'react';
  10. import { useMemo } from 'react';
  11. import ColGroup from "../ColGroup";
  12. import TableContext from "../context/TableContext";
  13. import devRenderTimes from "../hooks/useRenderTimes";
  14. function useColumnWidth(colWidths, columCount) {
  15. return useMemo(function () {
  16. var cloneColumns = [];
  17. for (var i = 0; i < columCount; i += 1) {
  18. var val = colWidths[i];
  19. if (val !== undefined) {
  20. cloneColumns[i] = val;
  21. } else {
  22. return null;
  23. }
  24. }
  25. return cloneColumns;
  26. }, [colWidths.join('_'), columCount]);
  27. }
  28. var FixedHolder = /*#__PURE__*/React.forwardRef(function (props, ref) {
  29. if (process.env.NODE_ENV !== 'production') {
  30. devRenderTimes(props);
  31. }
  32. var className = props.className,
  33. noData = props.noData,
  34. columns = props.columns,
  35. flattenColumns = props.flattenColumns,
  36. colWidths = props.colWidths,
  37. colGroup = props.colGroup,
  38. columCount = props.columCount,
  39. stickyOffsets = props.stickyOffsets,
  40. direction = props.direction,
  41. fixHeader = props.fixHeader,
  42. stickyTopOffset = props.stickyTopOffset,
  43. stickyBottomOffset = props.stickyBottomOffset,
  44. stickyClassName = props.stickyClassName,
  45. scrollX = props.scrollX,
  46. _props$tableLayout = props.tableLayout,
  47. tableLayout = _props$tableLayout === void 0 ? 'fixed' : _props$tableLayout,
  48. onScroll = props.onScroll,
  49. children = props.children,
  50. restProps = _objectWithoutProperties(props, _excluded);
  51. var _useContext = useContext(TableContext, ['prefixCls', 'scrollbarSize', 'isSticky', 'getComponent']),
  52. prefixCls = _useContext.prefixCls,
  53. scrollbarSize = _useContext.scrollbarSize,
  54. isSticky = _useContext.isSticky,
  55. getComponent = _useContext.getComponent;
  56. var TableComponent = getComponent(['header', 'table'], 'table');
  57. var combinationScrollBarSize = isSticky && !fixHeader ? 0 : scrollbarSize;
  58. // Pass wheel to scroll event
  59. var scrollRef = React.useRef(null);
  60. var setScrollRef = React.useCallback(function (element) {
  61. fillRef(ref, element);
  62. fillRef(scrollRef, element);
  63. }, []);
  64. React.useEffect(function () {
  65. function onWheel(e) {
  66. var _ref = e,
  67. currentTarget = _ref.currentTarget,
  68. deltaX = _ref.deltaX;
  69. if (deltaX) {
  70. onScroll({
  71. currentTarget: currentTarget,
  72. scrollLeft: currentTarget.scrollLeft + deltaX
  73. });
  74. e.preventDefault();
  75. }
  76. }
  77. var scrollEle = scrollRef.current;
  78. scrollEle === null || scrollEle === void 0 || scrollEle.addEventListener('wheel', onWheel, {
  79. passive: false
  80. });
  81. return function () {
  82. scrollEle === null || scrollEle === void 0 || scrollEle.removeEventListener('wheel', onWheel);
  83. };
  84. }, []);
  85. // Add scrollbar column
  86. var lastColumn = flattenColumns[flattenColumns.length - 1];
  87. var ScrollBarColumn = {
  88. fixed: lastColumn ? lastColumn.fixed : null,
  89. scrollbar: true,
  90. onHeaderCell: function onHeaderCell() {
  91. return {
  92. className: "".concat(prefixCls, "-cell-scrollbar")
  93. };
  94. }
  95. };
  96. var columnsWithScrollbar = useMemo(function () {
  97. return combinationScrollBarSize ? [].concat(_toConsumableArray(columns), [ScrollBarColumn]) : columns;
  98. }, [combinationScrollBarSize, columns]);
  99. var flattenColumnsWithScrollbar = useMemo(function () {
  100. return combinationScrollBarSize ? [].concat(_toConsumableArray(flattenColumns), [ScrollBarColumn]) : flattenColumns;
  101. }, [combinationScrollBarSize, flattenColumns]);
  102. // Calculate the sticky offsets
  103. var headerStickyOffsets = useMemo(function () {
  104. var right = stickyOffsets.right,
  105. left = stickyOffsets.left;
  106. return _objectSpread(_objectSpread({}, stickyOffsets), {}, {
  107. left: direction === 'rtl' ? [].concat(_toConsumableArray(left.map(function (width) {
  108. return width + combinationScrollBarSize;
  109. })), [0]) : left,
  110. right: direction === 'rtl' ? right : [].concat(_toConsumableArray(right.map(function (width) {
  111. return width + combinationScrollBarSize;
  112. })), [0]),
  113. isSticky: isSticky
  114. });
  115. }, [combinationScrollBarSize, stickyOffsets, isSticky]);
  116. var mergedColumnWidth = useColumnWidth(colWidths, columCount);
  117. var isColGroupEmpty = useMemo(function () {
  118. // use original ColGroup if no data or no calculated column width, otherwise use calculated column width
  119. // Return original colGroup if no data, or mergedColumnWidth is empty, or all widths are falsy
  120. var noWidth = !mergedColumnWidth || !mergedColumnWidth.length || mergedColumnWidth.every(function (w) {
  121. return !w;
  122. });
  123. return noData || noWidth;
  124. }, [noData, mergedColumnWidth]);
  125. return /*#__PURE__*/React.createElement("div", {
  126. style: _objectSpread({
  127. overflow: 'hidden'
  128. }, isSticky ? {
  129. top: stickyTopOffset,
  130. bottom: stickyBottomOffset
  131. } : {}),
  132. ref: setScrollRef,
  133. className: classNames(className, _defineProperty({}, stickyClassName, !!stickyClassName))
  134. }, /*#__PURE__*/React.createElement(TableComponent, {
  135. style: {
  136. tableLayout: tableLayout,
  137. minWidth: '100%',
  138. // https://github.com/ant-design/ant-design/issues/54894
  139. width: scrollX
  140. }
  141. }, isColGroupEmpty ? colGroup : /*#__PURE__*/React.createElement(ColGroup, {
  142. colWidths: [].concat(_toConsumableArray(mergedColumnWidth), [combinationScrollBarSize]),
  143. columCount: columCount + 1,
  144. columns: flattenColumnsWithScrollbar
  145. }), children(_objectSpread(_objectSpread({}, restProps), {}, {
  146. stickyOffsets: headerStickyOffsets,
  147. columns: columnsWithScrollbar,
  148. flattenColumns: flattenColumnsWithScrollbar
  149. }))));
  150. });
  151. if (process.env.NODE_ENV !== 'production') {
  152. FixedHolder.displayName = 'FixedHolder';
  153. }
  154. /** Return a table in div as fixed element which contains sticky info */
  155. // export default responseImmutable(FixedHolder);
  156. export default /*#__PURE__*/React.memo(FixedHolder);