@kdcloudjs/table 1.2.2-canary.12 → 1.2.2-canary.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -28,6 +28,7 @@ import TableHeader from './header';
28
28
  import { getRichVisibleRectsStream } from './helpers/getRichVisibleRectsStream';
29
29
  import { getFullRenderRange, makeRowHeightManager } from './helpers/rowHeightManager';
30
30
  import { TableDOMHelper } from './helpers/TableDOMUtils';
31
+ import { FastScrollManager } from './helpers/FastScrollManager';
31
32
  import { HtmlTable } from './html-table';
32
33
  import Loading from './loading';
33
34
  import { Classes, LOCK_SHADOW_PADDING, StyledArtTableWrapper } from './styles';
@@ -35,6 +36,7 @@ import GlobalStyleComponent from './globalStyleComponent';
35
36
  import { addResizeObserver, getScrollbarSize, OVERSCAN_SIZE, shallowEqual, STYLED_REF_PROP, sum, syncScrollLeft, throttledWindowResize$, getTableScrollFooterDOM, getTableScrollHeaderDOM, cssPolifill, swapRTLDirection } from './utils';
36
37
  import { console, browserType, isStickyUIDegrade } from '../utils';
37
38
  import getTableRenderTemplate from './renderTemplates';
39
+ import { TopBlank, BottomBlank } from './BlankComponent';
38
40
  var propsDotEmptyContentDeprecatedWarned = false;
39
41
  function warnPropsDotEmptyContentIsDeprecated() {
40
42
  if (!propsDotEmptyContentDeprecatedWarned) {
@@ -53,6 +55,9 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
53
55
  _this.artTableWrapperRef = /*#__PURE__*/React.createRef();
54
56
  _this.hasScrollY = false;
55
57
  _this.offsetY = 0;
58
+ // Blank组件的引用,用于快速滚动时直接更新
59
+ _this.topBlankRef = /*#__PURE__*/React.createRef();
60
+ _this.bottomBlankRef = /*#__PURE__*/React.createRef();
56
61
  _this.handleRowMouseEnter = function (e) {
57
62
  var nodeList = _this.domHelper.getRowNodeListByEvent(e);
58
63
  nodeList && nodeList.forEach(function (node) {
@@ -72,8 +77,7 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
72
77
  getRowProps = _this$props.getRowProps,
73
78
  primaryKey = _this$props.primaryKey,
74
79
  isLoading = _this$props.isLoading,
75
- emptyCellHeight = _this$props.emptyCellHeight,
76
- footerDataSource = _this$props.footerDataSource;
80
+ emptyCellHeight = _this$props.emptyCellHeight;
77
81
  var tableBodyClassName = cx(Classes.tableBody, Classes.horizontalScrollContainer);
78
82
  // 低版本Edge浏览器下也会出现双滚动条,这里设置overflow: 'hidden',先去掉edge的方向键控制滚动条的功能
79
83
  var virtualStyle = browserType.isIE || browserType.isEdge ? {
@@ -123,12 +127,9 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
123
127
  className: Classes.virtual,
124
128
  tabIndex: -1,
125
129
  style: virtualStyle
126
- }, topBlank > 0 && /*#__PURE__*/React.createElement("div", {
127
- key: "top-blank",
128
- className: cx(Classes.virtualBlank, 'top'),
129
- style: {
130
- height: topBlank
131
- }
130
+ }, /*#__PURE__*/React.createElement(TopBlank, {
131
+ ref: _this.topBlankRef,
132
+ height: topBlank
132
133
  }), /*#__PURE__*/React.createElement(HtmlTable, {
133
134
  tbodyHtmlTag: "tbody",
134
135
  getRowProps: getRowProps,
@@ -141,12 +142,9 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
141
142
  limit: bottomIndex,
142
143
  last: dataSource.length - 1
143
144
  }
144
- }), bottomBlank > 0 && /*#__PURE__*/React.createElement("div", {
145
- key: "bottom-blank",
146
- className: cx(Classes.virtualBlank, 'bottom'),
147
- style: {
148
- height: bottomBlank
149
- }
145
+ }), /*#__PURE__*/React.createElement(BottomBlank, {
146
+ ref: _this.bottomBlankRef,
147
+ height: bottomBlank
150
148
  })));
151
149
  };
152
150
  _this.state = {
@@ -161,6 +159,26 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
161
159
  maxRenderHeight: 600,
162
160
  maxRenderWidth: 800
163
161
  };
162
+ // 初始化快速滚动管理器
163
+ var fastScrollCallbacks = {
164
+ onFastScrollStart: function onFastScrollStart(renderData) {
165
+ _this.setState({
166
+ previousRenderData: renderData
167
+ });
168
+ },
169
+ onFastScrollEnd: function onFastScrollEnd(scrollData) {
170
+ _this.setState({
171
+ previousRenderData: undefined,
172
+ offsetY: scrollData.offsetY,
173
+ maxRenderHeight: scrollData.maxRenderHeight,
174
+ maxRenderWidth: scrollData.maxRenderWidth
175
+ });
176
+ },
177
+ getCurrentRenderRange: function getCurrentRenderRange(offsetY, maxRenderHeight, dataLength) {
178
+ return _this.rowHeightManager.getRenderRange(offsetY, maxRenderHeight, dataLength);
179
+ }
180
+ };
181
+ _this.fastScrollManager = new FastScrollManager(fastScrollCallbacks);
164
182
  return _this;
165
183
  }
166
184
  /** @deprecated BaseTable.getDoms() 已经过时,请勿调用 */
@@ -282,7 +300,6 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
282
300
  }, {
283
301
  key: "syncHorizontalScroll",
284
302
  value: function syncHorizontalScroll(x) {
285
- var direction = this.props.direction;
286
303
  var _x = Math.abs(x);
287
304
  this.updateOffsetX(_x);
288
305
  var flat = _flatInstanceProperty(this.lastInfo);
@@ -310,11 +327,18 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
310
327
  }, {
311
328
  key: "getVerticalRenderRange",
312
329
  value: function getVerticalRenderRange(useVirtual) {
313
- var dataSource = this.props.dataSource;
330
+ var _this$props4 = this.props,
331
+ dataSource = _this$props4.dataSource,
332
+ isLowPerformance = _this$props4.isLowPerformance;
314
333
  var _this$state = this.state,
315
334
  offsetY = _this$state.offsetY,
316
- maxRenderHeight = _this$state.maxRenderHeight;
335
+ maxRenderHeight = _this$state.maxRenderHeight,
336
+ previousRenderData = _this$state.previousRenderData;
317
337
  var rowCount = dataSource.length;
338
+ // 只有在启用快速滚动时才使用 FastScrollManager 的判断
339
+ if (isLowPerformance && this.fastScrollManager.getIsFastScrolling() && (previousRenderData === null || previousRenderData === void 0 ? void 0 : previousRenderData.verticalRenderRange)) {
340
+ return previousRenderData.verticalRenderRange;
341
+ }
318
342
  if (useVirtual.vertical) {
319
343
  return this.rowHeightManager.getRenderRange(offsetY, maxRenderHeight, rowCount);
320
344
  } else {
@@ -325,12 +349,12 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
325
349
  key: "renderTableFooter",
326
350
  value: function renderTableFooter(info) {
327
351
  // console.log('render footer')
328
- var _this$props4 = this.props,
329
- _this$props4$footerDa = _this$props4.footerDataSource,
330
- footerDataSource = _this$props4$footerDa === void 0 ? [] : _this$props4$footerDa,
331
- getRowProps = _this$props4.getRowProps,
332
- primaryKey = _this$props4.primaryKey,
333
- stickyBottom = _this$props4.stickyBottom;
352
+ var _this$props5 = this.props,
353
+ _this$props5$footerDa = _this$props5.footerDataSource,
354
+ footerDataSource = _this$props5$footerDa === void 0 ? [] : _this$props5$footerDa,
355
+ getRowProps = _this$props5.getRowProps,
356
+ primaryKey = _this$props5.primaryKey,
357
+ stickyBottom = _this$props5.stickyBottom;
334
358
  var stickyRightOffset = this.hasScrollY ? this.getScrollBarWidth() : 0;
335
359
  var renderFooter = getTableRenderTemplate('footer');
336
360
  if (typeof renderFooter === 'function') {
@@ -392,9 +416,9 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
392
416
  key: "renderStickyScroll",
393
417
  value: function renderStickyScroll(info) {
394
418
  // console.log('render stickyscroll')
395
- var _this$props5 = this.props,
396
- hasStickyScroll = _this$props5.hasStickyScroll,
397
- stickyBottom = _this$props5.stickyBottom;
419
+ var _this$props6 = this.props,
420
+ hasStickyScroll = _this$props6.hasStickyScroll,
421
+ stickyBottom = _this$props6.stickyBottom;
398
422
  var hasScroll = this.state.hasScroll;
399
423
  var isScroll = hasStickyScroll && hasScroll;
400
424
  var stickyScrollContainerStyle = this.getStickyScrollContainerStyle();
@@ -431,9 +455,9 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
431
455
  }, {
432
456
  key: "getStickyScrollContainerStyle",
433
457
  value: function getStickyScrollContainerStyle() {
434
- var _this$props6 = this.props,
435
- hasStickyScroll = _this$props6.hasStickyScroll,
436
- stickyScrollHeight = _this$props6.stickyScrollHeight;
458
+ var _this$props7 = this.props,
459
+ hasStickyScroll = _this$props7.hasStickyScroll,
460
+ stickyScrollHeight = _this$props7.stickyScrollHeight;
437
461
  var hasScroll = this.state.hasScroll;
438
462
  var isScroll = hasStickyScroll && hasScroll;
439
463
  var height = stickyScrollHeight === 'auto' ? this.getScrollBarWidth() : stickyScrollHeight;
@@ -451,21 +475,21 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
451
475
  // console.log('render table')
452
476
  var info = calculateRenderInfo(this);
453
477
  this.lastInfo = info;
454
- var _this$props7 = this.props,
455
- dataSource = _this$props7.dataSource,
456
- className = _this$props7.className,
457
- style = _this$props7.style,
458
- hasHeader = _this$props7.hasHeader,
459
- useOuterBorder = _this$props7.useOuterBorder,
460
- isStickyHead = _this$props7.isStickyHead,
461
- isStickyHeader = _this$props7.isStickyHeader,
462
- isStickyFooter = _this$props7.isStickyFooter,
463
- isLoading = _this$props7.isLoading,
464
- getTableProps = _this$props7.getTableProps,
465
- footerDataSource = _this$props7.footerDataSource,
466
- components = _this$props7.components,
467
- bordered = _this$props7.bordered,
468
- direction = _this$props7.direction;
478
+ var _this$props8 = this.props,
479
+ dataSource = _this$props8.dataSource,
480
+ className = _this$props8.className,
481
+ style = _this$props8.style,
482
+ hasHeader = _this$props8.hasHeader,
483
+ useOuterBorder = _this$props8.useOuterBorder,
484
+ isStickyHead = _this$props8.isStickyHead,
485
+ isStickyHeader = _this$props8.isStickyHeader,
486
+ isStickyFooter = _this$props8.isStickyFooter,
487
+ isLoading = _this$props8.isLoading,
488
+ getTableProps = _this$props8.getTableProps,
489
+ footerDataSource = _this$props8.footerDataSource,
490
+ components = _this$props8.components,
491
+ bordered = _this$props8.bordered,
492
+ direction = _this$props8.direction;
469
493
  info.direction = direction;
470
494
  var artTableWrapperClassName = cx(Classes.artTableWrapper, (_cx = {
471
495
  'use-outer-border': useOuterBorder,
@@ -506,10 +530,10 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
506
530
  this.initSubscriptions();
507
531
  this.didMountOrUpdate();
508
532
  // console.log('did mount end')
509
- var _this$props8 = this.props,
510
- cssVariables = _this$props8.cssVariables,
511
- enableCSSVariables = _this$props8.enableCSSVariables,
512
- bordered = _this$props8.bordered;
533
+ var _this$props9 = this.props,
534
+ cssVariables = _this$props9.cssVariables,
535
+ enableCSSVariables = _this$props9.enableCSSVariables,
536
+ bordered = _this$props9.bordered;
513
537
  cssPolifill({
514
538
  variables: cssVariables || {},
515
539
  enableCSSVariables: enableCSSVariables,
@@ -524,10 +548,10 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
524
548
  value: function componentDidUpdate(prevProps, prevState) {
525
549
  var _a;
526
550
  // console.log('did update start')
527
- var _this$props9 = this.props,
528
- cssVariables = _this$props9.cssVariables,
529
- enableCSSVariables = _this$props9.enableCSSVariables,
530
- bordered = _this$props9.bordered;
551
+ var _this$props10 = this.props,
552
+ cssVariables = _this$props10.cssVariables,
553
+ enableCSSVariables = _this$props10.enableCSSVariables,
554
+ bordered = _this$props10.bordered;
531
555
  if (!shallowEqual(prevProps === null || prevProps === void 0 ? void 0 : prevProps.cssVariables, (_a = this.props) === null || _a === void 0 ? void 0 : _a.cssVariables)) {
532
556
  cssPolifill({
533
557
  variables: cssVariables || {},
@@ -543,10 +567,13 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
543
567
  }, {
544
568
  key: "didMountOrUpdate",
545
569
  value: function didMountOrUpdate(prevProps, prevState) {
546
- this.syncHorizontalScrollFromTableBody();
547
- this.updateStickyScroll();
548
- this.adjustNeedRenderLock();
549
- this.updateRowHeightManager();
570
+ var _this2 = this;
571
+ window.requestAnimationFrame(function () {
572
+ _this2.syncHorizontalScrollFromTableBody();
573
+ _this2.updateStickyScroll();
574
+ _this2.adjustNeedRenderLock();
575
+ _this2.updateRowHeightManager();
576
+ });
550
577
  this.updateScrollLeftWhenLayoutChanged(prevProps, prevState);
551
578
  }
552
579
  }, {
@@ -568,25 +595,25 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
568
595
  }, {
569
596
  key: "initSubscriptions",
570
597
  value: function initSubscriptions() {
571
- var _this2 = this;
598
+ var _this3 = this;
572
599
  var _this$domHelper2 = this.domHelper,
573
600
  virtual = _this$domHelper2.virtual,
574
601
  stickyScroll = _this$domHelper2.stickyScroll;
575
602
  this.rootSubscription.add(throttledWindowResize$.subscribe(function () {
576
- _this2.updateStickyScroll();
577
- _this2.adjustNeedRenderLock();
603
+ _this3.updateStickyScroll();
604
+ _this3.adjustNeedRenderLock();
578
605
  }));
579
606
  this.resizeSubject.pipe(op.debounceTime(100)).subscribe(function () {
580
607
  var _a, _b;
581
- (_b = (_a = _this2.props).setTableWidth) === null || _b === void 0 ? void 0 : _b.call(_a, _this2.domHelper.tableBody.clientWidth);
608
+ (_b = (_a = _this3.props).setTableWidth) === null || _b === void 0 ? void 0 : _b.call(_a, _this3.domHelper.tableBody.clientWidth);
582
609
  });
583
610
  var handleTableWrapperResize = function handleTableWrapperResize() {
584
- _this2.resizeSubject.next();
611
+ _this3.resizeSubject.next();
585
612
  };
586
613
  this.resizeObserver = addResizeObserver(this.domHelper.artTableWrapper, handleTableWrapperResize);
587
614
  // 滚动同步
588
615
  this.rootSubscription.add(syncScrollLeft([getTableScrollHeaderDOM(this.domHelper), virtual, getTableScrollFooterDOM(this.domHelper), stickyScroll], function (scrollLeft) {
589
- _this2.syncHorizontalScroll(scrollLeft);
616
+ _this3.syncHorizontalScroll(scrollLeft);
590
617
  }));
591
618
  var richVisibleRects$ = getRichVisibleRectsStream(this.domHelper.virtual, this.props$.pipe(op.skip(1), op.mapTo('structure-may-change')), this.props.virtualDebugLabel).pipe(op.shareReplay());
592
619
  // 每当可见部分发生变化的时候,调整 loading icon 的未知(如果 loading icon 存在的话)
@@ -600,7 +627,7 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
600
627
  }))]).subscribe(function (_ref3) {
601
628
  var _ref4 = _slicedToArray(_ref3, 1),
602
629
  clipRect = _ref4[0];
603
- var loadingIndicator = _this2.domHelper.getLoadingIndicator();
630
+ var loadingIndicator = _this3.domHelper.getLoadingIndicator();
604
631
  if (!loadingIndicator) {
605
632
  return;
606
633
  }
@@ -611,9 +638,9 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
611
638
  }));
612
639
  // 每当可见部分发生变化的时候,如果开启了虚拟滚动,则重新触发 render
613
640
  this.rootSubscription.add(richVisibleRects$.pipe(op.filter(function () {
614
- var _this2$lastInfo$useVi = _this2.lastInfo.useVirtual,
615
- horizontal = _this2$lastInfo$useVi.horizontal,
616
- vertical = _this2$lastInfo$useVi.vertical;
641
+ var _this3$lastInfo$useVi = _this3.lastInfo.useVirtual,
642
+ horizontal = _this3$lastInfo$useVi.horizontal,
643
+ vertical = _this3$lastInfo$useVi.vertical;
617
644
  return horizontal || vertical;
618
645
  }), op.map(function (_ref5) {
619
646
  var clipRect = _ref5.clipRect,
@@ -630,8 +657,29 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
630
657
  }
631
658
  // 因为 overscan 的存在,滚动较小的距离时不需要触发组件重渲染
632
659
  return Math.abs(x.maxRenderWidth - y.maxRenderWidth) < OVERSCAN_SIZE / 2 && Math.abs(x.maxRenderHeight - y.maxRenderHeight) < OVERSCAN_SIZE / 2 && Math.abs(x.offsetY - y.offsetY) < OVERSCAN_SIZE / 2;
660
+ }),
661
+ // 快速滚动检测和处理
662
+ op.tap(function (sizeAndOffset) {
663
+ // 只有在启用快速滚动时才使用 FastScrollManager 处理滚动事件
664
+ if (_this3.props.isLowPerformance) {
665
+ _this3.fastScrollManager.handleScrollEvent(sizeAndOffset, {
666
+ offsetY: _this3.state.offsetY,
667
+ maxRenderHeight: _this3.state.maxRenderHeight,
668
+ maxRenderWidth: _this3.state.maxRenderWidth
669
+ }, _this3.props.dataSource.length, _this3.domHelper.virtual.scrollHeight);
670
+ }
633
671
  })).subscribe(function (sizeAndOffset) {
634
- _this2.setState(sizeAndOffset);
672
+ var _a, _b;
673
+ // 正常滚动时也需要实时更新 blank 高度,确保缓慢滚动时的视觉连续性
674
+ var currentRange = _this3.rowHeightManager.getRenderRange(sizeAndOffset.offsetY, sizeAndOffset.maxRenderHeight, _this3.props.dataSource.length);
675
+ // 直接更新 DOM,避免等待下次渲染
676
+ (_a = _this3.topBlankRef.current) === null || _a === void 0 ? void 0 : _a.updateHeight(currentRange.topBlank);
677
+ (_b = _this3.bottomBlankRef.current) === null || _b === void 0 ? void 0 : _b.updateHeight(currentRange.bottomBlank);
678
+ // 只有在启用快速滚动时才检查快速滚动状态
679
+ if (_this3.props.isLowPerformance && _this3.fastScrollManager.getIsFastScrolling()) {
680
+ return;
681
+ }
682
+ _this3.setState(sizeAndOffset);
635
683
  }));
636
684
  this.rootSubscription.add(richVisibleRects$.pipe(op.map(function (_ref6) {
637
685
  var clipRect = _ref6.clipRect,
@@ -649,13 +697,13 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
649
697
  var _a;
650
698
  var offsetY = sizeAndOffset.offsetY,
651
699
  maxRenderHeight = sizeAndOffset.maxRenderHeight;
652
- var scrollDirection = offsetY - _this2.offsetY >= 0 ? 'down' : 'up';
653
- _this2.offsetY = offsetY;
654
- var rowCount = _this2.props.dataSource.length;
655
- var vertical = _this2.rowHeightManager.getRenderRange(offsetY, maxRenderHeight, rowCount);
700
+ var scrollDirection = offsetY - _this3.offsetY >= 0 ? 'down' : 'up';
701
+ _this3.offsetY = offsetY;
702
+ var rowCount = _this3.props.dataSource.length;
703
+ var vertical = _this3.rowHeightManager.getRenderRange(offsetY, maxRenderHeight, rowCount);
656
704
  var topIndex = vertical.topIndex,
657
705
  bottomIndex = vertical.bottomIndex;
658
- var blockSize = ((_a = _this2.props.scrollLoad) === null || _a === void 0 ? void 0 : _a.blockSize) || 200;
706
+ var blockSize = ((_a = _this3.props.scrollLoad) === null || _a === void 0 ? void 0 : _a.blockSize) || 200;
659
707
  var topBlockStartIndex = Math.floor(Math.max(topIndex - 1, 0) / blockSize) * blockSize;
660
708
  var bottomBlockStartIndex = Math.floor((bottomIndex + 1) / blockSize) * blockSize;
661
709
  return scrollDirection === 'down' ? [topBlockStartIndex, bottomBlockStartIndex] : [bottomBlockStartIndex, topBlockStartIndex];
@@ -670,7 +718,7 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
670
718
  // 过滤掉重复掉值
671
719
  op.distinctUntilChanged()).subscribe(function (startIndex) {
672
720
  var _a;
673
- (_a = _this2.props.scrollLoad) === null || _a === void 0 ? void 0 : _a.callback(startIndex);
721
+ (_a = _this3.props.scrollLoad) === null || _a === void 0 ? void 0 : _a.callback(startIndex);
674
722
  }));
675
723
  }
676
724
  }, {
@@ -680,6 +728,10 @@ export var BaseTable = /*#__PURE__*/function (_React$Component) {
680
728
  (_a = this.resizeObserver) === null || _a === void 0 ? void 0 : _a.disconnect();
681
729
  this.rootSubscription.unsubscribe();
682
730
  this.resizeSubject.unsubscribe();
731
+ // 只有在启用快速滚动时才清理快速滚动管理器
732
+ if (this.props.isLowPerformance) {
733
+ this.fastScrollManager.cleanup();
734
+ }
683
735
  }
684
736
  /** 更新 DOM 节点的引用,方便其他方法直接操作 DOM */
685
737
  }, {
@@ -774,6 +826,7 @@ BaseTable.defaultProps = {
774
826
  stickyScrollHeight: 'auto',
775
827
  useVirtual: 'auto',
776
828
  estimatedRowHeight: 48,
829
+ isLowPerformance: false,
777
830
  isLoading: false,
778
831
  components: {},
779
832
  getTableProps: noop,
@@ -0,0 +1,11 @@
1
+ import React from 'react';
2
+ interface BlankProps {
3
+ height: number;
4
+ className?: string;
5
+ }
6
+ export interface BlankRef {
7
+ updateHeight: (newHeight: number) => void;
8
+ }
9
+ export declare const TopBlank: React.MemoExoticComponent<React.ForwardRefExoticComponent<BlankProps & React.RefAttributes<BlankRef>>>;
10
+ export declare const BottomBlank: React.MemoExoticComponent<React.ForwardRefExoticComponent<BlankProps & React.RefAttributes<BlankRef>>>;
11
+ export {};
@@ -0,0 +1,75 @@
1
+ "use strict";
2
+
3
+ var _typeof = require("@babel/runtime-corejs3/helpers/typeof");
4
+ var _WeakMap = require("@babel/runtime-corejs3/core-js-stable/weak-map");
5
+ var _Object$getOwnPropertyDescriptor = require("@babel/runtime-corejs3/core-js-stable/object/get-own-property-descriptor");
6
+ var _interopRequireDefault = require("@babel/runtime-corejs3/helpers/interopRequireDefault");
7
+ Object.defineProperty(exports, "__esModule", {
8
+ value: true
9
+ });
10
+ exports.TopBlank = exports.BottomBlank = void 0;
11
+ var _slicedToArray2 = _interopRequireDefault(require("@babel/runtime-corejs3/helpers/slicedToArray"));
12
+ var _react = _interopRequireWildcard(require("react"));
13
+ var _classnames = _interopRequireDefault(require("classnames"));
14
+ var _styles = require("./styles");
15
+ function _getRequireWildcardCache(nodeInterop) { if (typeof _WeakMap !== "function") return null; var cacheBabelInterop = new _WeakMap(); var cacheNodeInterop = new _WeakMap(); return (_getRequireWildcardCache = function _getRequireWildcardCache(nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
16
+ function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || _typeof(obj) !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && _Object$getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? _Object$getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
17
+ var TopBlankComponent = /*#__PURE__*/(0, _react.forwardRef)(function (_ref, ref) {
18
+ var initialHeight = _ref.height;
19
+ var _useState = (0, _react.useState)(initialHeight),
20
+ _useState2 = (0, _slicedToArray2.default)(_useState, 2),
21
+ height = _useState2[0],
22
+ setHeight = _useState2[1];
23
+ (0, _react.useImperativeHandle)(ref, function () {
24
+ return {
25
+ updateHeight: function updateHeight(newHeight) {
26
+ if (height !== newHeight) {
27
+ setHeight(newHeight);
28
+ }
29
+ }
30
+ };
31
+ }, [height]);
32
+ return /*#__PURE__*/_react.default.createElement("div", {
33
+ style: {
34
+ height: height
35
+ }
36
+ });
37
+ });
38
+ TopBlankComponent.displayName = 'TopBlank';
39
+ var BottomBlankComponent = /*#__PURE__*/(0, _react.forwardRef)(function (_ref2, ref) {
40
+ var initialHeight = _ref2.height,
41
+ className = _ref2.className;
42
+ var _useState3 = (0, _react.useState)(initialHeight),
43
+ _useState4 = (0, _slicedToArray2.default)(_useState3, 2),
44
+ height = _useState4[0],
45
+ setHeight = _useState4[1];
46
+ (0, _react.useImperativeHandle)(ref, function () {
47
+ return {
48
+ updateHeight: function updateHeight(newHeight) {
49
+ if (height !== newHeight) {
50
+ setHeight(newHeight);
51
+ }
52
+ }
53
+ };
54
+ }, [height]);
55
+ if (height <= 0) {
56
+ return null;
57
+ }
58
+ return /*#__PURE__*/_react.default.createElement("div", {
59
+ key: "bottom-blank",
60
+ className: (0, _classnames.default)(_styles.Classes.virtualBlank, 'bottom', className),
61
+ style: {
62
+ height: height
63
+ }
64
+ });
65
+ });
66
+ BottomBlankComponent.displayName = 'BottomBlank';
67
+ // 使用 memo 优化,只有当 height 或 className 改变时才重新渲染
68
+ var TopBlank = /*#__PURE__*/(0, _react.memo)(TopBlankComponent, function (prevProps, nextProps) {
69
+ return prevProps.height === nextProps.height && prevProps.className === nextProps.className;
70
+ });
71
+ exports.TopBlank = TopBlank;
72
+ var BottomBlank = /*#__PURE__*/(0, _react.memo)(BottomBlankComponent, function (prevProps, nextProps) {
73
+ return prevProps.height === nextProps.height && prevProps.className === nextProps.className;
74
+ });
75
+ exports.BottomBlank = BottomBlank;
@@ -0,0 +1,96 @@
1
+ /**
2
+ * 快速滚动管理器
3
+ * 抽取 BaseTable 中的快速滚动相关逻辑
4
+ */
5
+ export interface FastScrollConfig {
6
+ /** 预渲染缓冲区大小,用于快速滚动判断 */
7
+ overscanSize?: number;
8
+ /** 快速滚动速度阈值 (像素/毫秒) */
9
+ velocityThreshold?: number;
10
+ /** 快速滚动距离倍数阈值 */
11
+ distanceMultiplier?: number;
12
+ /** 快速滚动结束等待时间 (毫秒) - 高速滚动 */
13
+ fastScrollEndDelayHigh?: number;
14
+ /** 快速滚动结束等待时间 (毫秒) - 普通滚动 */
15
+ fastScrollEndDelayNormal?: number;
16
+ /** 高速滚动速度阈值 (像素/毫秒) */
17
+ highVelocityThreshold?: number;
18
+ }
19
+ export interface FastScrollState {
20
+ lastScrollTime: number;
21
+ scrollVelocity: number;
22
+ lastOffsetY: number;
23
+ }
24
+ export interface ScrollEventData {
25
+ offsetY: number;
26
+ maxRenderHeight: number;
27
+ maxRenderWidth: number;
28
+ }
29
+ export interface VerticalRenderRange {
30
+ topIndex: number;
31
+ bottomIndex: number;
32
+ topBlank: number;
33
+ bottomBlank: number;
34
+ }
35
+ export interface FastScrollCallbacks {
36
+ onFastScrollStart: (renderData: {
37
+ offsetY: number;
38
+ maxRenderHeight: number;
39
+ maxRenderWidth: number;
40
+ verticalRenderRange: VerticalRenderRange;
41
+ }) => void;
42
+ onFastScrollEnd: (scrollData: ScrollEventData) => void;
43
+ getCurrentRenderRange: (offsetY: number, maxRenderHeight: number, dataLength: number) => VerticalRenderRange;
44
+ }
45
+ export declare class FastScrollManager {
46
+ private state;
47
+ private isFastScrolling;
48
+ private fastScrollEndTimer?;
49
+ private config;
50
+ private callbacks;
51
+ constructor(callbacks: FastScrollCallbacks, config?: FastScrollConfig);
52
+ /**
53
+ * 检测是否接近底部(剩余滚动距离少于两屏)
54
+ */
55
+ private isNearBottom;
56
+ /**
57
+ * 处理滚动事件 - 检测和处理快速滚动
58
+ */
59
+ handleScrollEvent(sizeAndOffset: ScrollEventData, currentState: {
60
+ offsetY: number;
61
+ maxRenderHeight: number;
62
+ maxRenderWidth: number;
63
+ }, dataLength: number, totalScrollHeight: number): void;
64
+ /**
65
+ * 开始快速滚动
66
+ */
67
+ private startFastScrolling;
68
+ /**
69
+ * 重置快速滚动结束定时器
70
+ */
71
+ private resetFastScrollEndTimer;
72
+ /**
73
+ * 结束快速滚动
74
+ */
75
+ private endFastScrolling;
76
+ /**
77
+ * 清理资源
78
+ */
79
+ cleanup(): void;
80
+ /**
81
+ * 获取当前是否处于快速滚动状态
82
+ */
83
+ getIsFastScrolling(): boolean;
84
+ /**
85
+ * 获取当前滚动速度
86
+ */
87
+ getScrollVelocity(): number;
88
+ /**
89
+ * 清理资源
90
+ */
91
+ destroy(): void;
92
+ /**
93
+ * 获取当前配置
94
+ */
95
+ getConfig(): Readonly<Required<FastScrollConfig>>;
96
+ }