@shoplflow/templates 0.2.46 → 0.2.47

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.
package/dist/index.cjs CHANGED
@@ -1,19 +1,22 @@
1
1
  'use strict';
2
2
 
3
3
  var base = require('@shoplflow/base');
4
- var React2 = require('react');
5
- var styled2 = require('@emotion/styled');
4
+ var React3 = require('react');
5
+ var styled3 = require('@emotion/styled');
6
6
  var shoplAssets = require('@shoplflow/shopl-assets');
7
7
  var jsxRuntime = require('react/jsx-runtime');
8
8
  var reactTable = require('@tanstack/react-table');
9
9
  var lodashEs = require('lodash-es');
10
- var reactVirtual = require('@tanstack/react-virtual');
10
+ var core = require('@dnd-kit/core');
11
+ var sortable = require('@dnd-kit/sortable');
11
12
  var utils = require('@shoplflow/utils');
13
+ var utilities = require('@dnd-kit/utilities');
14
+ var reactVirtual = require('@tanstack/react-virtual');
12
15
 
13
16
  function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }
14
17
 
15
- var React2__default = /*#__PURE__*/_interopDefault(React2);
16
- var styled2__default = /*#__PURE__*/_interopDefault(styled2);
18
+ var React3__default = /*#__PURE__*/_interopDefault(React3);
19
+ var styled3__default = /*#__PURE__*/_interopDefault(styled3);
17
20
 
18
21
  var __defProp = Object.defineProperty;
19
22
  var __defProps = Object.defineProperties;
@@ -46,6 +49,26 @@ var __objRest = (source, exclude) => {
46
49
  }
47
50
  return target;
48
51
  };
52
+ var __async = (__this, __arguments, generator) => {
53
+ return new Promise((resolve, reject) => {
54
+ var fulfilled = (value) => {
55
+ try {
56
+ step(generator.next(value));
57
+ } catch (e) {
58
+ reject(e);
59
+ }
60
+ };
61
+ var rejected = (value) => {
62
+ try {
63
+ step(generator.throw(value));
64
+ } catch (e) {
65
+ reject(e);
66
+ }
67
+ };
68
+ var step = (x) => x.done ? resolve(x.value) : Promise.resolve(x.value).then(fulfilled, rejected);
69
+ step((generator = generator.apply(__this, __arguments)).next());
70
+ });
71
+ };
49
72
  var getTypographyAndColor = (depth) => {
50
73
  switch (depth) {
51
74
  case 1:
@@ -57,16 +80,16 @@ var getTypographyAndColor = (depth) => {
57
80
  return { typography: "body1_700", color: "neutral500" };
58
81
  }
59
82
  };
60
- var StyledRequired = styled2__default.default.div`
83
+ var StyledRequired = styled3__default.default.div`
61
84
  color: ${base.colorTokens.red300};
62
85
  font-weight: 700;
63
86
  font-size: 14px;
64
87
  line-height: 18px;
65
88
  padding-top: 1px;
66
89
  `;
67
- var TitleGroupContext = React2.createContext(null);
90
+ var TitleGroupContext = React3.createContext(null);
68
91
  var useTitleGroupContext = () => {
69
- const context = React2.useContext(TitleGroupContext);
92
+ const context = React3.useContext(TitleGroupContext);
70
93
  return context != null ? context : { depth: 1 };
71
94
  };
72
95
  var TitleGroupHelpIcon = ({
@@ -126,16 +149,47 @@ TitleGroup.Header = Header;
126
149
  TitleGroup.Actions = Actions;
127
150
  TitleGroup.Description = Description;
128
151
  exports.TitleGroup = TitleGroup;
129
- var TableContext = React2.createContext(void 0);
152
+ var TableBtn = styled3__default.default.button`
153
+ display: flex;
154
+ align-items: center;
155
+ gap: 2px;
156
+ border: 1px solid ${base.colorTokens.neutral200};
157
+ border-radius: 4px;
158
+ padding: 4px;
159
+ background: ${base.colorTokens.neutral150};
160
+ color: ${base.colorTokens.neutral700};
161
+ cursor: ${({ onClick }) => onClick ? "pointer" : "default"};
162
+
163
+ &:hover {
164
+ background: ${({ disabled }) => disabled ? base.colorTokens.neutral150 : base.colorTokens.neutral200};
165
+ }
166
+
167
+ &:disabled {
168
+ cursor: not-allowed;
169
+ opacity: 0.5;
170
+ }
171
+ `;
172
+ exports.TableButton = (_a) => {
173
+ var _b = _a, { children, leftSource, rightSource } = _b, buttonProps = __objRest(_b, ["children", "leftSource", "rightSource"]);
174
+ return /* @__PURE__ */ jsxRuntime.jsxs(TableBtn, __spreadProps(__spreadValues({}, buttonProps), { children: [
175
+ leftSource && leftSource,
176
+ /* @__PURE__ */ jsxRuntime.jsx(base.Text, { typography: "body2_500", lineClamp: 2, children }),
177
+ rightSource && rightSource
178
+ ] }));
179
+ };
180
+ exports.TableBadge = ({ children }) => {
181
+ return /* @__PURE__ */ jsxRuntime.jsx(base.StackContainer, { radius: "borderRadius04", background: "neutral150", padding: "2px 4px", children: /* @__PURE__ */ jsxRuntime.jsx(base.Text, { typography: "body2_400", children }) });
182
+ };
183
+ var TableContext = React3.createContext(void 0);
130
184
  var useTable = () => {
131
- const context = React2.useContext(TableContext);
185
+ const context = React3.useContext(TableContext);
132
186
  if (!context) {
133
187
  throw new Error("useTable must be used within a TableProvider");
134
188
  }
135
189
  return context;
136
190
  };
137
191
  var TableProvider = TableContext.Provider;
138
- var TableContainer = styled2__default.default.div`
192
+ var TableContainer = styled3__default.default.div`
139
193
  border: ${({ hasToolbar }) => !hasToolbar && `1px solid ${base.colorTokens.neutral200}`};
140
194
  border-radius: 8px;
141
195
  background-color: ${base.colorTokens.neutral0};
@@ -169,134 +223,169 @@ var TableContainer = styled2__default.default.div`
169
223
  }
170
224
  }
171
225
  `;
172
- var TableHeader = styled2__default.default.thead`
173
- color: ${base.colorTokens.neutral400};
226
+ var TableHeader = styled3__default.default.thead`
174
227
  background-color: ${base.colorTokens.neutral100};
175
- font-size: 13px;
176
- font-weight: 400;
177
- line-height: 16px;
178
228
 
179
229
  tr {
180
230
  border-radius: 8px 8px 0 0;
181
231
  }
182
232
 
183
- th {
184
- position: relative;
185
- padding: 8px;
186
- height: 48px;
187
- min-height: 48px;
233
+ th:last-of-type::after {
234
+ display: none;
235
+ }
236
+ `;
237
+ var TableRow = styled3__default.default.tr`
238
+ &.clickable[data-has-pinned='true']:hover td {
188
239
  background-color: ${base.colorTokens.neutral100};
189
- vertical-align: middle;
190
- // 일반 컬럼의 border를 가상 요소로 처리
191
- &::after {
192
- content: '';
193
- position: absolute;
194
- top: 0;
195
- right: 0;
196
- height: 100%;
197
- width: 1px;
198
- background-color: ${base.colorTokens.neutral200};
199
- pointer-events: none;
200
- }
240
+ }
201
241
 
202
- // Fixed border for multi-column headers (colspan)
203
- &[colspan] {
204
- position: relative;
242
+ &.clickable:hover td {
243
+ background-color: ${base.colorTokens.neutral400_5};
244
+ cursor: pointer;
205
245
 
206
- // Ensure the right border is visible for colspan cells
246
+ /* neutral400_5 컬럼의 경우 호버 neutral150 컬러 적용 */
247
+ &[data-has-custom-style='true'] {
248
+ position: relative;
207
249
  &::after {
208
250
  content: '';
209
251
  position: absolute;
210
252
  top: 0;
211
253
  right: 0;
212
- height: 100%;
213
- width: 1px;
214
- background-color: ${base.colorTokens.neutral200};
215
- pointer-events: none;
216
- display: block;
217
- }
218
-
219
- // Add bottom border for spanning headers to make them visually distinct
220
- &::before {
221
- content: '';
222
- position: absolute;
223
- bottom: 0;
224
254
  left: 0;
255
+ bottom: 0;
256
+ height: 100%;
225
257
  width: 100%;
226
- height: 1px;
227
- background-color: ${base.colorTokens.neutral200};
258
+ background-color: ${base.colorTokens.neutral400_5};
228
259
  pointer-events: none;
229
260
  }
230
261
  }
262
+ }
263
+
264
+ &.clickable[data-has-pinned='true']:hover td[data-no-hover='true'] {
265
+ background-color: ${base.colorTokens.neutral100};
266
+ }
267
+
268
+ &:hover td[data-no-hover='true'] {
269
+ background-color: ${base.colorTokens.neutral400_5};
270
+ }
271
+ `;
272
+ var TableHead = styled3__default.default.th`
273
+ padding: ${({ sortable, filterable }) => sortable || filterable ? "4px" : "8px"};
274
+ height: 48px;
275
+ font-weight: ${base.fontWeightTokens.fontWeightRegular};
276
+ line-height: 16px;
277
+ font-size: 13px;
278
+ border-bottom: 1px solid ${base.colorTokens.neutral200};
279
+ border-right: 1px solid ${base.colorTokens.neutral200};
231
280
 
232
- // fixed 컬럼의 border를 별도의 가상 요소로 처리
233
- /* &[data-pinned='left']::before,
234
- &[data-pinned='right']::before {
281
+ position: relative;
282
+ background-color: ${base.colorTokens.neutral100};
283
+ vertical-align: middle;
284
+ // 고정 컬럼의 border를 가상 요소로 처리하여 스크롤 시 고정되도록 함
285
+ // borderRight: 'none'이 설정된 경우 ::after를 표시하지 않음
286
+ &[data-pinned='left']:not([data-last-left-pinned='true']):not([data-no-border-right='true']) {
287
+ border-right: none;
288
+ &::after {
235
289
  content: '';
236
290
  position: absolute;
237
291
  top: 0;
292
+ right: 0;
238
293
  height: 100%;
239
294
  width: 1px;
240
295
  background-color: ${base.colorTokens.neutral200};
241
296
  pointer-events: none;
242
- z-index: 5;
243
- } */
297
+ }
298
+ }
299
+
300
+ // Fixed border for multi-column headers (colspan)
301
+ &[colspan] {
302
+ position: relative;
244
303
 
245
- &[data-pinned='left']::before {
304
+ // Ensure the right border is visible for colspan cells
305
+ // *주석 처리한 이유: 가상 요소로 border를 처리하여 바디 셀에 있는 borderRight과 너비가 다름 (borderRight 스타일 새로 추가 및 last-left-pinned 스타일에는 borderRight 스타일 적용 X) 이슈티켓 SH-16534
306
+ /* &::after {
307
+ content: '';
308
+ position: absolute;
309
+ top: 0;
246
310
  right: 0;
247
- }
311
+ height: 100%;
312
+ width: 1px;
313
+ background-color: ${base.colorTokens.neutral200};
314
+ pointer-events: none;
315
+ display: block;
316
+ } */
248
317
 
249
- &[data-pinned='right']::before {
318
+ // Add bottom border for spanning headers to make them visually distinct
319
+ /* &::before {
320
+ content: '';
321
+ position: absolute;
322
+ bottom: 0;
250
323
  left: 0;
251
- }
252
- &:last-child {
253
- border-right: none;
254
- }
324
+ width: 100%;
325
+ height: 1px;
326
+ background-color: ${base.colorTokens.neutral200};
327
+ pointer-events: none;
328
+ } */
329
+ }
255
330
 
256
- &[data-last-left-pinned='true'] {
257
- &::after {
258
- content: '';
259
- position: absolute;
260
- top: 0;
261
- right: -4px; // border 바깥으로 이동
262
- height: 100%;
263
- width: 4px;
264
- pointer-events: none;
265
- z-index: 11;
266
- background: linear-gradient(to right, rgba(0, 0, 0, 0.1), transparent);
267
- }
268
- }
331
+ // fixed 컬럼의 border를 별도의 가상 요소로 처리
332
+ /* &[data-pinned='left']::before,
333
+ &[data-pinned='right']::before {
334
+ content: '';
335
+ position: absolute;
336
+ top: 0;
337
+ height: 100%;
338
+ width: 1px;
339
+ background-color: ${base.colorTokens.neutral200};
340
+ pointer-events: none;
341
+ z-index: 5;
342
+ } */
269
343
 
270
- &[data-first-right-pinned='true'] {
271
- &::before {
272
- content: '';
273
- position: absolute;
274
- top: 0;
275
- left: -5px; // border 바깥으로 이동
276
- height: 100%;
277
- width: 4px;
278
- pointer-events: none;
279
- z-index: 11;
280
- background: linear-gradient(to left, rgba(0, 0, 0, 0.1), transparent);
281
- }
282
- }
344
+ &[data-pinned='left']::before {
345
+ right: 0;
283
346
  }
284
347
 
285
- th:last-of-type::after {
286
- display: none;
348
+ &[data-pinned='right']::before {
349
+ left: 0;
287
350
  }
288
- `;
289
- var TableRow = styled2__default.default.tr`
290
- &.clickable:hover td {
291
- background-color: ${base.colorTokens.neutral400_5};
292
- cursor: pointer;
351
+ &:last-child {
352
+ border-right: none;
353
+
354
+ /* &[data-first-right-pinned='true'] {
355
+ border-bottom: 1px solid ${base.colorTokens.neutral200};
356
+ } */
293
357
  }
294
358
 
295
- &:hover td[data-no-hover='true'] {
296
- background-color: ${base.colorTokens.neutral400_5};
359
+ &[data-last-left-pinned='true'] {
360
+ /* //!고정 컬럼은 borderRight 스타일 적용 X */
361
+ border-right: none;
362
+ &::after {
363
+ content: '';
364
+ position: absolute;
365
+ top: 0;
366
+ right: -4px; // border 바깥으로 이동
367
+ height: 100%;
368
+ width: 4px;
369
+ pointer-events: none;
370
+ z-index: 11;
371
+ background: linear-gradient(to right, rgba(0, 0, 0, 0.1), transparent);
372
+ }
297
373
  }
298
- `;
299
- var TableHead = styled2__default.default.th`
374
+
375
+ &[data-first-right-pinned='true'] {
376
+ &::before {
377
+ content: '';
378
+ position: absolute;
379
+ top: 0;
380
+ left: -5px; // border 바깥으로 이동
381
+ height: 100%;
382
+ width: 4px;
383
+ pointer-events: none;
384
+ z-index: 11;
385
+ background: linear-gradient(to left, rgba(0, 0, 0, 0.1), transparent);
386
+ }
387
+ }
388
+
300
389
  .table-head[data-filter-open='true'] {
301
390
  background-color: black;
302
391
  }
@@ -304,7 +393,7 @@ var TableHead = styled2__default.default.th`
304
393
  color: ${base.colorTokens.neutral400};
305
394
  }
306
395
  `;
307
- var TableRootContainer = styled2__default.default.div`
396
+ var TableRootContainer = styled3__default.default.div`
308
397
  -ms-overflow-style: none; /* IE and Edge */
309
398
  scrollbar-width: none; /* Firefox */
310
399
  border: ${({ hasFilterBar, hasToolbar }) => hasFilterBar && !hasToolbar && `1px solid ${base.colorTokens.neutral200}`};
@@ -314,9 +403,9 @@ var TableRootContainer = styled2__default.default.div`
314
403
  display: none; /* Chrome, Safari, Opera*/
315
404
  }
316
405
  `;
317
- var HeaderTableContainer = styled2__default.default.div`
406
+ var HeaderTableContainer = styled3__default.default.div`
318
407
  width: 100%;
319
- z-index: 15;
408
+ z-index: 12;
320
409
  position: ${({ isSticky }) => isSticky ? "sticky" : ""};
321
410
  top: ${({ stickyHeaderMarginTop }) => stickyHeaderMarginTop}px;
322
411
  overflow-x: hidden;
@@ -329,12 +418,12 @@ var HeaderTableContainer = styled2__default.default.div`
329
418
  display: none; /* Chrome, Safari, Opera*/
330
419
  }
331
420
  `;
332
- var BodyTableContainer = styled2__default.default.div`
421
+ var BodyTableContainer = styled3__default.default.div`
333
422
  width: 100%;
334
423
  overflow-x: scroll;
335
424
  -ms-overflow-style: none; /* IE and Edge */
336
425
  scrollbar-width: none; /* Firefox */
337
- border-radius: ${({ hasPagination }) => hasPagination ? "0 0 8px 8px" : "0"};
426
+ border-radius: ${({ hasPagination, hasFooter }) => hasPagination || hasFooter ? "0" : "0 0 8px 8px"};
338
427
 
339
428
  opacity: ${({ isFetching }) => isFetching && 0.7};
340
429
  pointer-events: ${({ isFetching }) => isFetching && "none"};
@@ -342,7 +431,91 @@ var BodyTableContainer = styled2__default.default.div`
342
431
  display: none; /* Chrome, Safari, Opera*/
343
432
  }
344
433
  `;
345
- var TableCell = styled2__default.default.td`
434
+ var FooterTableContainer = styled3__default.default.div`
435
+ width: 100%;
436
+ z-index: 11;
437
+ position: ${({ isSticky }) => isSticky ? "sticky" : ""};
438
+ bottom: 0;
439
+ overflow-x: hidden;
440
+ border-radius: ${({ hasPagination, hasHeader }) => {
441
+ if (hasPagination)
442
+ return "0";
443
+ if (hasHeader)
444
+ return "0 0 8px 8px";
445
+ return "0 0 8px 8px";
446
+ }};
447
+
448
+ -ms-overflow-style: none; /* IE and Edge */
449
+ scrollbar-width: none; /* Firefox */
450
+
451
+ &::-webkit-scrollbar {
452
+ display: none; /* Chrome, Safari, Opera*/
453
+ }
454
+ `;
455
+ var TableFooter = styled3__default.default.tfoot`
456
+ color: ${base.colorTokens.neutral400};
457
+ ${base.typographyTokens.body2_400};
458
+ border-top: ${`1px solid ${base.colorTokens.neutral200}`};
459
+
460
+ tr {
461
+ border-radius: 0 0 8px 8px;
462
+ }
463
+
464
+ td:last-of-type::after {
465
+ display: none;
466
+ }
467
+ `;
468
+ var TableFoot = styled3__default.default.td`
469
+ padding: ${({ sortable, filterable }) => sortable || filterable ? "4px" : "8px"};
470
+ height: 48px;
471
+ min-height: 48px;
472
+ font-weight: ${base.fontWeightTokens.fontWeightRegular};
473
+ line-height: 16px;
474
+ font-size: 13px;
475
+
476
+ position: relative;
477
+ vertical-align: middle;
478
+
479
+ &[data-pinned='left']::before {
480
+ right: 0;
481
+ }
482
+
483
+ &[data-pinned='right']::before {
484
+ left: 0;
485
+ }
486
+ &:last-child {
487
+ border-right: none;
488
+ }
489
+
490
+ &[data-last-left-pinned='true'] {
491
+ &::after {
492
+ content: '';
493
+ position: absolute;
494
+ top: 0;
495
+ right: -4px; // border 바깥으로 이동
496
+ height: 100%;
497
+ width: 4px;
498
+ pointer-events: none;
499
+ z-index: 11;
500
+ background: linear-gradient(to right, rgba(0, 0, 0, 0.1), transparent);
501
+ }
502
+ }
503
+
504
+ &[data-first-right-pinned='true'] {
505
+ &::before {
506
+ content: '';
507
+ position: absolute;
508
+ top: 0;
509
+ left: -5px; // border 바깥으로 이동
510
+ height: 100%;
511
+ width: 4px;
512
+ pointer-events: none;
513
+ z-index: 11;
514
+ background: linear-gradient(to left, rgba(0, 0, 0, 0.1), transparent);
515
+ }
516
+ }
517
+ `;
518
+ var TableCell = styled3__default.default.td`
346
519
  position: relative;
347
520
  padding: 8px;
348
521
  vertical-align: middle;
@@ -380,7 +553,7 @@ var TableCell = styled2__default.default.td`
380
553
  }
381
554
  }
382
555
  `;
383
- var TableBody = styled2__default.default.tbody`
556
+ var TableBody = styled3__default.default.tbody`
384
557
  color: ${base.colorTokens.neutral700};
385
558
  font-size: 14px;
386
559
  position: relative;
@@ -393,10 +566,6 @@ var TableBody = styled2__default.default.tbody`
393
566
  border-bottom: ${({ innerBorder }) => innerBorder != null ? innerBorder : "1px solid #eaeaea"};
394
567
  }
395
568
 
396
- &:hover {
397
- background-color: ${base.colorTokens.neutral100};
398
- }
399
-
400
569
  // 데이터가 minRows 이하여서 빈칸을 채워준 경우 호버 액션, 커서 액션 모두 OFF
401
570
  &[data-empty='true'] {
402
571
  border: none; /* 테두리 제거 */
@@ -422,33 +591,36 @@ var TableBody = styled2__default.default.tbody`
422
591
  }
423
592
  }
424
593
  `;
425
- var PaginationWrapper = styled2__default.default.div`
594
+ var PaginationWrapper = styled3__default.default.div`
426
595
  position: relative;
427
596
  display: flex;
428
597
  justify-content: space-between;
429
598
  align-items: center;
430
599
  width: 100%;
431
- height: 56px;
600
+ height: ${({ sizeVar }) => sizeVar === "XS" ? "40px" : "56px"};
601
+ background-color: ${base.colorTokens.neutral0};
432
602
  border-top: ${`1px solid ${base.colorTokens.neutral200}`};
433
-
603
+ border-radius: ${({ isEndOfPage }) => isEndOfPage && "0 0 12px 12px"};
434
604
  .table-pagination {
435
605
  border-top: none;
436
606
  }
437
607
  `;
438
- var BottomContainer = styled2__default.default.div`
439
- position: sticky;
608
+ var BottomContainer = styled3__default.default.div`
609
+ position: ${({ disableStickyFooter }) => disableStickyFooter ? "relative" : "sticky"};
440
610
  width: 100%;
441
- bottom: 0;
611
+ bottom: ${({ disableStickyFooter }) => disableStickyFooter ? "auto" : "0"};
442
612
  background-color: ${base.colorTokens.neutral0};
443
- z-index: 11;
613
+ z-index: ${({ disableStickyFooter }) => disableStickyFooter ? 1 : 20};
614
+ ${({ disableStickyFooter }) => !disableStickyFooter ? "isolation: isolate;" : ""}
444
615
  border-radius: ${({ isEndOfPage }) => isEndOfPage && "0 0 12px 12px"};
445
- border: ${({ hasFilterBar, hasToolbar }) => hasFilterBar && !hasToolbar && `1px solid ${base.colorTokens.neutral200}`};
616
+ border: ${({ hasFilterBar, hasToolbar, hideBorder }) => !hideBorder && hasFilterBar && !hasToolbar && `1px solid ${base.colorTokens.neutral200}`};
446
617
  border-top: none;
447
618
  `;
448
- var ScrollContainer = styled2__default.default.div`
619
+ var ScrollContainer = styled3__default.default.div`
449
620
  height: 6px;
450
621
  position: absolute;
451
- bottom: 50px;
622
+ //* JIRA SH-18674: 테이블 스크롤바 테이블 바디 내에 위치할 수 있도록 푸터 위로 올림. 없을 때는 푸터에 2px 여유
623
+ bottom: ${({ isPagination }) => isPagination ? "56px" : "2px"};
452
624
  width: 100%;
453
625
  z-index: 12;
454
626
  overflow-x: scroll;
@@ -463,45 +635,235 @@ var ScrollContainer = styled2__default.default.div`
463
635
  border-radius: 100px;
464
636
  }
465
637
  `;
466
- var TableResizer = styled2__default.default.div``;
467
- var EmptySource = styled2__default.default.div`
638
+ var TableResizer = styled3__default.default.div``;
639
+ styled3__default.default.div`
468
640
  width: 60px;
469
641
  `;
470
- var PaginationLeftSlot = styled2__default.default.div`
642
+ var PaginationLeftSlot = styled3__default.default.div`
471
643
  position: absolute;
472
644
  left: 16px;
473
645
  top: 50%;
474
646
  transform: translateY(-50%);
475
647
  `;
476
- var SmallIconButton = styled2__default.default(base.IconButton)`
477
- svg {
478
- width: 12px !important;
479
- height: 12px !important;
648
+ var PaginationSizeSelectorSlot = styled3__default.default.div`
649
+ [data-shoplflow='Dropdown-Content-Area'],
650
+ [data-shoplflow='Text'],
651
+ [data-shoplflow='Menu'] {
652
+ white-space: nowrap;
480
653
  }
481
654
  `;
482
- var TableToolbar = ({
483
- children,
484
- filterAccessor,
485
- height = "56px",
486
- padding = "12px 20px",
487
- totalCount
488
- }) => {
489
- const { table, filterValue, setFilterValue } = useTable();
490
- const _totalCount = totalCount || table.getPrePaginationRowModel().rows.length;
491
- const onSearch = (value) => {
492
- var _a;
493
- if (!filterAccessor) {
494
- return null;
495
- }
496
- setFilterValue(value);
497
- (_a = table.getColumn(filterAccessor)) == null ? void 0 : _a.setFilterValue(value);
655
+ var TableFilterBar = React3.memo(
656
+ React3.forwardRef(({ onReset, onRemoveFilter }, ref) => {
657
+ const { table, setFilterValue, hasToolbar, outsideFilters } = useTable();
658
+ const filters = table.getState().columnFilters;
659
+ const prevFiltersRef = React3.useRef();
660
+ const allFilters = [
661
+ ...outsideFilters || [],
662
+ ...filters.filter((filter) => {
663
+ return !(outsideFilters == null ? void 0 : outsideFilters.some((outsideFilter) => outsideFilter.id === filter.id));
664
+ })
665
+ ];
666
+ const onSearch = (value) => {
667
+ setFilterValue(value);
668
+ table.resetColumnFilters();
669
+ };
670
+ const resetFilters = () => {
671
+ table.setColumnFilters([]);
672
+ onReset == null ? void 0 : onReset();
673
+ const resetColumnFilters = (columns) => {
674
+ columns.forEach((column) => {
675
+ var _a, _b;
676
+ if ((_b = (_a = column.columnDef) == null ? void 0 : _a.meta) == null ? void 0 : _b.onFilterChange) {
677
+ column.columnDef.meta.onFilterChange("");
678
+ }
679
+ if (column.columns && column.columns.length > 0) {
680
+ resetColumnFilters(column.columns);
681
+ }
682
+ });
683
+ };
684
+ resetColumnFilters(table.getAllColumns());
685
+ };
686
+ React3.useImperativeHandle(ref, () => ({
687
+ resetFilters
688
+ }));
689
+ const handleRemoveFilter = (columnId, filterValue) => {
690
+ var _a, _b, _c;
691
+ const isOutsideFilter = outsideFilters == null ? void 0 : outsideFilters.some((f) => f.id === columnId && f.value === filterValue);
692
+ if (isOutsideFilter && onRemoveFilter) {
693
+ onRemoveFilter(columnId);
694
+ }
695
+ const column = table.getColumn(columnId);
696
+ const newFilters = table.getState().columnFilters.filter((filter) => filter.id !== columnId);
697
+ table.setColumnFilters(newFilters);
698
+ column == null ? void 0 : column.setFilterValue(void 0);
699
+ (_c = (_b = (_a = column == null ? void 0 : column.columnDef) == null ? void 0 : _a.meta) == null ? void 0 : _b.onFilterChange) == null ? void 0 : _c.call(_b, "");
700
+ };
701
+ const getFilterLabel = (columnId, value) => {
702
+ var _a;
703
+ const outsideFilter = outsideFilters == null ? void 0 : outsideFilters.find((f) => f.id === columnId && f.value === value);
704
+ if (outsideFilter == null ? void 0 : outsideFilter.label) {
705
+ return outsideFilter.label;
706
+ }
707
+ const column = table.getColumn(columnId);
708
+ if (column && ((_a = column.columnDef.meta) == null ? void 0 : _a.filterOptions)) {
709
+ const filterOption = column.columnDef.meta.filterOptions.find((option) => option.value === value);
710
+ if (filterOption) {
711
+ return filterOption.label;
712
+ }
713
+ }
714
+ return value;
715
+ };
716
+ React3.useEffect(() => {
717
+ var _a;
718
+ const outsideFilterIds = [...new Set((_a = outsideFilters == null ? void 0 : outsideFilters.map((f) => f.id)) != null ? _a : [])];
719
+ const tableFilters = table.getState().columnFilters;
720
+ const validTableFilters = tableFilters.filter((f) => !outsideFilterIds.includes(f.id));
721
+ if (!lodashEs.isEqual(prevFiltersRef.current, validTableFilters)) {
722
+ prevFiltersRef.current = validTableFilters;
723
+ table.setColumnFilters(validTableFilters);
724
+ }
725
+ outsideFilterIds.forEach((columnId) => {
726
+ const column = table.getColumn(columnId);
727
+ if (column && column.getFilterValue() != null && column.getFilterValue() !== "") {
728
+ column.setFilterValue(void 0);
729
+ }
730
+ });
731
+ }, [outsideFilters, table]);
732
+ const _allFilters = allFilters.filter((filter) => filter.value !== "ALL");
733
+ return /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children: _allFilters.length > 0 && /* @__PURE__ */ jsxRuntime.jsxs(
734
+ base.StackContainer.Horizontal,
735
+ {
736
+ width: "100%",
737
+ align: "center",
738
+ padding: hasToolbar ? "0px 16px 8px" : "0px 0px 8px 0px",
739
+ spacing: "spacing08",
740
+ "data-component": "table-filter-bar",
741
+ children: [
742
+ /* @__PURE__ */ jsxRuntime.jsx(
743
+ base.IconButton,
744
+ {
745
+ sizeVar: "XS",
746
+ styleVar: "GHOST",
747
+ onClick: () => {
748
+ resetFilters();
749
+ if (filters) {
750
+ onSearch("");
751
+ }
752
+ },
753
+ "data-component": "reset-button",
754
+ children: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: shoplAssets.RefreshIcon, color: "neutral700" })
755
+ }
756
+ ),
757
+ allFilters.map((filter) => {
758
+ const filterValueString = filter.value;
759
+ const filterLabel = getFilterLabel(filter.id, filterValueString);
760
+ const truncatedLabel = filterLabel.length > 50 ? `${filterLabel.slice(0, 50)}...` : filterLabel;
761
+ return /* @__PURE__ */ jsxRuntime.jsx(
762
+ base.Tag,
763
+ {
764
+ sizeVar: "XS",
765
+ styleVar: "TINT",
766
+ color: "neutral600",
767
+ background: "neutral150",
768
+ radius: true,
769
+ rightSource: /* @__PURE__ */ jsxRuntime.jsx(
770
+ base.Icon,
771
+ {
772
+ iconSource: shoplAssets.CloseSmallIcon,
773
+ sizeVar: "XS",
774
+ color: "neutral350",
775
+ onClick: () => handleRemoveFilter(filter.id, filterValueString),
776
+ style: { cursor: "pointer" },
777
+ "data-component": "filter-tag-delete-button",
778
+ role: "button"
779
+ }
780
+ ),
781
+ children: /* @__PURE__ */ jsxRuntime.jsx(base.Text, { typography: "caption_400", color: "neutral600", lineClamp: 1, children: truncatedLabel })
782
+ },
783
+ `${filter.id}-${filterValueString}`
784
+ );
785
+ })
786
+ ]
787
+ }
788
+ ) });
789
+ })
790
+ );
791
+ var TableEmpty = ({ children, minHeight }) => {
792
+ return /* @__PURE__ */ jsxRuntime.jsx(base.StackContainer, { width: "100%", minHeight, height: "max-content", align: "center", justify: "center", children });
793
+ };
794
+
795
+ // src/components/Table/utils/getColumnActiveHoverDataAttribute.ts
796
+ function getColumnActiveHoverDataAttribute(activeHover, rowOriginal) {
797
+ if (activeHover === void 0)
798
+ return void 0;
799
+ const enabled = typeof activeHover === "function" ? activeHover(rowOriginal) : activeHover;
800
+ return enabled ? "true" : void 0;
801
+ }
802
+
803
+ // src/components/Table/utils/getTableHeadSortModel.ts
804
+ function getTableHeadSortModel(header) {
805
+ var _a, _b;
806
+ const meta = header.column.columnDef.meta;
807
+ const hasChildColumns = ((_b = (_a = header.column.columns) == null ? void 0 : _a.length) != null ? _b : 0) > 0;
808
+ if ((meta == null ? void 0 : meta.delegateSortToSingleLeaf) === true && hasChildColumns) {
809
+ const leafColumns = header.column.getLeafColumns();
810
+ if (leafColumns.length === 1) {
811
+ return {
812
+ showSortMenu: true,
813
+ sortColumn: leafColumns[0]
814
+ };
815
+ }
816
+ }
817
+ return {
818
+ showSortMenu: header.column.getCanSort(),
819
+ sortColumn: header.column
498
820
  };
499
- return /* @__PURE__ */ jsxRuntime.jsx(base.StackContainer.Horizontal, { width: "100%", height, align: "center", padding, justify: "space-between", children: children({
500
- totalCount: _totalCount,
501
- filterAccessor: filterAccessor != null ? filterAccessor : "",
502
- onSearch,
503
- filterValue
504
- }) });
821
+ }
822
+
823
+ // src/components/Table/utils/resolveBodyRowStyle.ts
824
+ var DEFAULT_TABLE_BODY_ROW_HEIGHT_PX = 60;
825
+ var parseCssSizeToPx = (value) => {
826
+ if (typeof value === "number" && Number.isFinite(value)) {
827
+ return value;
828
+ }
829
+ if (typeof value !== "string") {
830
+ return void 0;
831
+ }
832
+ const parsed = Number.parseInt(value, 10);
833
+ if (Number.isNaN(parsed)) {
834
+ return void 0;
835
+ }
836
+ return parsed;
837
+ };
838
+ var resolveBodyRowCss = (bodyRowStyle, rowIndex, row) => {
839
+ if (typeof bodyRowStyle === "function") {
840
+ if (rowIndex === void 0) {
841
+ return void 0;
842
+ }
843
+ return bodyRowStyle(rowIndex, row);
844
+ }
845
+ return bodyRowStyle;
846
+ };
847
+ var resolveHeightPx = (style) => {
848
+ const fromHeight = parseCssSizeToPx(style.height);
849
+ if (fromHeight !== void 0) {
850
+ return fromHeight;
851
+ }
852
+ const fromMinHeight = parseCssSizeToPx(style.minHeight);
853
+ if (fromMinHeight !== void 0) {
854
+ return fromMinHeight;
855
+ }
856
+ return DEFAULT_TABLE_BODY_ROW_HEIGHT_PX;
857
+ };
858
+ var resolveBodyRowStyle = (bodyRowStyle, rowIndex, row) => {
859
+ if (!bodyRowStyle) {
860
+ return { heightPx: DEFAULT_TABLE_BODY_ROW_HEIGHT_PX };
861
+ }
862
+ const style = resolveBodyRowCss(bodyRowStyle, rowIndex, row);
863
+ if (!style) {
864
+ return { heightPx: DEFAULT_TABLE_BODY_ROW_HEIGHT_PX };
865
+ }
866
+ return { style, heightPx: resolveHeightPx(style) };
505
867
  };
506
868
 
507
869
  // src/components/Table/utils/index.ts
@@ -522,597 +884,439 @@ var PAGE_SIZE = [
522
884
  { key: "50", label: "50" },
523
885
  { key: "100", label: "100" }
524
886
  ];
525
- var useIntersectionObserver = (target, callback, options) => {
526
- React2.useEffect(() => {
527
- if (!target.current) {
528
- return;
529
- }
530
- const observer = new IntersectionObserver(callback, options);
531
- observer.observe(target.current);
532
- return () => observer.disconnect();
533
- }, [callback]);
534
- };
535
- var TablePagination = ({
536
- total,
537
- defaultPageSize,
538
- children,
539
- pageSizeList = PAGE_SIZE,
540
- setCurrentPage,
541
- notSizeOption = false,
542
- currentPage,
543
- sizeVar = "S"
544
- }) => {
545
- const { table, headerRef, bodyRef, tableScrollRef, footerRef, hasFilterBar, hasToolbar } = useTable();
546
- const { pageSize, pageIndex } = table.getState().pagination;
547
- const [isEndOfPage, setIsEndOfPage] = React2.useState(false);
548
- const handleScroll = React2.useCallback(() => {
549
- if (!headerRef.current || !bodyRef.current || !tableScrollRef.current) {
550
- return;
887
+ var FilterMenu = ({ header, onFilterChange, triggerWidth }) => {
888
+ var _a;
889
+ const { outsideFilters } = useTable();
890
+ const columnFilterValue = header.column.getFilterValue();
891
+ const meta = (_a = header.column.columnDef.meta) != null ? _a : {};
892
+ const { filterOptions, filterMenuWidth = "trigger" } = meta;
893
+ const [maxLabelWidth, setMaxLabelWidth] = React3.useState(0);
894
+ const measureRefs = React3.useRef([]);
895
+ const outsideFilterValues = outsideFilters == null ? void 0 : outsideFilters.filter((filter) => filter.id === header.column.id).map((filter) => filter.value);
896
+ const activeFilterValues = outsideFilterValues && outsideFilterValues.length > 0 ? outsideFilterValues : columnFilterValue != null && columnFilterValue !== "" ? [String(columnFilterValue)] : [];
897
+ React3.useEffect(() => {
898
+ var _a2;
899
+ const count = (_a2 = filterOptions == null ? void 0 : filterOptions.length) != null ? _a2 : 0;
900
+ const widths = measureRefs.current.slice(0, count).map((ref) => {
901
+ var _a3;
902
+ return (_a3 = ref == null ? void 0 : ref.offsetWidth) != null ? _a3 : 0;
903
+ });
904
+ setMaxLabelWidth(widths.length ? Math.max(...widths, 0) : 0);
905
+ }, [filterOptions]);
906
+ const handleFilterChange = (value) => {
907
+ const isCurrentlySelected = activeFilterValues.includes(value);
908
+ if (isCurrentlySelected) {
909
+ header.column.setFilterValue("");
910
+ if (onFilterChange) {
911
+ onFilterChange("");
912
+ }
913
+ } else {
914
+ header.column.setFilterValue(value);
915
+ if (onFilterChange) {
916
+ onFilterChange(value);
917
+ }
551
918
  }
552
- const scrollLeft = tableScrollRef.current.scrollLeft;
553
- headerRef.current.scrollLeft = scrollLeft;
554
- bodyRef.current.scrollLeft = scrollLeft;
555
- }, []);
556
- const onIntersect = React2.useCallback(
557
- (entries) => {
558
- const entry = entries[0];
559
- entry.isIntersecting ? setIsEndOfPage(true) : setIsEndOfPage(false);
560
- },
561
- // eslint-disable-next-line react-hooks/exhaustive-deps
562
- [isEndOfPage]
563
- );
564
- useIntersectionObserver(footerRef, onIntersect, {
565
- threshold: 1,
566
- rootMargin: "0px 0px -1px"
567
- });
568
- const handlePageChange = React2.useCallback(
569
- (updater) => {
570
- const newPage = typeof updater === "function" ? updater(pageIndex) : updater;
571
- table.setPageIndex(newPage);
572
- setCurrentPage == null ? void 0 : setCurrentPage({ pageIndex: newPage, pageSize });
573
- },
574
- [pageIndex, pageSize, table, setCurrentPage]
575
- );
576
- const handlePageSizeChange = React2.useCallback(
577
- (value) => {
578
- const newSize = Number(value);
579
- table.setPageSize(newSize);
580
- table.setPageIndex(0);
581
- setCurrentPage == null ? void 0 : setCurrentPage({ pageIndex: 0, pageSize: newSize });
582
- },
583
- [table, setCurrentPage]
584
- );
585
- const TableColumns = () => /* @__PURE__ */ jsxRuntime.jsx("colgroup", { children: table.getAllColumns().map((column) => {
586
- const size = column.columnDef.size;
587
- const minSize = column.columnDef.minSize;
588
- const maxSize = column.columnDef.maxSize;
589
- const style = size === 0 ? { width: "100%" } : {
590
- width: `${size}px`,
591
- minWidth: `${minSize}px`,
592
- maxWidth: `${maxSize}px`
593
- };
594
- return /* @__PURE__ */ jsxRuntime.jsx("col", { style }, column.id);
595
- }) });
596
- React2.useEffect(() => {
597
- table.setPageSize(defaultPageSize);
598
- }, [defaultPageSize, table]);
599
- React2.useEffect(() => {
600
- table.setPageIndex(currentPage != null ? currentPage : 0);
601
- }, [table, currentPage]);
602
- return /* @__PURE__ */ jsxRuntime.jsxs(BottomContainer, { ref: footerRef, isEndOfPage, hasFilterBar, hasToolbar, children: [
603
- /* @__PURE__ */ jsxRuntime.jsx(ScrollContainer, { ref: tableScrollRef, onScroll: handleScroll, children: /* @__PURE__ */ jsxRuntime.jsx("table", { style: { width: table.getTotalSize() || "100%", height: "6px", tableLayout: "fixed" }, children: /* @__PURE__ */ jsxRuntime.jsx(TableColumns, {}) }) }),
604
- /* @__PURE__ */ jsxRuntime.jsxs(PaginationWrapper, { children: [
605
- /* @__PURE__ */ jsxRuntime.jsx(PaginationLeftSlot, { children }),
606
- /* @__PURE__ */ jsxRuntime.jsx(
607
- base.Pagination,
608
- {
609
- pageSize: `${pageSize}`,
610
- currentPage: pageIndex,
611
- itemsTotalCount: total,
612
- totalCount: Math.ceil(total / Number(pageSize)),
613
- previousPage: () => handlePageChange(pageIndex - 1),
614
- nextPage: () => handlePageChange(pageIndex + 1),
615
- sizeVar,
616
- style: { paddingInline: "16px" },
617
- gotoPage: handlePageChange,
618
- rightSource: notSizeOption ? /* @__PURE__ */ jsxRuntime.jsx(EmptySource, {}) : /* @__PURE__ */ jsxRuntime.jsx(
619
- base.Pagination.SizeSelector,
620
- {
621
- data: pageSizeList.map((item) => ({ label: item.label, value: item.key })),
622
- pageSize: `${pageSize}`,
623
- setPageSize: handlePageSizeChange
624
- }
625
- )
919
+ };
920
+ if (!header.column.getCanFilter()) {
921
+ return null;
922
+ }
923
+ const menuWidth = filterMenuWidth === "auto" && maxLabelWidth > triggerWidth ? "100%" : `${triggerWidth}px`;
924
+ return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
925
+ /* @__PURE__ */ jsxRuntime.jsx(
926
+ "div",
927
+ {
928
+ style: {
929
+ position: "absolute",
930
+ left: "-9999px",
931
+ top: 0,
932
+ visibility: "hidden",
933
+ pointerEvents: "none",
934
+ display: "flex",
935
+ flexDirection: "column",
936
+ alignItems: "flex-start"
626
937
  },
627
- Math.ceil(total / Number(pageSize))
628
- )
629
- ] })
938
+ children: filterOptions == null ? void 0 : filterOptions.map((option, idx) => /* @__PURE__ */ jsxRuntime.jsx(
939
+ base.Text,
940
+ {
941
+ typography: "body1_400",
942
+ ref: (el) => measureRefs.current[idx] = el,
943
+ style: { whiteSpace: "nowrap" },
944
+ children: option.label
945
+ },
946
+ option.value
947
+ ))
948
+ }
949
+ ),
950
+ /* @__PURE__ */ jsxRuntime.jsx(
951
+ base.StackContainer.Vertical,
952
+ {
953
+ padding: "4px",
954
+ radius: "borderRadius04",
955
+ background: "neutral0",
956
+ width: menuWidth,
957
+ style: { boxShadow: "0px 8px 16px 0px rgba(0, 0, 0, 0.12)" },
958
+ onWheel: (e) => e.stopPropagation(),
959
+ onScroll: (e) => e.stopPropagation(),
960
+ children: /* @__PURE__ */ jsxRuntime.jsx(base.ScrollArea, { autoHeight: true, autoHeightMax: 240, children: /* @__PURE__ */ jsxRuntime.jsx("ul", { children: filterOptions == null ? void 0 : filterOptions.map((option) => /* @__PURE__ */ jsxRuntime.jsx(
961
+ base.Menu,
962
+ {
963
+ isSelected: activeFilterValues.includes(option.value),
964
+ onClick: () => handleFilterChange(option.value),
965
+ leftSource: option.icon,
966
+ children: /* @__PURE__ */ jsxRuntime.jsx(base.Text, { typography: "body1_400", lineClamp: 2, children: option.label })
967
+ },
968
+ option.value
969
+ )) }) })
970
+ }
971
+ )
630
972
  ] });
631
973
  };
632
- var TableFilterBar = React2.memo(({ outsideFilters }) => {
633
- const { table, setFilterValue, hasToolbar } = useTable();
634
- const filters = table.getState().columnFilters;
635
- const prevFiltersRef = React2.useRef();
636
- const onSearch = (value) => {
637
- setFilterValue(value);
638
- table.resetColumnFilters();
639
- };
640
- const resetFilters = () => {
641
- table.setColumnFilters([]);
642
- const resetColumnFilters = (columns) => {
643
- columns.forEach((column) => {
644
- var _a, _b;
645
- if ((_b = (_a = column.columnDef) == null ? void 0 : _a.meta) == null ? void 0 : _b.onFilterChange) {
646
- column.columnDef.meta.onFilterChange("");
647
- }
648
- if (column.columns && column.columns.length > 0) {
649
- resetColumnFilters(column.columns);
650
- }
651
- });
652
- };
653
- resetColumnFilters(table.getAllColumns());
654
- };
655
- const handleRemoveFilter = (columnId, filterValue) => {
656
- var _a, _b, _c, _d;
657
- const newFilters = table.getState().columnFilters.filter((filter) => !(filter.id === columnId && filter.value === filterValue));
658
- table.setColumnFilters(newFilters);
659
- (_d = (_c = (_b = (_a = table.getColumn(columnId)) == null ? void 0 : _a.columnDef) == null ? void 0 : _b.meta) == null ? void 0 : _c.onFilterChange) == null ? void 0 : _d.call(_c, "");
660
- };
661
- const getFilterLabel = (columnId, value) => {
662
- var _a;
663
- const column = table.getColumn(columnId);
664
- if (!column || !((_a = column.columnDef.meta) == null ? void 0 : _a.filterOptions)) {
665
- return value;
974
+ var SortMenu = ({ onSortChange, header, sortColumn, triggerWidth }) => {
975
+ var _a, _b, _c, _d, _e, _f, _g;
976
+ const column = sortColumn != null ? sortColumn : header.column;
977
+ const sortLabels = (_d = (_c = (_a = header.column.columnDef.meta) == null ? void 0 : _a.sortLabels) != null ? _c : (_b = column.columnDef.meta) == null ? void 0 : _b.sortLabels) != null ? _d : ["\uC815\uB82C \uD574\uC81C", "\uC624\uB984\uCC28\uC21C", "\uB0B4\uB9BC\uCC28\uC21C"];
978
+ const currentSort = column.getIsSorted();
979
+ const handleSortChange = (value) => {
980
+ if (value === void 0) {
981
+ column.clearSorting();
982
+ } else {
983
+ column.toggleSorting(value === "desc", false);
984
+ }
985
+ if (onSortChange) {
986
+ onSortChange(value);
666
987
  }
667
- const filterOption = column.columnDef.meta.filterOptions.find((option) => option.value === value);
668
- return filterOption ? filterOption.label : value;
669
988
  };
670
- React2.useEffect(() => {
671
- const validFilters = outsideFilters == null ? void 0 : outsideFilters.filter((item) => item.value !== void 0 && item.value !== "").map((item) => ({ id: item.id, value: item.value }));
672
- if (!lodashEs.isEqual(prevFiltersRef.current, validFilters)) {
673
- prevFiltersRef.current = validFilters;
674
- if (validFilters && validFilters.length > 0) {
675
- table.setColumnFilters(validFilters);
676
- } else {
677
- table.setColumnFilters([]);
678
- }
989
+ const delegatedSingleLeaf = ((_e = header.column.columnDef.meta) == null ? void 0 : _e.delegateSortToSingleLeaf) === true && ((_g = (_f = header.column.columns) == null ? void 0 : _f.length) != null ? _g : 0) > 0 && header.column.getLeafColumns().length === 1;
990
+ if (!delegatedSingleLeaf && !column.getCanSort()) {
991
+ return null;
992
+ }
993
+ return /* @__PURE__ */ jsxRuntime.jsxs(
994
+ base.StackContainer.Vertical,
995
+ {
996
+ padding: "4px",
997
+ radius: "borderRadius04",
998
+ background: "neutral0",
999
+ width: `${triggerWidth}px`,
1000
+ style: { boxShadow: "0px 8px 16px 0px rgba(0, 0, 0, 0.12)" },
1001
+ as: "ul",
1002
+ children: [
1003
+ /* @__PURE__ */ jsxRuntime.jsx(
1004
+ base.Menu,
1005
+ {
1006
+ leftSource: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: shoplAssets.MoreIcon, sizeVar: "S" }),
1007
+ isSelected: !currentSort,
1008
+ onClick: () => handleSortChange(void 0),
1009
+ children: sortLabels[0]
1010
+ }
1011
+ ),
1012
+ /* @__PURE__ */ jsxRuntime.jsx(
1013
+ base.Menu,
1014
+ {
1015
+ leftSource: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: shoplAssets.AscIcon, sizeVar: "S" }),
1016
+ isSelected: currentSort === "asc",
1017
+ onClick: () => handleSortChange("asc"),
1018
+ children: sortLabels[1]
1019
+ }
1020
+ ),
1021
+ /* @__PURE__ */ jsxRuntime.jsx(
1022
+ base.Menu,
1023
+ {
1024
+ leftSource: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: shoplAssets.DescIcon, sizeVar: "S" }),
1025
+ isSelected: currentSort === "desc",
1026
+ onClick: () => handleSortChange("desc"),
1027
+ children: sortLabels[2]
1028
+ }
1029
+ )
1030
+ ]
679
1031
  }
680
- }, [outsideFilters, table]);
681
- return /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children: filters.length > 0 && /* @__PURE__ */ jsxRuntime.jsxs(
1032
+ );
1033
+ };
1034
+ var SmallIconButton = styled3__default.default(base.IconButton)`
1035
+ svg {
1036
+ width: 12px !important;
1037
+ height: 12px !important;
1038
+ }
1039
+ `;
1040
+ var TableHeadTrigger = ({
1041
+ header,
1042
+ uniqueClass,
1043
+ tableHeadRef,
1044
+ isOpen,
1045
+ onTriggerClick
1046
+ }) => {
1047
+ var _a, _b;
1048
+ const showFilterMenu = header.column.getCanFilter();
1049
+ const { showSortMenu, sortColumn } = getTableHeadSortModel(header);
1050
+ const headerStyle = (_b = (_a = header.column.columnDef.meta) == null ? void 0 : _a.headerProps) == null ? void 0 : _b.style;
1051
+ const currentSort = sortColumn.getIsSorted();
1052
+ let triggerIcon;
1053
+ if (currentSort === "asc") {
1054
+ triggerIcon = shoplAssets.AscIcon;
1055
+ } else if (currentSort === "desc") {
1056
+ triggerIcon = shoplAssets.DescIcon;
1057
+ } else {
1058
+ triggerIcon = shoplAssets.MoreIcon;
1059
+ }
1060
+ return /* @__PURE__ */ jsxRuntime.jsxs(
682
1061
  base.StackContainer.Horizontal,
683
1062
  {
684
1063
  width: "100%",
1064
+ height: "100%",
685
1065
  align: "center",
686
- padding: hasToolbar ? "0px 16px 8px" : "0px 0px 8px 0px",
687
- spacing: "spacing08",
1066
+ style: __spreadValues(__spreadValues({
1067
+ alignItems: "center",
1068
+ boxSizing: "border-box"
1069
+ }, showSortMenu || showFilterMenu ? { justifyContent: "space-between" } : {}), headerStyle),
1070
+ className: uniqueClass,
1071
+ ref: tableHeadRef,
1072
+ onClick: (e) => {
1073
+ e.stopPropagation();
1074
+ onTriggerClick();
1075
+ },
1076
+ role: "button",
688
1077
  children: [
689
1078
  /* @__PURE__ */ jsxRuntime.jsx(
690
- base.IconButton,
1079
+ base.Text,
691
1080
  {
692
- sizeVar: "XS",
693
- styleVar: "GHOST",
694
- onClick: () => {
695
- resetFilters();
696
- if (filters) {
697
- onSearch("");
698
- }
699
- },
700
- children: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: shoplAssets.RefreshIcon, color: "neutral700" })
1081
+ typography: "body2_400",
1082
+ color: "neutral400",
1083
+ lineClamp: 2,
1084
+ style: showSortMenu || showFilterMenu ? { flex: 1, minWidth: 0 } : void 0,
1085
+ children: reactTable.flexRender(header.column.columnDef.header, header.getContext())
701
1086
  }
702
1087
  ),
703
- filters.map((filter) => {
704
- const filterValueString = filter.value;
705
- const filterLabel = getFilterLabel(filter.id, filterValueString);
706
- return /* @__PURE__ */ jsxRuntime.jsx(
707
- base.Tag,
708
- {
709
- sizeVar: "XS",
710
- styleVar: "TINT",
711
- color: "neutral600",
712
- background: "neutral150",
713
- radius: true,
714
- rightSource: /* @__PURE__ */ jsxRuntime.jsx(
715
- base.Icon,
716
- {
717
- iconSource: shoplAssets.CloseSmallIcon,
718
- sizeVar: "XS",
719
- color: "neutral350",
720
- onClick: () => handleRemoveFilter(filter.id, filterValueString),
721
- style: { cursor: "pointer" }
722
- }
723
- ),
724
- children: /* @__PURE__ */ jsxRuntime.jsx(base.Text, { typography: "caption_400", color: "neutral600", children: filterLabel })
725
- },
726
- `${filter.id}-${filterValueString}`
727
- );
728
- })
729
- ]
730
- }
731
- ) });
732
- });
733
- var Table = ({
734
- data,
735
- columns,
736
- columnResizing = false,
737
- children,
738
- manualPagination = false,
739
- manualFiltering = false,
740
- manualSorting = true,
741
- selectedRows = [],
742
- onSelectedRowsChange,
743
- onClickRow
744
- }) => {
745
- const [sorting, setSorting] = React2.useState([]);
746
- const [columnFilters, setColumnFilters] = React2.useState([]);
747
- const [globalFilter, setGlobalFilter] = React2.useState([]);
748
- const [columnVisibility, setColumnVisibility] = React2.useState({});
749
- const [columnPinning, setColumnPinning] = React2.useState({});
750
- const [rowSelection, setRowSelection] = React2.useState({});
751
- const [filterValue, setFilterValue] = React2.useState("");
752
- const visibleColumns = React2.useMemo(() => columns.filter((column) => {
753
- var _a;
754
- return !((_a = column.meta) == null ? void 0 : _a.hiddenColumn);
755
- }), [columns]);
756
- const table = reactTable.useReactTable({
757
- data,
758
- columns: visibleColumns,
759
- columnResizeMode: "onChange",
760
- initialState: {
761
- pagination: {
762
- pageSize: 100
763
- }
764
- },
765
- state: {
766
- sorting,
767
- columnFilters,
768
- globalFilter,
769
- columnVisibility,
770
- columnPinning,
771
- rowSelection
772
- },
773
- defaultColumn: {
774
- size: 0,
775
- // TODO: 필터링 기능 추가 시 props로 옵션 처리
776
- enableColumnFilter: false,
777
- enableSorting: false,
778
- enableResizing: true
779
- },
780
- onSortingChange: (updater) => {
781
- var _a, _b;
782
- const newSorting = typeof updater === "function" ? updater(table.getState().sorting) : updater;
783
- setSorting(newSorting);
784
- if (newSorting.length > 0) {
785
- const { id, desc } = newSorting[0];
786
- const column = table.getAllLeafColumns().find((col) => col.id === id);
787
- (_b = (_a = column == null ? void 0 : column.columnDef.meta) == null ? void 0 : _a.onSortChange) == null ? void 0 : _b.call(_a, desc ? "desc" : "asc");
788
- } else {
789
- table.getAllLeafColumns().forEach((column) => {
790
- var _a2, _b2;
791
- (_b2 = (_a2 = column.columnDef.meta) == null ? void 0 : _a2.onSortChange) == null ? void 0 : _b2.call(_a2, void 0);
792
- });
793
- }
794
- },
795
- onColumnFiltersChange: (updater) => {
796
- const newFilters = typeof updater === "function" ? updater(table.getState().columnFilters) : updater;
797
- setColumnFilters(newFilters);
798
- newFilters.forEach((filter) => {
799
- var _a, _b;
800
- const column = table.getColumn(filter.id);
801
- if ((_b = (_a = column == null ? void 0 : column.columnDef) == null ? void 0 : _a.meta) == null ? void 0 : _b.onFilterChange) {
802
- column.columnDef.meta.onFilterChange(filter.value || "");
803
- }
804
- });
805
- },
806
- onGlobalFilterChange: (updater) => {
807
- var _a;
808
- const newGlobalFilter = typeof updater === "function" ? updater(globalFilter) : updater;
809
- setGlobalFilter(newGlobalFilter);
810
- if ((_a = table.options.meta) == null ? void 0 : _a.onGlobalFilterChange) {
811
- table.options.meta.onGlobalFilterChange(newGlobalFilter || "");
812
- }
813
- if (newGlobalFilter) {
814
- table.getAllLeafColumns().forEach((column) => {
815
- var _a2;
816
- if (column.getCanFilter() && ((_a2 = column.columnDef.meta) == null ? void 0 : _a2.onFilterChange)) {
817
- column.columnDef.meta.onFilterChange(newGlobalFilter);
818
- }
819
- });
820
- }
821
- },
822
- onColumnVisibilityChange: setColumnVisibility,
823
- onColumnPinningChange: setColumnPinning,
824
- onRowSelectionChange: (updater) => {
825
- const newSelection = typeof updater === "function" ? updater(rowSelection) : updater;
826
- setRowSelection(newSelection);
827
- const newSelectedRows = table.getRowModel().rows.filter((row) => newSelection[row.id]).map((row) => row.original);
828
- onSelectedRowsChange == null ? void 0 : onSelectedRowsChange(newSelectedRows);
829
- },
830
- getCoreRowModel: reactTable.getCoreRowModel(),
831
- getFilteredRowModel: reactTable.getFilteredRowModel(),
832
- getPaginationRowModel: reactTable.getPaginationRowModel(),
833
- getSortedRowModel: reactTable.getSortedRowModel(),
834
- enableColumnResizing: columnResizing,
835
- manualPagination,
836
- manualFiltering,
837
- manualSorting
838
- });
839
- const headerRef = React2.useRef(null);
840
- const bodyRef = React2.useRef(null);
841
- const footerRef = React2.useRef(null);
842
- const tableScrollRef = React2.useRef(null);
843
- const hasToolbar = React2.Children.toArray(children).some((child) => React2.isValidElement(child) && child.type === TableToolbar);
844
- const hasPagination = React2.Children.toArray(children).some(
845
- (child) => React2.isValidElement(child) && child.type === TablePagination
846
- );
847
- const hasFilterBar = React2.Children.toArray(children).some(
848
- (child) => React2.isValidElement(child) && child.type === TableFilterBar
849
- );
850
- const contextValue = {
851
- table,
852
- headerRef,
853
- bodyRef,
854
- footerRef,
855
- tableScrollRef,
856
- selectedRows,
857
- onClickRow,
858
- hasToolbar,
859
- hasFilterBar,
860
- hasPagination,
861
- columnResizing,
862
- filterValue,
863
- setFilterValue
864
- };
865
- React2.useEffect(() => {
866
- if (selectedRows.length === 0) {
867
- table.resetRowSelection();
868
- }
869
- }, [onSelectedRowsChange, selectedRows.length, table]);
870
- return /* @__PURE__ */ jsxRuntime.jsx(TableContainer, { hasToolbar: hasToolbar || hasFilterBar, children: /* @__PURE__ */ jsxRuntime.jsx(TableProvider, { value: contextValue, children }) });
871
- };
872
- var TableEmpty = ({ children }) => {
873
- return /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children });
874
- };
875
- var FilterMenu = ({ header, onFilterChange, triggerWidth }) => {
876
- var _a;
877
- const columnFilterValue = header.column.getFilterValue();
878
- const { filterOptions } = (_a = header.column.columnDef.meta) != null ? _a : {};
879
- const [maxLabelWidth, setMaxLabelWidth] = React2.useState(0);
880
- const labelRefs = React2.useRef([]);
881
- React2.useEffect(() => {
882
- const widths = labelRefs.current.map((ref) => (ref == null ? void 0 : ref.offsetWidth) || 0);
883
- setMaxLabelWidth(Math.max(...widths, 0));
884
- }, [filterOptions]);
885
- const handleFilterChange = (value) => {
886
- header.column.setFilterValue(value);
887
- if (onFilterChange) {
888
- onFilterChange(value);
889
- }
890
- };
891
- if (!header.column.getCanFilter()) {
892
- return null;
893
- }
894
- return /* @__PURE__ */ jsxRuntime.jsx(
895
- base.StackContainer.Vertical,
896
- {
897
- padding: "4px",
898
- radius: "borderRadius04",
899
- background: "neutral0",
900
- width: maxLabelWidth > triggerWidth ? "100%" : `${triggerWidth}px`,
901
- style: { boxShadow: "0px 8px 16px 0px rgba(0, 0, 0, 0.12)" },
902
- children: /* @__PURE__ */ jsxRuntime.jsx(base.ScrollArea, { autoHeight: true, autoHeightMax: 240, children: filterOptions == null ? void 0 : filterOptions.map((option, idx) => /* @__PURE__ */ jsxRuntime.jsx(
903
- base.Menu,
904
- {
905
- isSelected: columnFilterValue === option.value,
906
- onClick: () => handleFilterChange(option.value),
907
- leftSource: option.icon,
908
- children: /* @__PURE__ */ jsxRuntime.jsx(
909
- base.Text,
910
- {
911
- typography: "body1_400",
912
- whiteSpace: "nowrap",
913
- ref: (el) => labelRefs.current[idx] = el,
914
- children: option.label
915
- }
916
- )
917
- },
918
- option.value
919
- )) })
920
- }
921
- );
922
- };
923
- var SortMenu = ({ onSortChange, header, triggerWidth }) => {
924
- var _a, _b;
925
- const sortLabels = (_b = (_a = header.column.columnDef.meta) == null ? void 0 : _a.sortLabels) != null ? _b : ["\uC624\uB984\uCC28\uC21C", "\uB0B4\uB9BC\uCC28\uC21C", "\uC815\uB82C \uD574\uC81C"];
926
- const currentSort = header.column.getIsSorted();
927
- const handleSortChange = (value) => {
928
- if (value === void 0) {
929
- header.column.clearSorting();
930
- } else {
931
- header.column.toggleSorting(value === "asc", false);
932
- }
933
- if (onSortChange) {
934
- onSortChange(value);
935
- }
936
- };
937
- if (!header.column.getCanSort()) {
938
- return null;
939
- }
940
- return /* @__PURE__ */ jsxRuntime.jsxs(
941
- base.StackContainer.Vertical,
942
- {
943
- padding: "4px",
944
- radius: "borderRadius04",
945
- background: "neutral0",
946
- width: `${triggerWidth}px`,
947
- style: { boxShadow: "0px 8px 16px 0px rgba(0, 0, 0, 0.12)" },
948
- children: [
949
- /* @__PURE__ */ jsxRuntime.jsx(
950
- base.Menu,
951
- {
952
- leftSource: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: shoplAssets.DescIcon, sizeVar: "S" }),
953
- isSelected: currentSort === "desc",
954
- onClick: () => handleSortChange("asc"),
955
- children: sortLabels[0]
956
- }
957
- ),
958
- /* @__PURE__ */ jsxRuntime.jsx(
959
- base.Menu,
960
- {
961
- leftSource: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: shoplAssets.AscIcon, sizeVar: "S" }),
962
- isSelected: currentSort === "asc",
963
- onClick: () => handleSortChange("desc"),
964
- children: sortLabels[1]
965
- }
966
- ),
967
- /* @__PURE__ */ jsxRuntime.jsx(
968
- base.Menu,
1088
+ showSortMenu && /* @__PURE__ */ jsxRuntime.jsx(base.IconButton, { sizeVar: "XS", styleVar: "GHOST", "data-component": "sort-button", children: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: triggerIcon, sizeVar: "S", color: "neutral400", className: uniqueClass }) }),
1089
+ showFilterMenu && /* @__PURE__ */ jsxRuntime.jsx(SmallIconButton, { sizeVar: "XS", styleVar: "GHOST", className: uniqueClass, "data-component": "filter-button", children: /* @__PURE__ */ jsxRuntime.jsx(
1090
+ base.Icon,
969
1091
  {
970
- leftSource: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: shoplAssets.MoreIcon, sizeVar: "S" }),
971
- isSelected: !currentSort,
972
- onClick: () => handleSortChange(void 0),
973
- children: sortLabels[2]
1092
+ iconSource: isOpen ? shoplAssets.UpArrowSolidXsmallIcon : shoplAssets.DownArrowSolidXsmallIcon,
1093
+ className: uniqueClass,
1094
+ sizeVar: "XS",
1095
+ color: "neutral400"
974
1096
  }
975
- )
1097
+ ) })
976
1098
  ]
977
1099
  }
978
1100
  );
979
1101
  };
980
- var TableHeadTrigger = ({
981
- header,
982
- uniqueClass,
983
- tableHeadRef,
984
- isOpen,
985
- onTriggerClick
986
- }) => {
987
- var _a, _b;
1102
+ var TableHeadCell = ({ header, onFilterChange, onSortChange }) => {
1103
+ const tableHeadRef = React3.useRef(null);
1104
+ const [triggerWidth, setTriggerWidth] = React3.useState(0);
1105
+ const uniqueClass = React3.useMemo(() => {
1106
+ return `filter-menu-${crypto.randomUUID()}`;
1107
+ }, []);
1108
+ const { isOpen: isPopoverOpen, onClickTrigger: onClickPopoverTrigger } = utils.usePopover({
1109
+ popoverSelector: `.${uniqueClass}`
1110
+ });
1111
+ const sortModel = getTableHeadSortModel(header);
988
1112
  const showFilterMenu = header.column.getCanFilter();
989
- const showSortMenu = header.column.getCanSort();
990
- const currentSort = header.column.getIsSorted();
991
- let triggerIcon;
992
- if (currentSort === "asc") {
993
- triggerIcon = shoplAssets.AscIcon;
994
- } else if (currentSort === "desc") {
995
- triggerIcon = shoplAssets.DescIcon;
996
- } else {
997
- triggerIcon = shoplAssets.MoreIcon;
998
- }
1113
+ const showSortMenu = sortModel.showSortMenu;
1114
+ const hasInteraction = showFilterMenu || showSortMenu;
1115
+ const cursorStyle = hasInteraction ? "pointer" : "default";
1116
+ React3.useEffect(() => {
1117
+ if (tableHeadRef.current) {
1118
+ setTriggerWidth(tableHeadRef.current.clientWidth);
1119
+ }
1120
+ }, [isPopoverOpen, tableHeadRef]);
999
1121
  return /* @__PURE__ */ jsxRuntime.jsxs(
1000
- base.StackContainer.Horizontal,
1122
+ base.Popper,
1001
1123
  {
1002
- width: "100%",
1003
- align: "center",
1004
- style: (_b = (_a = header.column.columnDef.meta) == null ? void 0 : _a.headerProps) == null ? void 0 : _b.style,
1005
- className: uniqueClass,
1006
- ref: tableHeadRef,
1124
+ offset: { mainAxis: 4, crossAxis: -4 },
1125
+ autoPlacement: { allowedPlacements: ["bottom-start", "bottom-end"] },
1126
+ placement: "bottom-start",
1127
+ strategy: "absolute",
1128
+ middlewares: [base.shift({ padding: 6 })],
1007
1129
  children: [
1008
- reactTable.flexRender(header.column.columnDef.header, header.getContext()),
1009
- showSortMenu && /* @__PURE__ */ jsxRuntime.jsx(
1010
- base.IconButton,
1130
+ /* @__PURE__ */ jsxRuntime.jsx(
1131
+ base.Popper.Trigger,
1011
1132
  {
1012
- sizeVar: "XS",
1013
- styleVar: "GHOST",
1014
- onClick: (e) => {
1015
- e.stopPropagation();
1016
- onTriggerClick();
1133
+ isOpen: isPopoverOpen,
1134
+ "data-expanded": isPopoverOpen,
1135
+ onClick: () => {
1136
+ onClickPopoverTrigger();
1017
1137
  },
1018
- children: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: triggerIcon, sizeVar: "S", color: "neutral400", className: uniqueClass })
1019
- }
1020
- ),
1021
- showFilterMenu && /* @__PURE__ */ jsxRuntime.jsx(
1022
- SmallIconButton,
1023
- {
1024
- sizeVar: "XS",
1025
- styleVar: "GHOST",
1026
- onClick: (e) => {
1027
- e.stopPropagation();
1028
- onTriggerClick();
1138
+ style: {
1139
+ cursor: cursorStyle,
1140
+ background: `${(showFilterMenu || showSortMenu) && isPopoverOpen ? base.colorTokens.neutral400_5 : "transparent"}`,
1141
+ padding: `${(showFilterMenu || showSortMenu) && "4px"}`,
1142
+ borderRadius: `${isPopoverOpen ? "6px" : "0px"}`,
1143
+ display: "flex",
1144
+ alignItems: "center",
1145
+ boxSizing: "border-box",
1146
+ width: "100%",
1147
+ height: "100%",
1148
+ minHeight: "100%"
1029
1149
  },
1150
+ width: "100%",
1030
1151
  children: /* @__PURE__ */ jsxRuntime.jsx(
1031
- base.Icon,
1152
+ TableHeadTrigger,
1032
1153
  {
1033
- iconSource: isOpen ? shoplAssets.UpArrowSolidXsmallIcon : shoplAssets.DownArrowSolidXsmallIcon,
1034
- sizeVar: "XS",
1035
- color: "neutral400"
1154
+ isOpen: isPopoverOpen,
1155
+ header,
1156
+ uniqueClass,
1157
+ tableHeadRef,
1158
+ onTriggerClick: () => {
1159
+ onClickPopoverTrigger();
1160
+ }
1036
1161
  }
1037
1162
  )
1038
1163
  }
1039
- )
1164
+ ),
1165
+ isPopoverOpen && /* @__PURE__ */ jsxRuntime.jsxs(base.Popper.Portal, { children: [
1166
+ showFilterMenu && /* @__PURE__ */ jsxRuntime.jsx(
1167
+ FilterMenu,
1168
+ {
1169
+ header,
1170
+ onFilterChange: (value) => {
1171
+ onFilterChange == null ? void 0 : onFilterChange(value);
1172
+ },
1173
+ triggerWidth: triggerWidth + 16
1174
+ }
1175
+ ),
1176
+ showSortMenu && /* @__PURE__ */ jsxRuntime.jsx(
1177
+ SortMenu,
1178
+ {
1179
+ header,
1180
+ sortColumn: sortModel.sortColumn,
1181
+ onSortChange: (value) => {
1182
+ onSortChange == null ? void 0 : onSortChange(value);
1183
+ },
1184
+ triggerWidth: triggerWidth + 16
1185
+ }
1186
+ )
1187
+ ] })
1040
1188
  ]
1041
1189
  }
1042
1190
  );
1043
1191
  };
1044
- var TableHeadCell = ({ header, onFilterChange, onSortChange }) => {
1045
- const tableHeadRef = React2.useRef(null);
1046
- const [triggerWidth, setTriggerWidth] = React2.useState(0);
1047
- const uniqueClass = `filter-menu-${header.column.id}`;
1048
- const [isOpen, setIsOpen] = utils.useOutsideClick({
1049
- selector: `.${uniqueClass}`
1192
+ var TableHeadCell_default = TableHeadCell;
1193
+ var DragHandle = ({ listeners, attributes }) => /* @__PURE__ */ jsxRuntime.jsx(
1194
+ base.StackContainer.Horizontal,
1195
+ __spreadProps(__spreadValues(__spreadValues({
1196
+ align: "center",
1197
+ justify: "center",
1198
+ padding: "4px"
1199
+ }, listeners), attributes), {
1200
+ style: {
1201
+ cursor: "grab",
1202
+ touchAction: "none"
1203
+ },
1204
+ background: "neutral0",
1205
+ children: /* @__PURE__ */ jsxRuntime.jsx(base.Icon, { iconSource: shoplAssets.ListMoveIcon, sizeVar: "S", color: "neutral700" })
1206
+ })
1207
+ );
1208
+ var SortableRow = ({
1209
+ row,
1210
+ index,
1211
+ cells,
1212
+ hasPinned,
1213
+ onClickRow,
1214
+ getFixedCellStyle,
1215
+ showDragHandle,
1216
+ shouldFixDragHandle = false,
1217
+ dragColWidth = 40,
1218
+ bodyRowStyle
1219
+ }) => {
1220
+ const {
1221
+ attributes,
1222
+ listeners,
1223
+ setNodeRef,
1224
+ transform,
1225
+ transition,
1226
+ isDragging: isSortableDragging
1227
+ } = sortable.useSortable({
1228
+ id: row.id || `row-${index}`
1050
1229
  });
1051
- const showFilterMenu = header.column.getCanFilter();
1052
- const showSortMenu = header.column.getCanSort();
1053
- const hasInteraction = showFilterMenu || showSortMenu;
1054
- const cursorStyle = hasInteraction ? "pointer" : "default";
1055
- React2.useEffect(() => {
1056
- if (tableHeadRef.current) {
1057
- setTriggerWidth(tableHeadRef.current.clientWidth);
1058
- }
1059
- }, [isOpen, tableHeadRef]);
1060
- return /* @__PURE__ */ jsxRuntime.jsxs(base.Popper, { offset: 4, placement: "bottom-start", strategy: "absolute", children: [
1061
- /* @__PURE__ */ jsxRuntime.jsx(
1062
- base.Popper.Trigger,
1063
- {
1064
- isOpen,
1065
- onClick: () => {
1066
- setIsOpen((prev) => !prev);
1067
- },
1068
- style: {
1069
- cursor: cursorStyle,
1070
- background: `${(showFilterMenu || showSortMenu) && isOpen ? base.colorTokens.neutral400_5 : base.colorTokens.neutral100}`,
1071
- padding: `${(showFilterMenu || showSortMenu) && "8px"}`,
1072
- borderRadius: `${isOpen ? "6px" : "0px"}`
1073
- },
1074
- width: "100%",
1075
- children: /* @__PURE__ */ jsxRuntime.jsx(
1076
- TableHeadTrigger,
1230
+ const baseRowStyle = typeof bodyRowStyle === "function" ? bodyRowStyle(index, row.original) : bodyRowStyle;
1231
+ const style = __spreadProps(__spreadValues({}, baseRowStyle), {
1232
+ transform: utilities.CSS.Transform.toString(transform),
1233
+ transition,
1234
+ opacity: isSortableDragging ? 0.5 : 1,
1235
+ backgroundColor: isSortableDragging ? "#f5f5f5" : void 0
1236
+ });
1237
+ return /* @__PURE__ */ jsxRuntime.jsxs(
1238
+ TableRow,
1239
+ {
1240
+ ref: setNodeRef,
1241
+ style,
1242
+ "data-index": index,
1243
+ "data-has-pinned": hasPinned,
1244
+ onClick: () => {
1245
+ var _a;
1246
+ if (typeof row.getVisibleCells === "function") {
1247
+ onClickRow == null ? void 0 : onClickRow(row.original);
1248
+ } else if (Array.isArray(row) && row.length > 0 && ((_a = row[0].row) == null ? void 0 : _a.original)) {
1249
+ onClickRow == null ? void 0 : onClickRow(row[0].row.original);
1250
+ }
1251
+ },
1252
+ className: onClickRow !== void 0 ? "clickable" : `row-${index}`,
1253
+ children: [
1254
+ showDragHandle && /* @__PURE__ */ jsxRuntime.jsx(
1255
+ TableCell,
1077
1256
  {
1078
- isOpen,
1079
- header,
1080
- uniqueClass,
1081
- tableHeadRef,
1082
- onTriggerClick: () => setIsOpen((prev) => !prev)
1257
+ style: shouldFixDragHandle ? {
1258
+ position: "sticky",
1259
+ left: 0,
1260
+ zIndex: 11,
1261
+ width: `${dragColWidth}px`,
1262
+ minWidth: `${dragColWidth}px`,
1263
+ maxWidth: `${dragColWidth}px`,
1264
+ backgroundColor: "neutral0"
1265
+ } : void 0,
1266
+ "data-last-left-pinned": shouldFixDragHandle ? false : void 0,
1267
+ children: /* @__PURE__ */ jsxRuntime.jsx(DragHandle, { listeners, attributes })
1083
1268
  }
1084
- )
1085
- }
1086
- ),
1087
- isOpen && /* @__PURE__ */ jsxRuntime.jsxs(base.Popper.Portal, { children: [
1088
- showFilterMenu && /* @__PURE__ */ jsxRuntime.jsx(
1089
- FilterMenu,
1090
- {
1091
- header,
1092
- onFilterChange: (value) => {
1093
- onFilterChange == null ? void 0 : onFilterChange(value);
1094
- },
1095
- triggerWidth: triggerWidth + 16
1096
- }
1097
- ),
1098
- showSortMenu && /* @__PURE__ */ jsxRuntime.jsx(
1099
- SortMenu,
1100
- {
1101
- header,
1102
- onSortChange: (value) => {
1103
- onSortChange == null ? void 0 : onSortChange(value);
1104
- },
1105
- triggerWidth: triggerWidth + 16
1106
- }
1107
- )
1108
- ] })
1109
- ] });
1269
+ ),
1270
+ cells.map((cell) => {
1271
+ var _a;
1272
+ const isPinned = cell.column.getIsPinned();
1273
+ const isLastLeftPinned = isPinned === "left" && cell.column.getIsLastColumn("left");
1274
+ const isFirstRightPinned = isPinned === "right" && cell.column.getIsFirstColumn("right");
1275
+ const cellContext = cell.getContext();
1276
+ const overriddenContext = __spreadProps(__spreadValues({}, cellContext), {
1277
+ row: __spreadProps(__spreadValues({}, cellContext.row), {
1278
+ index
1279
+ })
1280
+ });
1281
+ return /* @__PURE__ */ jsxRuntime.jsx(React3.Fragment, { children: /* @__PURE__ */ jsxRuntime.jsx(
1282
+ TableCell,
1283
+ {
1284
+ "data-last-left-pinned": isLastLeftPinned,
1285
+ "data-first-right-pinned": isFirstRightPinned,
1286
+ "data-no-hover": getColumnActiveHoverDataAttribute(
1287
+ (_a = cell.column.columnDef.meta) == null ? void 0 : _a.activeHover,
1288
+ cell.row.original
1289
+ ),
1290
+ style: getFixedCellStyle(cell.column),
1291
+ children: reactTable.flexRender(cell.column.columnDef.cell, overriddenContext)
1292
+ }
1293
+ ) }, cell.id);
1294
+ })
1295
+ ]
1296
+ }
1297
+ );
1110
1298
  };
1111
- var TableHeadCell_default = TableHeadCell;
1299
+ var CellSkeleton = () => /* @__PURE__ */ jsxRuntime.jsx(base.Skeleton, { styleVar: "rectangle", width: "80%", height: "20px" });
1300
+ var SkeletonRows = ({ rowCount, columns, enableDragDrop }) => /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children: Array.from({ length: rowCount }).map((_, rowIndex) => /* @__PURE__ */ jsxRuntime.jsxs(TableRow, { children: [
1301
+ enableDragDrop && /* @__PURE__ */ jsxRuntime.jsx(TableCell, { style: { width: 40, minWidth: 40, height: "60px" }, children: /* @__PURE__ */ jsxRuntime.jsx(CellSkeleton, {}) }),
1302
+ columns.map((column) => /* @__PURE__ */ jsxRuntime.jsx(TableCell, { style: { height: "60px" }, children: /* @__PURE__ */ jsxRuntime.jsx(CellSkeleton, {}) }, column.id))
1303
+ ] }, `skeleton-row-${rowIndex}`)) });
1112
1304
  var FixedTable = ({ tableState }) => {
1113
- const { table, headerRef, bodyRef, tableScrollRef, hasToolbar, hasPagination, onClickRow } = useTable();
1114
1305
  const {
1115
- displayedRows,
1306
+ table,
1307
+ headerRef,
1308
+ bodyRef,
1309
+ tableScrollRef,
1310
+ footerRef,
1311
+ hasToolbar,
1312
+ hasPagination,
1313
+ onClickRow,
1314
+ hasFooter,
1315
+ hasFilterBar,
1316
+ isLoading
1317
+ } = useTable();
1318
+ const {
1319
+ displayedRows: initialDisplayedRows,
1116
1320
  paddingTop,
1117
1321
  paddingBottom,
1118
1322
  isEmpty,
@@ -1121,43 +1325,122 @@ var FixedTable = ({ tableState }) => {
1121
1325
  isSticky,
1122
1326
  stickyHeaderTopPosition,
1123
1327
  maxHeight = "100%",
1124
- emptyRowCount = 8
1328
+ emptyRowCount = 8,
1329
+ enableDragDrop = false,
1330
+ dragColWidth = 40,
1331
+ onRowReorder,
1332
+ shouldFixDragHandle = false,
1333
+ footerRowProps,
1334
+ headerRowStyle,
1335
+ bodyRowStyle
1125
1336
  } = tableState;
1126
- const handleScroll = React2.useCallback(() => {
1127
- if (!bodyRef.current) {
1337
+ const [displayedRows, setDisplayedRows] = React3.useState(initialDisplayedRows);
1338
+ const sensors = core.useSensors(
1339
+ core.useSensor(core.PointerSensor, {
1340
+ activationConstraint: {
1341
+ distance: 8
1342
+ }
1343
+ }),
1344
+ core.useSensor(core.KeyboardSensor, {
1345
+ coordinateGetter: sortable.sortableKeyboardCoordinates
1346
+ })
1347
+ );
1348
+ const handleScroll = React3.useCallback(() => {
1349
+ if (!bodyRef.current)
1128
1350
  return;
1129
- }
1130
1351
  const bodyScrollLeft = bodyRef.current.scrollLeft;
1131
1352
  if (headerRef.current) {
1132
1353
  headerRef.current.scrollLeft = bodyScrollLeft;
1133
1354
  }
1355
+ if (footerRef.current) {
1356
+ footerRef.current.scrollLeft = bodyScrollLeft;
1357
+ }
1134
1358
  if (tableScrollRef.current) {
1135
1359
  tableScrollRef.current.scrollLeft = bodyScrollLeft;
1136
1360
  }
1137
- }, [bodyRef, headerRef, tableScrollRef]);
1138
- const TableColumns = () => /* @__PURE__ */ jsxRuntime.jsx("colgroup", { children: table.getVisibleFlatColumns().map((column) => {
1139
- const size = column.columnDef.size;
1140
- const minSize = column.columnDef.minSize;
1141
- const maxSize = column.columnDef.maxSize;
1142
- const style = size === 0 ? { width: "100%" } : {
1143
- width: `${size}px`,
1144
- minWidth: `${minSize}px`,
1145
- maxWidth: `${maxSize}px`
1146
- };
1147
- return /* @__PURE__ */ jsxRuntime.jsx("col", { style }, column.id);
1148
- }) });
1149
- const getFixedCellStyle = (column, isHeader = false) => {
1150
- var _a, _b, _c, _d;
1151
- const baseStyle = __spreadValues(__spreadValues({}, getCommonPinningStyles(column)), isHeader ? (_b = (_a = column.columnDef.meta) == null ? void 0 : _a.headerProps) == null ? void 0 : _b.style : (_d = (_c = column.columnDef.meta) == null ? void 0 : _c.cellProps) == null ? void 0 : _d.style);
1361
+ }, [bodyRef, headerRef, footerRef, tableScrollRef]);
1362
+ const handleScrollBarScroll = React3.useCallback(() => {
1363
+ if (!tableScrollRef.current || !bodyRef.current)
1364
+ return;
1365
+ bodyRef.current.scrollLeft = tableScrollRef.current.scrollLeft;
1366
+ }, [bodyRef, tableScrollRef]);
1367
+ const dragColWidthPx = `${dragColWidth}px`;
1368
+ const TableColumns = ({ showDragHandle = false }) => {
1369
+ const leafColumns = table.getVisibleLeafColumns();
1370
+ return /* @__PURE__ */ jsxRuntime.jsxs("colgroup", { children: [
1371
+ showDragHandle && /* @__PURE__ */ jsxRuntime.jsx("col", { style: { width: dragColWidthPx, minWidth: dragColWidthPx, maxWidth: dragColWidthPx } }),
1372
+ leafColumns.map((column) => {
1373
+ var _a, _b;
1374
+ const size = column.columnDef.size;
1375
+ const minSize = (_a = column.columnDef.minSize) != null ? _a : size;
1376
+ const maxSize = (_b = column.columnDef.maxSize) != null ? _b : size;
1377
+ const style = size === 0 ? { width: "100%" } : {
1378
+ width: `${size}px`,
1379
+ minWidth: `${minSize}px`,
1380
+ maxWidth: `${maxSize}px`
1381
+ };
1382
+ return /* @__PURE__ */ jsxRuntime.jsx("col", { style }, column.id);
1383
+ })
1384
+ ] });
1385
+ };
1386
+ const getFixedCellStyle = (column, isHeader = false, isFooter = false) => {
1387
+ var _a, _b, _c, _d, _e, _f;
1388
+ const baseStyle = __spreadValues(__spreadValues({}, getCommonPinningStyles(column)), isHeader ? (_b = (_a = column.columnDef.meta) == null ? void 0 : _a.headerProps) == null ? void 0 : _b.style : isFooter ? (_d = (_c = column.columnDef.meta) == null ? void 0 : _c.footerProps) == null ? void 0 : _d.style : (_f = (_e = column.columnDef.meta) == null ? void 0 : _e.cellProps) == null ? void 0 : _f.style);
1152
1389
  const size = column.columnDef.size;
1153
1390
  const minSize = column.columnDef.minSize;
1154
1391
  const maxSize = column.columnDef.maxSize;
1155
- return __spreadValues(__spreadValues({}, baseStyle), size === 0 ? { width: "100%" } : {
1392
+ const isPinned = column.getIsPinned();
1393
+ const adjustedLeft = shouldFixDragHandle && isPinned === "left" && baseStyle.left ? `${parseFloat(baseStyle.left.toString()) + dragColWidth}px` : baseStyle.left;
1394
+ return __spreadValues(__spreadProps(__spreadValues({}, baseStyle), {
1395
+ left: adjustedLeft
1396
+ }), size === 0 ? { width: "100%" } : {
1156
1397
  width: `${size}px`,
1157
1398
  minWidth: `${minSize}px`,
1158
1399
  maxWidth: `${maxSize}px`
1159
1400
  });
1160
1401
  };
1402
+ const handleDragEnd = (event) => {
1403
+ const { active, over } = event;
1404
+ if (over && active.id !== over.id) {
1405
+ setDisplayedRows((rows) => {
1406
+ const oldIndex = rows.findIndex((r) => {
1407
+ const row = r.row;
1408
+ const id = typeof row.id !== "undefined" ? row.id : rows.indexOf(r);
1409
+ return id === active.id;
1410
+ });
1411
+ const newIndex = rows.findIndex((r) => {
1412
+ const row = r.row;
1413
+ const id = typeof row.id !== "undefined" ? row.id : rows.indexOf(r);
1414
+ return id === over.id;
1415
+ });
1416
+ const newOrder = sortable.arrayMove(rows, oldIndex, newIndex);
1417
+ if (onRowReorder) {
1418
+ const reorderedData = newOrder.map((r) => {
1419
+ var _a;
1420
+ const row = r.row;
1421
+ if (typeof row.getVisibleCells === "function") {
1422
+ return row.original;
1423
+ } else if (Array.isArray(row) && row.length > 0 && ((_a = row[0].row) == null ? void 0 : _a.original)) {
1424
+ return row[0].row.original;
1425
+ }
1426
+ return null;
1427
+ }).filter(Boolean);
1428
+ onRowReorder(reorderedData);
1429
+ }
1430
+ return newOrder;
1431
+ });
1432
+ }
1433
+ };
1434
+ const rowIds = React3__default.default.useMemo(
1435
+ () => displayedRows.map((r) => {
1436
+ var _a, _b, _c;
1437
+ return r.row.id || `row-${((_a = r.row.original) == null ? void 0 : _a.id) || ((_c = (_b = r.row.original) == null ? void 0 : _b.userName) == null ? void 0 : _c.name) || "fallback"}`;
1438
+ }),
1439
+ [displayedRows]
1440
+ );
1441
+ React3.useEffect(() => {
1442
+ setDisplayedRows(initialDisplayedRows);
1443
+ }, [initialDisplayedRows]);
1161
1444
  return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
1162
1445
  /* @__PURE__ */ jsxRuntime.jsx(
1163
1446
  HeaderTableContainer,
@@ -1175,40 +1458,108 @@ var FixedTable = ({ tableState }) => {
1175
1458
  tableLayout: "fixed"
1176
1459
  },
1177
1460
  children: [
1178
- /* @__PURE__ */ jsxRuntime.jsx(TableColumns, {}),
1179
- /* @__PURE__ */ jsxRuntime.jsx(TableHeader, { children: table.getHeaderGroups().map((headerGroup) => /* @__PURE__ */ jsxRuntime.jsx(TableRow, { children: headerGroup.headers.map((header) => {
1180
- const isPinned = header.column.getIsPinned();
1181
- const isLastLeftPinned = isPinned === "left" && header.column.getIsLastColumn("left");
1182
- const isFirstRightPinned = isPinned === "right" && header.column.getIsFirstColumn("right");
1183
- const columnRelativeDepth = header.depth - header.column.depth;
1184
- if (!header.isPlaceholder && columnRelativeDepth > 1 && header.id === header.column.id) {
1185
- return null;
1186
- }
1187
- let rowSpan = 1;
1188
- if (header.isPlaceholder) {
1189
- const leafs = header.getLeafHeaders();
1190
- rowSpan = leafs[leafs.length - 1].depth - header.depth;
1191
- }
1192
- return /* @__PURE__ */ jsxRuntime.jsx(
1193
- TableHead,
1194
- {
1195
- "data-last-left-pinned": isLastLeftPinned,
1196
- "data-first-right-pinned": isFirstRightPinned,
1197
- "data-pinned": isPinned,
1198
- style: getFixedCellStyle(header.column, true),
1199
- colSpan: header.colSpan,
1200
- rowSpan,
1201
- children: /* @__PURE__ */ jsxRuntime.jsx(TableHeadCell_default, { header })
1202
- },
1203
- header.id
1204
- );
1205
- }) }, headerGroup.id)) })
1461
+ /* @__PURE__ */ jsxRuntime.jsx(TableColumns, { showDragHandle: enableDragDrop }),
1462
+ /* @__PURE__ */ jsxRuntime.jsx(TableHeader, { children: table.getHeaderGroups().map((headerGroup, i) => {
1463
+ const rowStyle = typeof headerRowStyle === "function" ? headerRowStyle(i, headerGroup) : headerRowStyle;
1464
+ return /* @__PURE__ */ jsxRuntime.jsxs(TableRow, { style: rowStyle, children: [
1465
+ enableDragDrop && /* @__PURE__ */ jsxRuntime.jsx(
1466
+ TableHead,
1467
+ {
1468
+ colSpan: 1,
1469
+ style: shouldFixDragHandle ? {
1470
+ position: "sticky",
1471
+ left: 0,
1472
+ zIndex: 11,
1473
+ width: dragColWidthPx,
1474
+ minWidth: dragColWidthPx,
1475
+ maxWidth: dragColWidthPx,
1476
+ backgroundColor: (rowStyle == null ? void 0 : rowStyle.backgroundColor) || "neutral400"
1477
+ } : rowStyle ? {
1478
+ backgroundColor: (rowStyle == null ? void 0 : rowStyle.backgroundColor) || "neutral400",
1479
+ height: rowStyle == null ? void 0 : rowStyle.height,
1480
+ maxHeight: rowStyle == null ? void 0 : rowStyle.maxHeight,
1481
+ minHeight: rowStyle == null ? void 0 : rowStyle.minHeight
1482
+ } : void 0,
1483
+ "data-pinned": shouldFixDragHandle ? "left" : void 0,
1484
+ "data-last-left-pinned": shouldFixDragHandle ? false : void 0
1485
+ }
1486
+ ),
1487
+ headerGroup.headers.map((header) => {
1488
+ var _a, _b, _c, _d, _e;
1489
+ const isPinned = header.column.getIsPinned();
1490
+ const leafHeaders = header.getLeafHeaders();
1491
+ const hasLastLeftPinnedLeaf = leafHeaders.some(
1492
+ (leaf) => leaf.column.getIsPinned() === "left" && leaf.column.getIsLastColumn("left")
1493
+ );
1494
+ const hasFirstRightPinnedLeaf = leafHeaders.some(
1495
+ (leaf) => leaf.column.getIsPinned() === "right" && leaf.column.getIsFirstColumn("right")
1496
+ );
1497
+ const isLastLeftPinned = isPinned === "left" && header.column.getIsLastColumn("left") || hasLastLeftPinnedLeaf;
1498
+ const isFirstRightPinned = isPinned === "right" && header.column.getIsFirstColumn("right") || hasFirstRightPinnedLeaf;
1499
+ const columnRelativeDepth = header.depth - header.column.depth;
1500
+ if (!header.isPlaceholder && columnRelativeDepth > 1 && header.id === header.column.id) {
1501
+ return null;
1502
+ }
1503
+ let rowSpan = 1;
1504
+ if (header.isPlaceholder) {
1505
+ const leafs = header.getLeafHeaders();
1506
+ rowSpan = leafs[leafs.length - 1].depth - header.depth;
1507
+ }
1508
+ let headerStyle = {};
1509
+ if (header.colSpan > 1) {
1510
+ const leafHeaders2 = header.getLeafHeaders();
1511
+ const groupId = header.column.id;
1512
+ const totalWidth = leafHeaders2.filter((leaf) => leaf.column.id !== groupId).reduce((sum, leaf) => {
1513
+ const size = leaf.column.columnDef.size || 0;
1514
+ return sum + size;
1515
+ }, 0);
1516
+ const firstLeaf = leafHeaders2[0];
1517
+ const firstLeafPinned = firstLeaf.column.getIsPinned();
1518
+ headerStyle = __spreadProps(__spreadValues({}, (_b = (_a = header.column.columnDef.meta) == null ? void 0 : _a.headerProps) == null ? void 0 : _b.style), {
1519
+ width: `${totalWidth}px`,
1520
+ minWidth: `${totalWidth}px`,
1521
+ maxWidth: `${totalWidth}px`,
1522
+ left: firstLeafPinned === "left" ? `${firstLeaf.column.getStart("left")}px` : void 0,
1523
+ right: firstLeafPinned === "right" ? `${firstLeaf.column.getAfter("right")}px` : void 0,
1524
+ position: firstLeafPinned ? "sticky" : "relative",
1525
+ zIndex: firstLeafPinned ? 10 : 0
1526
+ });
1527
+ } else {
1528
+ headerStyle = getFixedCellStyle(header.column, true);
1529
+ }
1530
+ const hasNoBorderRight = headerStyle.borderRight === "none" || ((_e = (_d = (_c = header.column.columnDef.meta) == null ? void 0 : _c.headerProps) == null ? void 0 : _d.style) == null ? void 0 : _e.borderRight) === "none";
1531
+ return /* @__PURE__ */ jsxRuntime.jsx(
1532
+ TableHead,
1533
+ {
1534
+ "data-last-left-pinned": isLastLeftPinned,
1535
+ "data-first-right-pinned": isFirstRightPinned,
1536
+ "data-pinned": isPinned,
1537
+ "data-no-border-right": hasNoBorderRight,
1538
+ style: __spreadValues(__spreadValues({}, headerStyle), rowStyle && {
1539
+ backgroundColor: rowStyle.backgroundColor,
1540
+ height: rowStyle.height,
1541
+ maxHeight: rowStyle.maxHeight,
1542
+ minHeight: rowStyle.minHeight
1543
+ }),
1544
+ colSpan: header.colSpan,
1545
+ rowSpan,
1546
+ sortable: getTableHeadSortModel(header).showSortMenu,
1547
+ filterable: header.column.getCanFilter(),
1548
+ "data-sortable": getTableHeadSortModel(header).showSortMenu,
1549
+ "data-filterable": header.column.getCanFilter(),
1550
+ children: /* @__PURE__ */ jsxRuntime.jsx(TableHeadCell_default, { header })
1551
+ },
1552
+ header.id
1553
+ );
1554
+ })
1555
+ ] }, headerGroup.id);
1556
+ }) })
1206
1557
  ]
1207
1558
  }
1208
1559
  )
1209
1560
  }
1210
1561
  ),
1211
- /* @__PURE__ */ jsxRuntime.jsx(base.ScrollArea, { autoHeightMax: maxHeight, autoHeight: true, children: /* @__PURE__ */ jsxRuntime.jsx(BodyTableContainer, { hasPagination, onScroll: handleScroll, ref: bodyRef, children: isEmpty ? children || emptyElement : /* @__PURE__ */ jsxRuntime.jsxs(
1562
+ /* @__PURE__ */ jsxRuntime.jsx(base.ScrollArea, { autoHeightMax: maxHeight, autoHeight: true, children: /* @__PURE__ */ jsxRuntime.jsx(BodyTableContainer, { hasPagination, hasFooter, onScroll: handleScroll, ref: bodyRef, children: /* @__PURE__ */ jsxRuntime.jsx(core.DndContext, { sensors, collisionDetection: core.closestCenter, onDragEnd: handleDragEnd, children: /* @__PURE__ */ jsxRuntime.jsx(sortable.SortableContext, { items: rowIds, strategy: sortable.verticalListSortingStrategy, children: /* @__PURE__ */ jsxRuntime.jsxs(
1212
1563
  "table",
1213
1564
  {
1214
1565
  style: {
@@ -1217,51 +1568,104 @@ var FixedTable = ({ tableState }) => {
1217
1568
  tableLayout: "fixed"
1218
1569
  },
1219
1570
  children: [
1220
- /* @__PURE__ */ jsxRuntime.jsx(TableColumns, {}),
1571
+ /* @__PURE__ */ jsxRuntime.jsx(TableColumns, { showDragHandle: enableDragDrop }),
1221
1572
  /* @__PURE__ */ jsxRuntime.jsxs(TableBody, { children: [
1222
1573
  paddingTop > 0 && /* @__PURE__ */ jsxRuntime.jsx(TableRow, { children: /* @__PURE__ */ jsxRuntime.jsx("td", { style: { height: `${paddingTop}px` } }) }),
1223
- displayedRows.map((rowObj, i) => {
1574
+ isLoading && /* @__PURE__ */ jsxRuntime.jsx(
1575
+ SkeletonRows,
1576
+ {
1577
+ rowCount: emptyRowCount || 8,
1578
+ columns: table.getVisibleLeafColumns(),
1579
+ enableDragDrop
1580
+ }
1581
+ ),
1582
+ !isLoading && isEmpty && /* @__PURE__ */ jsxRuntime.jsx(TableRow, { children: /* @__PURE__ */ jsxRuntime.jsx(
1583
+ TableCell,
1584
+ {
1585
+ colSpan: table.getAllColumns().length + (enableDragDrop ? 1 : 0),
1586
+ style: { padding: 0, border: "none" },
1587
+ children: children || emptyElement
1588
+ }
1589
+ ) }),
1590
+ !isLoading && !isEmpty && displayedRows.map((rowObj, i) => {
1591
+ var _a, _b, _c;
1224
1592
  const isVirtual = "virtualRow" in rowObj && rowObj.virtualRow;
1225
1593
  const row = rowObj.row;
1226
1594
  const cells = typeof row.getVisibleCells === "function" ? row.getVisibleCells() : row;
1595
+ const hasPinned = cells.some((cell) => cell.column.getIsPinned());
1596
+ const rowId = row.id || `row-${((_a = row.original) == null ? void 0 : _a.id) || ((_c = (_b = row.original) == null ? void 0 : _b.userName) == null ? void 0 : _c.name) || i}`;
1597
+ if (enableDragDrop) {
1598
+ return /* @__PURE__ */ jsxRuntime.jsx(
1599
+ SortableRow,
1600
+ {
1601
+ row,
1602
+ index: i,
1603
+ cells,
1604
+ hasPinned,
1605
+ onClickRow,
1606
+ getFixedCellStyle,
1607
+ showDragHandle: true,
1608
+ shouldFixDragHandle,
1609
+ dragColWidth,
1610
+ bodyRowStyle
1611
+ },
1612
+ rowId
1613
+ );
1614
+ }
1615
+ const rowStyle = typeof bodyRowStyle === "function" ? bodyRowStyle(i, row.original) : bodyRowStyle;
1616
+ const cellBackgroundColor = rowStyle == null ? void 0 : rowStyle.backgroundColor;
1227
1617
  return /* @__PURE__ */ jsxRuntime.jsx(
1228
1618
  TableRow,
1229
1619
  {
1230
1620
  "data-index": isVirtual ? rowObj.virtualRow.index : i,
1621
+ "data-has-pinned": hasPinned,
1622
+ style: rowStyle,
1231
1623
  onClick: () => {
1232
- var _a;
1624
+ var _a2;
1233
1625
  if (typeof row.getVisibleCells === "function") {
1234
1626
  onClickRow == null ? void 0 : onClickRow(row.original);
1235
- } else if (Array.isArray(row) && row.length > 0 && ((_a = row[0].row) == null ? void 0 : _a.original)) {
1627
+ } else if (Array.isArray(row) && row.length > 0 && ((_a2 = row[0].row) == null ? void 0 : _a2.original)) {
1236
1628
  onClickRow == null ? void 0 : onClickRow(row[0].row.original);
1237
1629
  }
1238
1630
  },
1239
- className: onClickRow !== void 0 ? "clickable" : "",
1631
+ className: onClickRow !== void 0 ? "clickable" : `row-${i}`,
1240
1632
  children: cells.map((cell) => {
1241
- var _a;
1633
+ var _a2, _b2, _c2, _d;
1242
1634
  const isPinned = cell.column.getIsPinned();
1243
1635
  const isLastLeftPinned = isPinned === "left" && cell.column.getIsLastColumn("left");
1244
1636
  const isFirstRightPinned = isPinned === "right" && cell.column.getIsFirstColumn("right");
1245
- return /* @__PURE__ */ jsxRuntime.jsx(React2.Fragment, { children: /* @__PURE__ */ jsxRuntime.jsx(
1637
+ const cellContext = cell.getContext();
1638
+ const overriddenContext = __spreadProps(__spreadValues({}, cellContext), {
1639
+ row: __spreadProps(__spreadValues({}, cellContext.row), {
1640
+ index: i
1641
+ })
1642
+ });
1643
+ return /* @__PURE__ */ jsxRuntime.jsx(React3.Fragment, { children: /* @__PURE__ */ jsxRuntime.jsx(
1246
1644
  TableCell,
1247
1645
  {
1248
1646
  "data-last-left-pinned": isLastLeftPinned,
1249
1647
  "data-first-right-pinned": isFirstRightPinned,
1250
- "data-no-hover": ((_a = cell.column.columnDef.meta) == null ? void 0 : _a.activeHover) ? "true" : void 0,
1251
- style: getFixedCellStyle(cell.column),
1252
- children: reactTable.flexRender(cell.column.columnDef.cell, cell.getContext())
1648
+ "data-no-hover": getColumnActiveHoverDataAttribute(
1649
+ (_a2 = cell.column.columnDef.meta) == null ? void 0 : _a2.activeHover,
1650
+ cell.row.original
1651
+ ),
1652
+ "data-has-custom-style": ((_d = (_c2 = (_b2 = cell.column.columnDef.meta) == null ? void 0 : _b2.cellProps) == null ? void 0 : _c2.style) == null ? void 0 : _d.backgroundColor) ? "true" : void 0,
1653
+ style: __spreadValues(__spreadValues({}, getFixedCellStyle(cell.column)), cellBackgroundColor && {
1654
+ backgroundColor: cellBackgroundColor
1655
+ }),
1656
+ children: isLoading ? /* @__PURE__ */ jsxRuntime.jsx(CellSkeleton, {}) : reactTable.flexRender(cell.column.columnDef.cell, overriddenContext)
1253
1657
  }
1254
1658
  ) }, cell.id);
1255
1659
  })
1256
1660
  },
1257
- typeof row.id !== "undefined" ? row.id : i
1661
+ rowId
1258
1662
  );
1259
1663
  }),
1260
1664
  paddingBottom > 0 && /* @__PURE__ */ jsxRuntime.jsx(TableRow, { children: /* @__PURE__ */ jsxRuntime.jsx("td", { style: { height: `${paddingBottom}px` } }) }),
1261
- emptyRowCount !== 0 && displayedRows.length < emptyRowCount && Array.from({ length: emptyRowCount - displayedRows.length }).map((_, index) => /* @__PURE__ */ jsxRuntime.jsx(TableRow, { "data-empty": true, children: /* @__PURE__ */ jsxRuntime.jsx(
1665
+ emptyRowCount !== 0 && displayedRows.length < emptyRowCount && !isLoading && !isEmpty && Array.from({ length: emptyRowCount - displayedRows.length }).map((_, index) => /* @__PURE__ */ jsxRuntime.jsx(TableRow, { "data-empty": true, children: /* @__PURE__ */ jsxRuntime.jsx(
1262
1666
  TableCell,
1263
1667
  {
1264
- colSpan: table.getAllColumns().length,
1668
+ colSpan: table.getAllColumns().length + (enableDragDrop ? 1 : 0),
1265
1669
  style: {
1266
1670
  height: `${60}px`
1267
1671
  }
@@ -1270,7 +1674,89 @@ var FixedTable = ({ tableState }) => {
1270
1674
  ] })
1271
1675
  ]
1272
1676
  }
1273
- ) }) })
1677
+ ) }) }) }) }),
1678
+ !hasPagination && /* @__PURE__ */ jsxRuntime.jsx(
1679
+ BottomContainer,
1680
+ {
1681
+ ref: footerRef,
1682
+ isEndOfPage: true,
1683
+ hasFilterBar,
1684
+ hasToolbar,
1685
+ hideBorder: true,
1686
+ children: /* @__PURE__ */ jsxRuntime.jsx(ScrollContainer, { ref: tableScrollRef, onScroll: handleScrollBarScroll, isPagination: false, children: /* @__PURE__ */ jsxRuntime.jsx(
1687
+ "table",
1688
+ {
1689
+ style: {
1690
+ width: enableDragDrop ? (table.getTotalSize() || 0) + dragColWidth : table.getTotalSize() || "100%",
1691
+ height: "6px",
1692
+ tableLayout: "fixed"
1693
+ },
1694
+ children: /* @__PURE__ */ jsxRuntime.jsx(TableColumns, { showDragHandle: enableDragDrop })
1695
+ }
1696
+ ) })
1697
+ }
1698
+ ),
1699
+ hasFooter && /* @__PURE__ */ jsxRuntime.jsx(FooterTableContainer, { ref: footerRef, isSticky, hasPagination, hasHeader: hasToolbar, children: /* @__PURE__ */ jsxRuntime.jsxs(
1700
+ "table",
1701
+ {
1702
+ style: {
1703
+ width: "100%",
1704
+ overflow: "auto",
1705
+ tableLayout: "fixed"
1706
+ },
1707
+ children: [
1708
+ /* @__PURE__ */ jsxRuntime.jsx(TableColumns, { showDragHandle: enableDragDrop }),
1709
+ /* @__PURE__ */ jsxRuntime.jsx(TableFooter, { children: table.getFooterGroups().map((footerGroup) => {
1710
+ var _a;
1711
+ return /* @__PURE__ */ jsxRuntime.jsxs(TableRow, { style: footerRowProps == null ? void 0 : footerRowProps.style, children: [
1712
+ enableDragDrop && /* @__PURE__ */ jsxRuntime.jsx(
1713
+ TableFoot,
1714
+ {
1715
+ colSpan: 1,
1716
+ style: shouldFixDragHandle ? {
1717
+ position: "sticky",
1718
+ left: 0,
1719
+ zIndex: 11,
1720
+ width: dragColWidthPx,
1721
+ minWidth: dragColWidthPx,
1722
+ maxWidth: dragColWidthPx,
1723
+ backgroundColor: ((_a = footerRowProps == null ? void 0 : footerRowProps.style) == null ? void 0 : _a.backgroundColor) || "inherit"
1724
+ } : void 0,
1725
+ "data-last-left-pinned": shouldFixDragHandle ? false : void 0
1726
+ }
1727
+ ),
1728
+ footerGroup.headers.map((footer) => {
1729
+ const isPinned = footer.column.getIsPinned();
1730
+ const isLastLeftPinned = isPinned === "left" && footer.column.getIsLastColumn("left");
1731
+ const isFirstRightPinned = isPinned === "right" && footer.column.getIsFirstColumn("right");
1732
+ const columnRelativeDepth = footer.depth - footer.column.depth;
1733
+ if (!footer.isPlaceholder && columnRelativeDepth > 1 && footer.id === footer.column.id) {
1734
+ return null;
1735
+ }
1736
+ let rowSpan = 1;
1737
+ if (footer.isPlaceholder) {
1738
+ const leafs = footer.getLeafHeaders();
1739
+ rowSpan = leafs[leafs.length - 1].depth - footer.depth;
1740
+ }
1741
+ return /* @__PURE__ */ jsxRuntime.jsx(
1742
+ TableFoot,
1743
+ {
1744
+ "data-last-left-pinned": isLastLeftPinned,
1745
+ "data-first-right-pinned": isFirstRightPinned,
1746
+ "data-pinned": isPinned,
1747
+ style: getFixedCellStyle(footer.column, false, true),
1748
+ colSpan: footer.colSpan,
1749
+ rowSpan,
1750
+ children: footer.isPlaceholder ? null : reactTable.flexRender(footer.column.columnDef.footer, footer.getContext())
1751
+ },
1752
+ footer.id
1753
+ );
1754
+ })
1755
+ ] }, footerGroup.id);
1756
+ }) })
1757
+ ]
1758
+ }
1759
+ ) })
1274
1760
  ] });
1275
1761
  };
1276
1762
  var ResizableTable = ({ tableState }) => {
@@ -1285,29 +1771,33 @@ var ResizableTable = ({ tableState }) => {
1285
1771
  isSticky,
1286
1772
  stickyHeaderTopPosition,
1287
1773
  maxHeight = "100%",
1288
- emptyRowCount = 8
1774
+ emptyRowCount = 8,
1775
+ headerRowStyle,
1776
+ bodyRowStyle
1289
1777
  } = tableState;
1290
- const handleScroll = React2.useCallback(() => {
1291
- if (headerRef.current && bodyRef.current && tableScrollRef.current) {
1292
- const scrollLeft = bodyRef.current.scrollLeft;
1293
- headerRef.current.scrollLeft = scrollLeft;
1294
- tableScrollRef.current.scrollLeft = scrollLeft;
1778
+ const handleScroll = React3.useCallback(() => {
1779
+ if (!bodyRef.current)
1780
+ return;
1781
+ const bodyScrollLeft = bodyRef.current.scrollLeft;
1782
+ if (headerRef.current) {
1783
+ headerRef.current.scrollLeft = bodyScrollLeft;
1295
1784
  }
1296
- }, []);
1297
- const columnSizeVars = React2__default.default.useMemo(() => {
1298
- var _a;
1785
+ if (tableScrollRef.current) {
1786
+ tableScrollRef.current.scrollLeft = bodyScrollLeft;
1787
+ }
1788
+ }, [bodyRef, headerRef, tableScrollRef]);
1789
+ const columnSizeVars = React3__default.default.useMemo(() => {
1299
1790
  const headers = table.getFlatHeaders();
1300
1791
  const colSizes = {};
1301
1792
  const visibleHeaders = headers.filter((header) => header.column.getIsVisible());
1302
- const lastLeafColumns = table.getLeafHeaders();
1303
- const lastColumnId = (_a = lastLeafColumns[lastLeafColumns.length - 1]) == null ? void 0 : _a.id;
1304
1793
  visibleHeaders.forEach((header) => {
1305
1794
  const currentSize = header.column.getSize();
1306
1795
  const defaultSize = header.column.columnDef.size;
1307
1796
  const maxSize = header.column.columnDef.maxSize;
1308
- const isLastColumn = header.id === lastColumnId;
1797
+ const isPinned = header.column.getIsPinned();
1798
+ const canResize = header.column.getCanResize();
1309
1799
  let size;
1310
- if (isLastColumn) {
1800
+ if (!isPinned && canResize) {
1311
1801
  size = "auto";
1312
1802
  } else if (currentSize !== void 0) {
1313
1803
  size = currentSize;
@@ -1316,7 +1806,7 @@ var ResizableTable = ({ tableState }) => {
1316
1806
  } else {
1317
1807
  size = 200;
1318
1808
  }
1319
- if (!isLastColumn && maxSize && typeof size === "number" && size > maxSize) {
1809
+ if (maxSize && typeof size === "number" && size > maxSize) {
1320
1810
  size = maxSize;
1321
1811
  }
1322
1812
  colSizes[`--header-${header.id}-size`] = size;
@@ -1324,8 +1814,11 @@ var ResizableTable = ({ tableState }) => {
1324
1814
  });
1325
1815
  return colSizes;
1326
1816
  }, [table.getState().columnSizingInfo, table.getState().columnSizing]);
1817
+ const totalTableWidth = React3__default.default.useMemo(() => {
1818
+ return table.getLeftTotalSize() + table.getCenterTotalSize() + table.getRightTotalSize();
1819
+ }, [table.getState().columnSizingInfo, table.getState().columnSizing, table.getState().columnPinning]);
1327
1820
  const getResizableCellStyle = (column, isHeader = false) => {
1328
- var _a, _b, _c, _d, _e;
1821
+ var _a, _b, _c, _d;
1329
1822
  const baseStyle = __spreadValues(__spreadValues({}, getCommonPinningStyles(column)), isHeader ? (_b = (_a = column.columnDef.meta) == null ? void 0 : _a.headerProps) == null ? void 0 : _b.style : (_d = (_c = column.columnDef.meta) == null ? void 0 : _c.cellProps) == null ? void 0 : _d.style);
1330
1823
  const colId = column.id;
1331
1824
  const headerId = isHeader ? colId : null;
@@ -1333,11 +1826,18 @@ var ResizableTable = ({ tableState }) => {
1333
1826
  const maxSize = column.columnDef.maxSize;
1334
1827
  const sizeKey = isHeader ? `--header-${headerId}-size` : `--col-${colId}-size`;
1335
1828
  const size = columnSizeVars[sizeKey];
1336
- const isLastColumn = (_e = column.columnDef.meta) == null ? void 0 : _e.isLastColumn;
1337
- return __spreadProps(__spreadValues(__spreadValues({}, baseStyle), size === "auto" ? { width: "auto", flex: "1 1 auto" } : { width: size ? `${size}px` : "auto" }), {
1829
+ const canResize = column.getCanResize();
1830
+ const isPinned = column.getIsPinned();
1831
+ const ellipsisStyle = !canResize && !isPinned ? {
1832
+ overflow: "hidden",
1833
+ textOverflow: "ellipsis",
1834
+ whiteSpace: "nowrap"
1835
+ } : {};
1836
+ return __spreadValues(__spreadProps(__spreadValues(__spreadValues({}, baseStyle), size === "auto" ? { width: "auto", flex: "1 1 auto" } : { width: size ? `${size}px` : "auto" }), {
1338
1837
  minWidth: `${minSize}px`,
1339
- maxWidth: isLastColumn ? "none" : `${maxSize || "none"}`
1340
- });
1838
+ // maxWidth: isLastColumn && canResize ? 'none' : `${maxSize || 'none'}`,
1839
+ maxWidth: canResize ? "none" : `${maxSize || "none"}`
1840
+ }), ellipsisStyle);
1341
1841
  };
1342
1842
  return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
1343
1843
  /* @__PURE__ */ jsxRuntime.jsx(
@@ -1351,48 +1851,67 @@ var ResizableTable = ({ tableState }) => {
1351
1851
  "table",
1352
1852
  {
1353
1853
  style: {
1354
- width: `${table.getCenterTotalSize()}px`,
1854
+ width: `${totalTableWidth}px`,
1355
1855
  minWidth: "100%",
1356
1856
  tableLayout: "fixed"
1357
1857
  },
1358
- children: /* @__PURE__ */ jsxRuntime.jsx(TableHeader, { children: table.getHeaderGroups().map((headerGroup) => /* @__PURE__ */ jsxRuntime.jsx(TableRow, { children: headerGroup.headers.map((header) => {
1359
- const isPinned = header.column.getIsPinned();
1360
- const isLastLeftPinned = isPinned === "left" && header.column.getIsLastColumn("left");
1361
- const isFirstRightPinned = isPinned === "right" && header.column.getIsFirstColumn("right");
1362
- const columnRelativeDepth = header.depth - header.column.depth;
1363
- if (!header.isPlaceholder && columnRelativeDepth > 1 && header.id === header.column.id) {
1364
- return null;
1365
- }
1366
- let rowSpan = 1;
1367
- if (header.isPlaceholder) {
1368
- const leafs = header.getLeafHeaders();
1369
- rowSpan = leafs[leafs.length - 1].depth - header.depth;
1370
- }
1371
- return /* @__PURE__ */ jsxRuntime.jsxs(
1372
- TableHead,
1373
- {
1374
- "data-last-left-pinned": isLastLeftPinned,
1375
- "data-first-right-pinned": isFirstRightPinned,
1376
- "data-pinned": isPinned,
1377
- style: getResizableCellStyle(header.column, true),
1378
- colSpan: header.colSpan,
1379
- rowSpan,
1380
- children: [
1381
- /* @__PURE__ */ jsxRuntime.jsx(TableHeadCell_default, { header }),
1382
- header.column.getCanResize() && /* @__PURE__ */ jsxRuntime.jsx(
1383
- TableResizer,
1384
- __spreadValues({}, {
1385
- onDoubleClick: () => header.column.resetSize(),
1386
- onMouseDown: header.getResizeHandler(),
1387
- onTouchStart: header.getResizeHandler(),
1388
- className: `resizer ${header.column.getIsResizing() ? "isResizing" : ""}`
1389
- })
1390
- )
1391
- ]
1392
- },
1393
- header.id
1394
- );
1395
- }) }, headerGroup.id)) })
1858
+ children: /* @__PURE__ */ jsxRuntime.jsx(TableHeader, { children: table.getHeaderGroups().map((headerGroup, i) => {
1859
+ const rowStyle = typeof headerRowStyle === "function" ? headerRowStyle(i, headerGroup) : headerRowStyle;
1860
+ return /* @__PURE__ */ jsxRuntime.jsx(TableRow, { style: rowStyle, children: headerGroup.headers.map((header) => {
1861
+ const isPinned = header.column.getIsPinned();
1862
+ const leafHeaders = header.getLeafHeaders();
1863
+ const hasLastLeftPinnedLeaf = leafHeaders.some(
1864
+ (leaf) => leaf.column.getIsPinned() === "left" && leaf.column.getIsLastColumn("left")
1865
+ );
1866
+ const hasFirstRightPinnedLeaf = leafHeaders.some(
1867
+ (leaf) => leaf.column.getIsPinned() === "right" && leaf.column.getIsFirstColumn("right")
1868
+ );
1869
+ const isLastLeftPinned = isPinned === "left" && header.column.getIsLastColumn("left") || hasLastLeftPinnedLeaf;
1870
+ const isFirstRightPinned = isPinned === "right" && header.column.getIsFirstColumn("right") || hasFirstRightPinnedLeaf;
1871
+ const columnRelativeDepth = header.depth - header.column.depth;
1872
+ if (!header.isPlaceholder && columnRelativeDepth > 1 && header.id === header.column.id) {
1873
+ return null;
1874
+ }
1875
+ let rowSpan = 1;
1876
+ if (header.isPlaceholder) {
1877
+ const leafs = header.getLeafHeaders();
1878
+ rowSpan = leafs[leafs.length - 1].depth - header.depth;
1879
+ }
1880
+ return /* @__PURE__ */ jsxRuntime.jsxs(
1881
+ TableHead,
1882
+ {
1883
+ "data-last-left-pinned": isLastLeftPinned,
1884
+ "data-first-right-pinned": isFirstRightPinned,
1885
+ "data-pinned": isPinned,
1886
+ style: __spreadValues(__spreadValues({}, getResizableCellStyle(header.column, true)), rowStyle && {
1887
+ backgroundColor: rowStyle.backgroundColor,
1888
+ height: rowStyle.height,
1889
+ maxHeight: rowStyle.maxHeight,
1890
+ minHeight: rowStyle.minHeight
1891
+ }),
1892
+ colSpan: header.colSpan,
1893
+ rowSpan,
1894
+ sortable: getTableHeadSortModel(header).showSortMenu,
1895
+ filterable: header.column.getCanFilter(),
1896
+ "data-sortable": getTableHeadSortModel(header).showSortMenu,
1897
+ "data-filterable": header.column.getCanFilter(),
1898
+ children: [
1899
+ /* @__PURE__ */ jsxRuntime.jsx(TableHeadCell_default, { header }),
1900
+ header.column.getCanResize() && /* @__PURE__ */ jsxRuntime.jsx(
1901
+ TableResizer,
1902
+ __spreadValues({}, {
1903
+ onDoubleClick: () => header.column.resetSize(),
1904
+ onMouseDown: header.getResizeHandler(),
1905
+ onTouchStart: header.getResizeHandler(),
1906
+ className: `resizer ${header.column.getIsResizing() ? "isResizing" : ""}`
1907
+ })
1908
+ )
1909
+ ]
1910
+ },
1911
+ header.id
1912
+ );
1913
+ }) }, headerGroup.id);
1914
+ }) })
1396
1915
  }
1397
1916
  )
1398
1917
  }
@@ -1401,146 +1920,1560 @@ var ResizableTable = ({ tableState }) => {
1401
1920
  "table",
1402
1921
  {
1403
1922
  style: {
1404
- width: `${table.getCenterTotalSize()}px`,
1923
+ width: `${totalTableWidth}px`,
1405
1924
  minWidth: "100%",
1406
1925
  tableLayout: "fixed"
1407
1926
  },
1408
1927
  children: /* @__PURE__ */ jsxRuntime.jsx(TableBody, { children: isEmpty ? /* @__PURE__ */ jsxRuntime.jsx(TableRow, { children: /* @__PURE__ */ jsxRuntime.jsx(
1409
1928
  TableCell,
1410
1929
  {
1411
- colSpan: table.getAllColumns().length,
1930
+ colSpan: table.getAllColumns().length,
1931
+ style: {
1932
+ height: "200px",
1933
+ textAlign: "center",
1934
+ verticalAlign: "middle"
1935
+ },
1936
+ children: children || emptyElement
1937
+ }
1938
+ ) }) : /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
1939
+ paddingTop > 0 && /* @__PURE__ */ jsxRuntime.jsx(TableRow, { children: /* @__PURE__ */ jsxRuntime.jsx("td", { style: { height: `${paddingTop}px` } }) }),
1940
+ displayedRows.map((rowObj, i) => {
1941
+ const isVirtual = "virtualRow" in rowObj && rowObj.virtualRow;
1942
+ const row = rowObj.row;
1943
+ const cells = typeof row.getVisibleCells === "function" ? row.getVisibleCells() : row;
1944
+ const rowStyle = typeof bodyRowStyle === "function" ? bodyRowStyle(i, row.original) : bodyRowStyle;
1945
+ const cellBackgroundColor = rowStyle == null ? void 0 : rowStyle.backgroundColor;
1946
+ return /* @__PURE__ */ jsxRuntime.jsx(
1947
+ TableRow,
1948
+ {
1949
+ "data-index": isVirtual ? rowObj.virtualRow.index : i,
1950
+ onClick: () => {
1951
+ onClickRow == null ? void 0 : onClickRow(row.original);
1952
+ },
1953
+ className: onClickRow !== void 0 ? "clickable" : "",
1954
+ style: rowStyle,
1955
+ children: cells.map((cell) => {
1956
+ var _a, _b, _c, _d;
1957
+ const isPinned = cell.column.getIsPinned();
1958
+ const isLastLeftPinned = isPinned === "left" && cell.column.getIsLastColumn("left");
1959
+ const isFirstRightPinned = isPinned === "right" && cell.column.getIsFirstColumn("right");
1960
+ return /* @__PURE__ */ jsxRuntime.jsx(
1961
+ TableCell,
1962
+ {
1963
+ "data-last-left-pinned": isLastLeftPinned,
1964
+ "data-first-right-pinned": isFirstRightPinned,
1965
+ "data-no-hover": getColumnActiveHoverDataAttribute(
1966
+ (_a = cell.column.columnDef.meta) == null ? void 0 : _a.activeHover,
1967
+ cell.row.original
1968
+ ),
1969
+ "data-has-custom-style": ((_d = (_c = (_b = cell.column.columnDef.meta) == null ? void 0 : _b.cellProps) == null ? void 0 : _c.style) == null ? void 0 : _d.backgroundColor) ? "true" : void 0,
1970
+ style: __spreadValues(__spreadValues({}, getResizableCellStyle(cell.column)), cellBackgroundColor && {
1971
+ backgroundColor: cellBackgroundColor
1972
+ }),
1973
+ children: reactTable.flexRender(cell.column.columnDef.cell, cell.getContext())
1974
+ },
1975
+ cell.id
1976
+ );
1977
+ })
1978
+ },
1979
+ typeof row.id !== "undefined" ? row.id : i
1980
+ );
1981
+ }),
1982
+ paddingBottom > 0 && /* @__PURE__ */ jsxRuntime.jsx(TableRow, { children: /* @__PURE__ */ jsxRuntime.jsx("td", { style: { height: `${paddingBottom}px` } }) }),
1983
+ emptyRowCount !== 0 && displayedRows.length < emptyRowCount && Array.from({ length: emptyRowCount - displayedRows.length }).map((_, index) => /* @__PURE__ */ jsxRuntime.jsx(TableRow, { "data-empty": true, children: /* @__PURE__ */ jsxRuntime.jsx(
1984
+ TableCell,
1985
+ {
1986
+ colSpan: table.getAllColumns().length,
1987
+ style: {
1988
+ height: `${60}px`
1989
+ }
1990
+ }
1991
+ ) }, `empty-row-${index}`))
1992
+ ] }) })
1993
+ }
1994
+ ) }) })
1995
+ ] });
1996
+ };
1997
+ var distributeResponsiveWidths = ({
1998
+ baseWidths,
1999
+ autoIndexes,
2000
+ maxWidths,
2001
+ targetTotalWidth
2002
+ }) => {
2003
+ const widths = [...baseWidths];
2004
+ const baseTotal = baseWidths.reduce((sum, width) => sum + width, 0);
2005
+ let remaining = Math.max(0, targetTotalWidth - baseTotal);
2006
+ if (remaining === 0 || autoIndexes.length === 0)
2007
+ return widths;
2008
+ const growable = new Set(autoIndexes);
2009
+ while (remaining > 0.01 && growable.size > 0) {
2010
+ const share = remaining / growable.size;
2011
+ let distributed = 0;
2012
+ Array.from(growable).forEach((index) => {
2013
+ var _a;
2014
+ const maxWidth = (_a = maxWidths[index]) != null ? _a : Number.POSITIVE_INFINITY;
2015
+ const capacity = Math.max(0, maxWidth - widths[index]);
2016
+ const delta = Math.min(share, capacity);
2017
+ widths[index] += delta;
2018
+ distributed += delta;
2019
+ if (capacity <= share + 0.01)
2020
+ growable.delete(index);
2021
+ });
2022
+ if (distributed <= 0.01)
2023
+ break;
2024
+ remaining -= distributed;
2025
+ }
2026
+ return widths;
2027
+ };
2028
+ var useResponsiveViewportWidth = (tableContainerRef, headerRef) => {
2029
+ const subscribe = React3.useCallback(
2030
+ (onStoreChange) => {
2031
+ let rafId = null;
2032
+ const notifyWithBatch = () => {
2033
+ if (rafId !== null)
2034
+ return;
2035
+ rafId = window.requestAnimationFrame(() => {
2036
+ rafId = null;
2037
+ onStoreChange();
2038
+ });
2039
+ };
2040
+ const resizeObserver = new ResizeObserver(() => {
2041
+ notifyWithBatch();
2042
+ });
2043
+ if (tableContainerRef.current)
2044
+ resizeObserver.observe(tableContainerRef.current);
2045
+ if (headerRef.current)
2046
+ resizeObserver.observe(headerRef.current);
2047
+ window.addEventListener("resize", notifyWithBatch);
2048
+ return () => {
2049
+ if (rafId !== null) {
2050
+ window.cancelAnimationFrame(rafId);
2051
+ rafId = null;
2052
+ }
2053
+ resizeObserver.disconnect();
2054
+ window.removeEventListener("resize", notifyWithBatch);
2055
+ };
2056
+ },
2057
+ [tableContainerRef, headerRef]
2058
+ );
2059
+ const getSnapshot = React3.useCallback(
2060
+ () => {
2061
+ var _a, _b, _c, _d;
2062
+ return (_d = (_c = (_a = tableContainerRef.current) == null ? void 0 : _a.clientWidth) != null ? _c : (_b = headerRef.current) == null ? void 0 : _b.clientWidth) != null ? _d : 0;
2063
+ },
2064
+ [tableContainerRef, headerRef]
2065
+ );
2066
+ return React3.useSyncExternalStore(subscribe, getSnapshot, getSnapshot);
2067
+ };
2068
+ var useResponsiveColumnLayout = ({
2069
+ unpinnedColumns,
2070
+ leftPinnedColumns,
2071
+ rightPinnedColumns,
2072
+ viewportWidth
2073
+ }) => {
2074
+ const getColumnMaxSize = React3.useCallback((column) => {
2075
+ var _a;
2076
+ const maxSize = (_a = column == null ? void 0 : column.columnDef) == null ? void 0 : _a.maxSize;
2077
+ return typeof maxSize === "number" && maxSize > 0 ? maxSize : Number.POSITIVE_INFINITY;
2078
+ }, []);
2079
+ const getActualColumnSize = React3.useCallback(
2080
+ (column) => {
2081
+ var _a;
2082
+ if (!column)
2083
+ return 150;
2084
+ const tableSize = (_a = column.getSize) == null ? void 0 : _a.call(column);
2085
+ if (typeof tableSize === "number" && Number.isFinite(tableSize) && tableSize > 0)
2086
+ return tableSize;
2087
+ const size = column.columnDef.size;
2088
+ if (typeof size === "number" && size > 0)
2089
+ return size;
2090
+ const minSize = column.columnDef.minSize;
2091
+ if (typeof minSize === "number" && minSize > 0) {
2092
+ return Math.min(minSize, getColumnMaxSize(column));
2093
+ }
2094
+ return Math.min(150, getColumnMaxSize(column));
2095
+ },
2096
+ [getColumnMaxSize]
2097
+ );
2098
+ const leftPinnedWidth = React3.useMemo(
2099
+ () => leftPinnedColumns.reduce((sum, header) => sum + getActualColumnSize(header.column), 0),
2100
+ [leftPinnedColumns, getActualColumnSize]
2101
+ );
2102
+ const rightPinnedWidth = React3.useMemo(
2103
+ () => rightPinnedColumns.reduce((sum, header) => sum + getActualColumnSize(header.column), 0),
2104
+ [rightPinnedColumns, getActualColumnSize]
2105
+ );
2106
+ const baseUnpinnedWidths = React3.useMemo(
2107
+ () => unpinnedColumns.map((header) => getActualColumnSize(header.column)),
2108
+ [unpinnedColumns, getActualColumnSize]
2109
+ );
2110
+ const autoColumnIndexes = React3.useMemo(
2111
+ () => unpinnedColumns.map((header, index) => ({ index, size: header.column.columnDef.size })).filter(({ size }) => typeof size !== "number").map(({ index }) => index),
2112
+ [unpinnedColumns]
2113
+ );
2114
+ const baseUnpinnedWidth = React3.useMemo(
2115
+ () => baseUnpinnedWidths.reduce((sum, width) => sum + width, 0),
2116
+ [baseUnpinnedWidths]
2117
+ );
2118
+ const availableUnpinnedWidth = Math.max(0, viewportWidth - leftPinnedWidth - rightPinnedWidth);
2119
+ const targetUnpinnedWidth = Math.max(baseUnpinnedWidth, availableUnpinnedWidth);
2120
+ const unpinnedMaxWidths = React3.useMemo(
2121
+ () => unpinnedColumns.map((header) => getColumnMaxSize(header.column)),
2122
+ [getColumnMaxSize, unpinnedColumns]
2123
+ );
2124
+ const computedUnpinnedWidths = React3.useMemo(
2125
+ () => distributeResponsiveWidths({
2126
+ baseWidths: baseUnpinnedWidths,
2127
+ autoIndexes: autoColumnIndexes,
2128
+ maxWidths: unpinnedMaxWidths,
2129
+ targetTotalWidth: targetUnpinnedWidth
2130
+ }),
2131
+ [autoColumnIndexes, baseUnpinnedWidths, targetUnpinnedWidth, unpinnedMaxWidths]
2132
+ );
2133
+ const totalUnpinnedWidth = React3.useMemo(
2134
+ () => computedUnpinnedWidths.reduce((sum, width) => sum + width, 0),
2135
+ [computedUnpinnedWidths]
2136
+ );
2137
+ const getUnpinnedColumnWidth = React3.useCallback(
2138
+ (index) => {
2139
+ var _a;
2140
+ return (_a = computedUnpinnedWidths[index]) != null ? _a : 150;
2141
+ },
2142
+ [computedUnpinnedWidths]
2143
+ );
2144
+ const totalTableWidth = React3.useMemo(
2145
+ () => leftPinnedWidth + totalUnpinnedWidth + rightPinnedWidth,
2146
+ [leftPinnedWidth, totalUnpinnedWidth, rightPinnedWidth]
2147
+ );
2148
+ return {
2149
+ getActualColumnSize,
2150
+ getUnpinnedColumnWidth,
2151
+ totalUnpinnedWidth,
2152
+ totalTableWidth
2153
+ };
2154
+ };
2155
+ var PinnedColumnEdgeShadow = styled3__default.default.div`
2156
+ position: absolute;
2157
+ top: 0;
2158
+ right: -4px;
2159
+ height: 100%;
2160
+ width: 4px;
2161
+ pointer-events: none;
2162
+ z-index: 11;
2163
+ background: linear-gradient(to right, rgba(0, 0, 0, 0.1), transparent);
2164
+ `;
2165
+ var VirtualTableRoot = styled3__default.default.div`
2166
+ position: relative;
2167
+ width: 100%;
2168
+ `;
2169
+ var VirtualTableScrollAreaInner = styled3__default.default.div`
2170
+ position: relative;
2171
+ width: 100%;
2172
+ `;
2173
+ var VirtualTableHeaderRoot = styled3__default.default.div`
2174
+ width: 100%;
2175
+ z-index: 11;
2176
+ position: sticky;
2177
+ top: 0;
2178
+ overflow-x: scroll;
2179
+ -ms-overflow-style: none;
2180
+ scrollbar-width: none;
2181
+
2182
+ &::-webkit-scrollbar {
2183
+ display: none;
2184
+ }
2185
+ `;
2186
+ var VirtualTableHeaderInner = styled3__default.default.div`
2187
+ background-color: ${base.colorTokens.neutral100};
2188
+ `;
2189
+ var VirtualTableHeaderRow = styled3__default.default.div`
2190
+ display: flex;
2191
+ width: ${({ $tableWidthPx }) => `${$tableWidthPx}px`};
2192
+ min-width: 100%;
2193
+ `;
2194
+ var VirtualTableGroupHeaderCell = styled3__default.default.div`
2195
+ display: flex;
2196
+ align-items: center;
2197
+ padding: 8px;
2198
+ height: 48px;
2199
+ font-weight: 400;
2200
+ line-height: 16px;
2201
+ font-size: 13px;
2202
+ border-bottom: 1px solid ${base.colorTokens.neutral200};
2203
+ background-color: ${base.colorTokens.neutral100};
2204
+ box-sizing: border-box;
2205
+ border-right: 1px solid ${base.colorTokens.neutral200};
2206
+
2207
+ &[data-last-left-pinned='true'] {
2208
+ border-right: none;
2209
+ }
2210
+
2211
+ position: relative;
2212
+ z-index: 0;
2213
+
2214
+ &[data-pinned='left'],
2215
+ &[data-pinned='right'] {
2216
+ position: sticky;
2217
+ z-index: 10;
2218
+ }
2219
+ `;
2220
+ var VirtualTableLeafHeaderPinnedLeft = styled3__default.default.div`
2221
+ display: flex;
2222
+ align-items: center;
2223
+ padding: 8px;
2224
+ height: 48px;
2225
+ font-weight: 400;
2226
+ line-height: 16px;
2227
+ font-size: 13px;
2228
+ border-bottom: 1px solid ${base.colorTokens.neutral200};
2229
+ background-color: ${base.colorTokens.neutral100};
2230
+ box-sizing: border-box;
2231
+ border-right: 1px solid ${base.colorTokens.neutral200};
2232
+ position: sticky;
2233
+ z-index: 10;
2234
+
2235
+ &[data-last-left-pinned='true'] {
2236
+ border-right: none;
2237
+ }
2238
+ `;
2239
+ var VirtualTableVirtualizedColumnsOuter = styled3__default.default.div`
2240
+ display: flex;
2241
+ width: ${({ $unpinnedWidthPx }) => `${$unpinnedWidthPx}px`};
2242
+ min-width: ${({ $unpinnedWidthPx }) => `${$unpinnedWidthPx}px`};
2243
+ position: relative;
2244
+ flex-shrink: 0;
2245
+ overflow: hidden;
2246
+ `;
2247
+ var VirtualTableHorizontalVirtualTrack = styled3__default.default.div`
2248
+ display: flex;
2249
+ transform: translateX(${(p) => p.$translateX}px);
2250
+ will-change: transform;
2251
+ ${({ $fillHeight }) => $fillHeight ? `height: 100%;` : ""}
2252
+ `;
2253
+ var VirtualTableLeafHeaderUnpinnedCell = styled3__default.default.div`
2254
+ display: flex;
2255
+ align-items: center;
2256
+ padding: 8px;
2257
+ height: 48px;
2258
+ font-weight: 400;
2259
+ line-height: 16px;
2260
+ font-size: 13px;
2261
+ border-bottom: 1px solid ${base.colorTokens.neutral200};
2262
+ border-right: 1px solid ${base.colorTokens.neutral200};
2263
+ background-color: ${base.colorTokens.neutral100};
2264
+ box-sizing: border-box;
2265
+ flex-shrink: 0;
2266
+ `;
2267
+ var VirtualTableLeafHeaderPinnedRight = styled3__default.default.div`
2268
+ display: flex;
2269
+ align-items: center;
2270
+ padding: 8px;
2271
+ height: 48px;
2272
+ font-weight: 400;
2273
+ line-height: 16px;
2274
+ font-size: 13px;
2275
+ border-bottom: 1px solid ${base.colorTokens.neutral200};
2276
+ border-right: none;
2277
+ background-color: ${base.colorTokens.neutral100};
2278
+ box-sizing: border-box;
2279
+ position: sticky;
2280
+ z-index: 10;
2281
+ `;
2282
+ var VirtualTableBodyRow = styled3__default.default.div`
2283
+ display: flex;
2284
+ width: ${({ $tableWidthPx }) => `${$tableWidthPx}px`};
2285
+ min-width: 100%;
2286
+ height: ${({ $rowHeightPx }) => `${$rowHeightPx != null ? $rowHeightPx : 60}px`};
2287
+ min-height: ${({ $rowHeightPx }) => `${$rowHeightPx != null ? $rowHeightPx : 60}px`};
2288
+ border-bottom: 1px solid ${base.colorTokens.neutral200};
2289
+ `;
2290
+ var VirtualTableBodyPinnedCell = styled3__default.default.div`
2291
+ display: flex;
2292
+ align-items: center;
2293
+ padding: 8px;
2294
+ height: 100%;
2295
+ background-color: ${base.colorTokens.neutral0};
2296
+ position: sticky;
2297
+ z-index: 10;
2298
+ box-sizing: border-box;
2299
+ `;
2300
+ var VirtualTableBodyUnpinnedSlice = styled3__default.default.div`
2301
+ display: flex;
2302
+ width: ${({ $unpinnedWidthPx }) => `${$unpinnedWidthPx}px`};
2303
+ min-width: ${({ $unpinnedWidthPx }) => `${$unpinnedWidthPx}px`};
2304
+ position: relative;
2305
+ flex-shrink: 0;
2306
+ overflow: hidden;
2307
+ `;
2308
+ var VirtualTableBodyUnpinnedCell = styled3__default.default.div`
2309
+ display: flex;
2310
+ align-items: center;
2311
+ padding: 8px;
2312
+ height: 100%;
2313
+ background-color: ${base.colorTokens.neutral0};
2314
+ box-sizing: border-box;
2315
+ flex-shrink: 0;
2316
+ `;
2317
+ var VirtualTableBodyGrid = styled3__default.default.div`
2318
+ display: grid;
2319
+ height: ${({ $totalHeightPx }) => `${$totalHeightPx}px`};
2320
+ position: relative;
2321
+ color: ${base.colorTokens.neutral700};
2322
+ font-size: 14px;
2323
+ overflow-x: scroll;
2324
+ overflow-y: hidden;
2325
+ -ms-overflow-style: none;
2326
+ scrollbar-width: none;
2327
+
2328
+ &::-webkit-scrollbar {
2329
+ display: none;
2330
+ }
2331
+ `;
2332
+ var VirtualTableVerticalVirtualTrack = styled3__default.default.div`
2333
+ position: absolute;
2334
+ top: 0;
2335
+ left: 0;
2336
+ width: 100%;
2337
+ transform: translateY(${(p) => p.$translateY}px);
2338
+ will-change: transform;
2339
+ display: flex;
2340
+ flex-direction: column;
2341
+ `;
2342
+ var CellSkeleton2 = () => /* @__PURE__ */ jsxRuntime.jsx(base.Skeleton, { styleVar: "rectangle", width: "80%", height: "20px" });
2343
+ var GroupHeaderRow = React3__default.default.memo(({ headerGroup, getActualColumnSize }) => {
2344
+ return /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children: headerGroup.headers.map((header) => {
2345
+ const leafHeaders = header.getLeafHeaders ? header.getLeafHeaders() : [];
2346
+ const groupId = header.column.id;
2347
+ const filteredLeafHeaders = leafHeaders.filter((leaf) => leaf.column.id !== groupId);
2348
+ const firstLeaf = filteredLeafHeaders[0];
2349
+ const firstLeafPinned = firstLeaf == null ? void 0 : firstLeaf.column.getIsPinned();
2350
+ const totalWidth = filteredLeafHeaders.reduce((sum, leaf) => {
2351
+ return sum + getActualColumnSize(leaf.column);
2352
+ }, 0);
2353
+ const hasLastLeftPinnedLeaf = filteredLeafHeaders.some(
2354
+ (leaf) => leaf.column.getIsPinned() === "left" && leaf.column.getIsLastColumn("left")
2355
+ );
2356
+ const hasFirstRightPinnedLeaf = filteredLeafHeaders.some(
2357
+ (leaf) => leaf.column.getIsPinned() === "right" && leaf.column.getIsFirstColumn("right")
2358
+ );
2359
+ const positionStyle = {
2360
+ width: `${totalWidth}px`,
2361
+ minWidth: `${totalWidth}px`,
2362
+ maxWidth: `${totalWidth}px`,
2363
+ left: firstLeafPinned === "left" ? `${firstLeaf == null ? void 0 : firstLeaf.column.getStart("left")}px` : void 0,
2364
+ right: firstLeafPinned === "right" ? `${firstLeaf == null ? void 0 : firstLeaf.column.getAfter("right")}px` : void 0
2365
+ };
2366
+ return /* @__PURE__ */ jsxRuntime.jsxs(
2367
+ VirtualTableGroupHeaderCell,
2368
+ {
2369
+ "data-last-left-pinned": hasLastLeftPinnedLeaf,
2370
+ "data-first-right-pinned": hasFirstRightPinnedLeaf,
2371
+ "data-pinned": firstLeafPinned || void 0,
2372
+ style: positionStyle,
2373
+ children: [
2374
+ header.isPlaceholder ? null : /* @__PURE__ */ jsxRuntime.jsx(TableHeadCell_default, { header }),
2375
+ hasLastLeftPinnedLeaf && /* @__PURE__ */ jsxRuntime.jsx(PinnedColumnEdgeShadow, {})
2376
+ ]
2377
+ },
2378
+ header.id
2379
+ );
2380
+ }) });
2381
+ });
2382
+ GroupHeaderRow.displayName = "GroupHeaderRow";
2383
+ var LeafHeaderRow = React3__default.default.memo(
2384
+ ({
2385
+ leftPinnedColumns,
2386
+ rightPinnedColumns,
2387
+ unpinnedColumns,
2388
+ virtualItems,
2389
+ totalUnpinnedWidth,
2390
+ getActualColumnSize,
2391
+ getUnpinnedColumnWidth
2392
+ }) => {
2393
+ var _a, _b;
2394
+ const leftPinnedPrepared = React3.useMemo(
2395
+ () => leftPinnedColumns.map((header) => {
2396
+ const isPinned = header.column.getIsPinned();
2397
+ const isLastLeftPinned = isPinned === "left" && header.column.getIsLastColumn("left");
2398
+ const headerWidth = getActualColumnSize(header.column);
2399
+ const leftPosition = header.column.getStart("left");
2400
+ return {
2401
+ header,
2402
+ isPinned,
2403
+ isLastLeftPinned,
2404
+ style: {
2405
+ width: `${headerWidth}px`,
2406
+ minWidth: `${headerWidth}px`,
2407
+ left: `${leftPosition}px`
2408
+ }
2409
+ };
2410
+ }),
2411
+ [leftPinnedColumns, getActualColumnSize]
2412
+ );
2413
+ const rightPinnedPrepared = React3.useMemo(
2414
+ () => rightPinnedColumns.map((header) => {
2415
+ const isPinned = header.column.getIsPinned();
2416
+ const isFirstRightPinned = isPinned === "right" && header.column.getIsFirstColumn("right");
2417
+ const headerWidth = getActualColumnSize(header.column);
2418
+ const rightPosition = header.column.getAfter("right");
2419
+ return {
2420
+ header,
2421
+ isPinned,
2422
+ isFirstRightPinned,
2423
+ style: {
2424
+ width: `${headerWidth}px`,
2425
+ minWidth: `${headerWidth}px`,
2426
+ right: `${rightPosition}px`
2427
+ }
2428
+ };
2429
+ }),
2430
+ [rightPinnedColumns, getActualColumnSize]
2431
+ );
2432
+ const virtualItemsLayoutKey = React3.useMemo(
2433
+ () => virtualItems.map((v) => `${v.index}:${v.start}`).join("|"),
2434
+ [virtualItems]
2435
+ );
2436
+ const unpinnedPrepared = React3.useMemo(() => {
2437
+ return virtualItems.map((virtualColumn) => {
2438
+ const header = unpinnedColumns[virtualColumn.index];
2439
+ if (!header)
2440
+ return null;
2441
+ const columnWidth = getUnpinnedColumnWidth(virtualColumn.index);
2442
+ return {
2443
+ header,
2444
+ style: {
2445
+ width: `${columnWidth}px`,
2446
+ minWidth: `${columnWidth}px`,
2447
+ maxWidth: `${columnWidth}px`
2448
+ }
2449
+ };
2450
+ });
2451
+ }, [virtualItemsLayoutKey, unpinnedColumns, getUnpinnedColumnWidth]);
2452
+ return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
2453
+ leftPinnedPrepared.map(({ header, isPinned, isLastLeftPinned, style }) => /* @__PURE__ */ jsxRuntime.jsxs(
2454
+ VirtualTableLeafHeaderPinnedLeft,
2455
+ {
2456
+ "data-last-left-pinned": isLastLeftPinned,
2457
+ "data-pinned": isPinned,
2458
+ style,
2459
+ children: [
2460
+ header.isPlaceholder ? null : /* @__PURE__ */ jsxRuntime.jsx(TableHeadCell_default, { header }),
2461
+ isLastLeftPinned && /* @__PURE__ */ jsxRuntime.jsx(PinnedColumnEdgeShadow, {})
2462
+ ]
2463
+ },
2464
+ header.id
2465
+ )),
2466
+ /* @__PURE__ */ jsxRuntime.jsx(VirtualTableVirtualizedColumnsOuter, { $unpinnedWidthPx: totalUnpinnedWidth, children: /* @__PURE__ */ jsxRuntime.jsx(VirtualTableHorizontalVirtualTrack, { $translateX: (_b = (_a = virtualItems[0]) == null ? void 0 : _a.start) != null ? _b : 0, children: unpinnedPrepared.map((item) => {
2467
+ if (!item)
2468
+ return null;
2469
+ const { header, style } = item;
2470
+ return /* @__PURE__ */ jsxRuntime.jsx(VirtualTableLeafHeaderUnpinnedCell, { style, children: /* @__PURE__ */ jsxRuntime.jsx(TableHeadCell_default, { header }) }, header.id);
2471
+ }) }) }),
2472
+ rightPinnedPrepared.map(({ header, isPinned, isFirstRightPinned, style }) => /* @__PURE__ */ jsxRuntime.jsx(
2473
+ VirtualTableLeafHeaderPinnedRight,
2474
+ {
2475
+ "data-first-right-pinned": isFirstRightPinned,
2476
+ "data-pinned": isPinned,
2477
+ style,
2478
+ children: header.isPlaceholder ? null : /* @__PURE__ */ jsxRuntime.jsx(TableHeadCell_default, { header })
2479
+ },
2480
+ header.id
2481
+ ))
2482
+ ] });
2483
+ }
2484
+ );
2485
+ LeafHeaderRow.displayName = "LeafHeaderRow";
2486
+ var VirtualTableHeader = ({
2487
+ table,
2488
+ headerRef,
2489
+ getFixedCellStyle: _getFixedCellStyle,
2490
+ tableContainerRef: _tableContainerRef,
2491
+ scrollViewportRef: _scrollViewportRef,
2492
+ onVirtualItemsChange,
2493
+ onHeaderScroll,
2494
+ viewportWidth
2495
+ }) => {
2496
+ const headerGroups = table.getHeaderGroups();
2497
+ const leafHeaderGroup = headerGroups[headerGroups.length - 1];
2498
+ const allHeaders = React3.useMemo(() => {
2499
+ const headers = (leafHeaderGroup == null ? void 0 : leafHeaderGroup.headers) || [];
2500
+ return headers.filter((h) => {
2501
+ const columns = h.column.columnDef.columns;
2502
+ return !columns || columns.length === 0;
2503
+ });
2504
+ }, [leafHeaderGroup]);
2505
+ const { leftPinnedColumns, rightPinnedColumns, unpinnedColumns } = React3.useMemo(() => {
2506
+ const left = allHeaders.filter((h) => h.column.getIsPinned() === "left");
2507
+ const right = allHeaders.filter((h) => h.column.getIsPinned() === "right");
2508
+ const unpinned = allHeaders.filter((h) => !h.column.getIsPinned());
2509
+ return {
2510
+ leftPinnedColumns: left,
2511
+ rightPinnedColumns: right,
2512
+ unpinnedColumns: unpinned
2513
+ };
2514
+ }, [allHeaders]);
2515
+ const { getActualColumnSize, getUnpinnedColumnWidth, totalUnpinnedWidth, totalTableWidth } = useResponsiveColumnLayout({
2516
+ unpinnedColumns,
2517
+ leftPinnedColumns,
2518
+ rightPinnedColumns,
2519
+ viewportWidth
2520
+ });
2521
+ const estimateSize = React3.useCallback((index) => getUnpinnedColumnWidth(index), [getUnpinnedColumnWidth]);
2522
+ const columnVirtualizer = reactVirtual.useVirtualizer({
2523
+ // flushSync는 중첩 렌더/레이아웃 효과와 충돌 시 경고를 유발하므로 비활성화
2524
+ // useFlushSync: false,
2525
+ count: unpinnedColumns.length,
2526
+ getScrollElement: () => headerRef.current,
2527
+ estimateSize,
2528
+ horizontal: true,
2529
+ overscan: 5
2530
+ });
2531
+ const virtualItems = columnVirtualizer.getVirtualItems();
2532
+ React3__default.default.useEffect(() => {
2533
+ if (onVirtualItemsChange) {
2534
+ onVirtualItemsChange(virtualItems);
2535
+ }
2536
+ }, [virtualItems, onVirtualItemsChange]);
2537
+ React3__default.default.useEffect(() => {
2538
+ if (headerRef.current) {
2539
+ const timeoutId = setTimeout(() => {
2540
+ columnVirtualizer.measure();
2541
+ }, 0);
2542
+ return () => clearTimeout(timeoutId);
2543
+ }
2544
+ }, [columnVirtualizer, headerRef]);
2545
+ const handleHeaderScroll = React3.useCallback(() => {
2546
+ if (!headerRef.current || !onHeaderScroll)
2547
+ return;
2548
+ onHeaderScroll();
2549
+ }, [headerRef, onHeaderScroll]);
2550
+ return /* @__PURE__ */ jsxRuntime.jsx(VirtualTableHeaderRoot, { ref: headerRef, onScroll: handleHeaderScroll, children: /* @__PURE__ */ jsxRuntime.jsx(VirtualTableHeaderInner, { children: headerGroups.map((headerGroup, groupIndex) => {
2551
+ const isLeafRow = groupIndex === headerGroups.length - 1;
2552
+ return /* @__PURE__ */ jsxRuntime.jsx(VirtualTableHeaderRow, { $tableWidthPx: totalTableWidth, children: isLeafRow ? /* @__PURE__ */ jsxRuntime.jsx(
2553
+ LeafHeaderRow,
2554
+ {
2555
+ leftPinnedColumns,
2556
+ rightPinnedColumns,
2557
+ unpinnedColumns,
2558
+ virtualItems,
2559
+ totalUnpinnedWidth,
2560
+ getActualColumnSize,
2561
+ getUnpinnedColumnWidth
2562
+ }
2563
+ ) : /* @__PURE__ */ jsxRuntime.jsx(GroupHeaderRow, { headerGroup, getActualColumnSize }) }, headerGroup.id);
2564
+ }) }) });
2565
+ };
2566
+ if (typeof VirtualTableHeader === "object" && VirtualTableHeader !== null) {
2567
+ VirtualTableHeader.displayName = "VirtualTableHeader";
2568
+ }
2569
+ var TableBodyRow = React3__default.default.memo(
2570
+ ({
2571
+ row,
2572
+ virtualRow,
2573
+ rowVirtualizer,
2574
+ getFixedCellStyle,
2575
+ tableContainerRef: _tableContainerRef,
2576
+ columnVirtualizer,
2577
+ unpinnedColumns,
2578
+ scrollMargin: _scrollMargin = 0,
2579
+ totalUnpinnedWidth,
2580
+ totalTableWidth,
2581
+ getUnpinnedColumnWidth,
2582
+ headerVirtualItems,
2583
+ isLoading = false,
2584
+ bodyRowStyle
2585
+ }) => {
2586
+ var _a, _b;
2587
+ const { style: rowStyle, heightPx: rowHeightPx } = resolveBodyRowStyle(
2588
+ bodyRowStyle,
2589
+ virtualRow.index,
2590
+ row.original
2591
+ );
2592
+ const cells = row.getVisibleCells();
2593
+ const { leftPinnedCells, rightPinnedCells, unpinnedCells } = React3.useMemo(() => {
2594
+ const left = cells.filter((cell) => cell.column.getIsPinned() === "left");
2595
+ const right = cells.filter((cell) => cell.column.getIsPinned() === "right");
2596
+ const unpinnedCellsMap = new Map(
2597
+ cells.filter((cell) => !cell.column.getIsPinned()).map((cell) => [cell.column.id, cell])
2598
+ );
2599
+ const unpinned = unpinnedColumns.map((header) => unpinnedCellsMap.get(header.column.id)).filter((cell) => cell !== void 0);
2600
+ return {
2601
+ leftPinnedCells: left,
2602
+ rightPinnedCells: right,
2603
+ unpinnedCells: unpinned
2604
+ };
2605
+ }, [cells, unpinnedColumns]);
2606
+ const hasPinned = React3.useMemo(() => cells.some((cell) => cell.column.getIsPinned()), [cells]);
2607
+ const virtualItems = columnVirtualizer.getVirtualItems();
2608
+ const effectiveVirtualItems = headerVirtualItems && headerVirtualItems.length > 0 ? headerVirtualItems : virtualItems;
2609
+ return /* @__PURE__ */ jsxRuntime.jsxs(
2610
+ VirtualTableBodyRow,
2611
+ {
2612
+ "data-index": virtualRow.index,
2613
+ "data-has-pinned": hasPinned,
2614
+ ref: (node) => rowVirtualizer.measureElement(node),
2615
+ $tableWidthPx: totalTableWidth,
2616
+ $rowHeightPx: rowHeightPx,
2617
+ style: rowStyle,
2618
+ children: [
2619
+ leftPinnedCells.map((cell) => {
2620
+ var _a2, _b2, _c, _d, _e, _f;
2621
+ const isPinned = cell.column.getIsPinned();
2622
+ const isLastLeftPinned = isPinned === "left" && cell.column.getIsLastColumn("left");
2623
+ const leftPosition = cell.column.getStart("left");
2624
+ const size = cell.column.columnDef.size;
2625
+ const minSize = cell.column.columnDef.minSize;
2626
+ const cellWidth = typeof size === "number" && size > 0 ? size : typeof minSize === "number" && minSize > 0 ? minSize : 150;
2627
+ return /* @__PURE__ */ jsxRuntime.jsxs(
2628
+ VirtualTableBodyPinnedCell,
2629
+ {
2630
+ "data-last-left-pinned": isLastLeftPinned,
2631
+ "data-pinned": isPinned,
2632
+ "data-no-hover": getColumnActiveHoverDataAttribute(
2633
+ (_a2 = cell.column.columnDef.meta) == null ? void 0 : _a2.activeHover,
2634
+ cell.row.original
2635
+ ),
2636
+ "data-has-custom-style": ((_d = (_c = (_b2 = cell.column.columnDef.meta) == null ? void 0 : _b2.cellProps) == null ? void 0 : _c.style) == null ? void 0 : _d.backgroundColor) ? "true" : void 0,
2637
+ style: __spreadProps(__spreadValues({}, ((_f = (_e = cell.column.columnDef.meta) == null ? void 0 : _e.cellProps) == null ? void 0 : _f.style) || {}), {
2638
+ width: `${cellWidth}px`,
2639
+ minWidth: `${cellWidth}px`,
2640
+ left: `${leftPosition}px`
2641
+ }),
2642
+ children: [
2643
+ isLoading ? /* @__PURE__ */ jsxRuntime.jsx(CellSkeleton2, {}) : reactTable.flexRender(cell.column.columnDef.cell, cell.getContext()),
2644
+ isLastLeftPinned && /* @__PURE__ */ jsxRuntime.jsx(PinnedColumnEdgeShadow, {})
2645
+ ]
2646
+ },
2647
+ cell.id
2648
+ );
2649
+ }),
2650
+ /* @__PURE__ */ jsxRuntime.jsx(VirtualTableBodyUnpinnedSlice, { $unpinnedWidthPx: totalUnpinnedWidth, children: /* @__PURE__ */ jsxRuntime.jsx(VirtualTableHorizontalVirtualTrack, { $translateX: (_b = (_a = effectiveVirtualItems[0]) == null ? void 0 : _a.start) != null ? _b : 0, $fillHeight: true, children: effectiveVirtualItems.map((virtualColumn) => {
2651
+ var _b2, _c, _d, _e;
2652
+ const header = unpinnedColumns[virtualColumn.index];
2653
+ if (!header)
2654
+ return null;
2655
+ const cell = unpinnedCells[virtualColumn.index];
2656
+ if (!cell)
2657
+ return null;
2658
+ const baseStyle = getFixedCellStyle(cell.column);
2659
+ const _a2 = baseStyle, restBaseStyle = __objRest(_a2, [
2660
+ "left",
2661
+ "right",
2662
+ "position",
2663
+ "width",
2664
+ "transform"
2665
+ ]);
2666
+ const columnWidth = getUnpinnedColumnWidth(virtualColumn.index);
2667
+ return /* @__PURE__ */ jsxRuntime.jsx(
2668
+ VirtualTableBodyUnpinnedCell,
2669
+ {
2670
+ "data-no-hover": getColumnActiveHoverDataAttribute(
2671
+ (_b2 = cell.column.columnDef.meta) == null ? void 0 : _b2.activeHover,
2672
+ cell.row.original
2673
+ ),
2674
+ "data-has-custom-style": ((_e = (_d = (_c = cell.column.columnDef.meta) == null ? void 0 : _c.cellProps) == null ? void 0 : _d.style) == null ? void 0 : _e.backgroundColor) ? "true" : void 0,
2675
+ style: __spreadProps(__spreadValues({}, restBaseStyle), {
2676
+ width: `${columnWidth}px`,
2677
+ minWidth: `${columnWidth}px`,
2678
+ maxWidth: `${columnWidth}px`
2679
+ }),
2680
+ children: isLoading ? /* @__PURE__ */ jsxRuntime.jsx(CellSkeleton2, {}) : reactTable.flexRender(cell.column.columnDef.cell, cell.getContext())
2681
+ },
2682
+ cell.id
2683
+ );
2684
+ }) }) }),
2685
+ rightPinnedCells.map((cell) => {
2686
+ var _a2, _b2, _c, _d, _e, _f;
2687
+ const isPinned = cell.column.getIsPinned();
2688
+ const isFirstRightPinned = isPinned === "right" && cell.column.getIsFirstColumn("right");
2689
+ const rightPosition = cell.column.getAfter("right");
2690
+ const size = cell.column.columnDef.size;
2691
+ const minSize = cell.column.columnDef.minSize;
2692
+ const cellWidth = typeof size === "number" && size > 0 ? size : typeof minSize === "number" && minSize > 0 ? minSize : 150;
2693
+ return /* @__PURE__ */ jsxRuntime.jsx(
2694
+ VirtualTableBodyPinnedCell,
2695
+ {
2696
+ "data-first-right-pinned": isFirstRightPinned,
2697
+ "data-pinned": isPinned,
2698
+ "data-no-hover": getColumnActiveHoverDataAttribute(
2699
+ (_a2 = cell.column.columnDef.meta) == null ? void 0 : _a2.activeHover,
2700
+ cell.row.original
2701
+ ),
2702
+ "data-has-custom-style": ((_d = (_c = (_b2 = cell.column.columnDef.meta) == null ? void 0 : _b2.cellProps) == null ? void 0 : _c.style) == null ? void 0 : _d.backgroundColor) ? "true" : void 0,
2703
+ style: __spreadProps(__spreadValues({}, ((_f = (_e = cell.column.columnDef.meta) == null ? void 0 : _e.cellProps) == null ? void 0 : _f.style) || {}), {
2704
+ width: `${cellWidth}px`,
2705
+ minWidth: `${cellWidth}px`,
2706
+ right: `${rightPosition}px`
2707
+ }),
2708
+ children: isLoading ? /* @__PURE__ */ jsxRuntime.jsx(CellSkeleton2, {}) : reactTable.flexRender(cell.column.columnDef.cell, cell.getContext())
2709
+ },
2710
+ cell.id
2711
+ );
2712
+ })
2713
+ ]
2714
+ }
2715
+ );
2716
+ },
2717
+ (prevProps, nextProps) => {
2718
+ var _a, _b;
2719
+ if (prevProps.row.id !== nextProps.row.id)
2720
+ return false;
2721
+ if (prevProps.virtualRow.start !== nextProps.virtualRow.start)
2722
+ return false;
2723
+ if (prevProps.virtualRow.index !== nextProps.virtualRow.index)
2724
+ return false;
2725
+ if (prevProps.isLoading !== nextProps.isLoading)
2726
+ return false;
2727
+ if (prevProps.isRowSelected !== nextProps.isRowSelected)
2728
+ return false;
2729
+ const prevHeaderItems = prevProps.headerVirtualItems;
2730
+ const nextHeaderItems = nextProps.headerVirtualItems;
2731
+ if ((prevHeaderItems == null ? void 0 : prevHeaderItems.length) !== (nextHeaderItems == null ? void 0 : nextHeaderItems.length))
2732
+ return false;
2733
+ if (prevHeaderItems && nextHeaderItems && ((_a = prevHeaderItems[0]) == null ? void 0 : _a.index) !== ((_b = nextHeaderItems[0]) == null ? void 0 : _b.index))
2734
+ return false;
2735
+ if (prevProps.totalUnpinnedWidth !== nextProps.totalUnpinnedWidth)
2736
+ return false;
2737
+ if (prevProps.totalTableWidth !== nextProps.totalTableWidth)
2738
+ return false;
2739
+ return true;
2740
+ }
2741
+ );
2742
+ if (typeof TableBodyRow === "object" && TableBodyRow !== null) {
2743
+ TableBodyRow.displayName = "TableBodyRow";
2744
+ }
2745
+ var VirtualTableBody = React3__default.default.memo(
2746
+ ({
2747
+ table,
2748
+ tableContainerRef,
2749
+ getFixedCellStyle,
2750
+ headerRef,
2751
+ headerVirtualItems,
2752
+ bodyRef,
2753
+ scrollViewportRef,
2754
+ onBodyScroll,
2755
+ viewportWidth,
2756
+ bodyRowStyle
2757
+ }) => {
2758
+ var _a, _b;
2759
+ const { rows } = table.getRowModel();
2760
+ const { isLoading } = useTable();
2761
+ const currentHeaderGroups = table.getHeaderGroups();
2762
+ const leafHeaderGroup = currentHeaderGroups[currentHeaderGroups.length - 1];
2763
+ const allHeaders = React3.useMemo(() => {
2764
+ const headers = (leafHeaderGroup == null ? void 0 : leafHeaderGroup.headers) || [];
2765
+ const filtered = headers.filter((h) => {
2766
+ const columns = h.column.columnDef.columns;
2767
+ return !columns || columns.length === 0;
2768
+ });
2769
+ return filtered;
2770
+ }, [leafHeaderGroup]);
2771
+ const unpinnedColumns = React3.useMemo(() => allHeaders.filter((h) => !h.column.getIsPinned()), [allHeaders]);
2772
+ const leftPinnedColumns = React3.useMemo(() => allHeaders.filter((h) => h.column.getIsPinned() === "left"), [allHeaders]);
2773
+ const rightPinnedColumns = React3.useMemo(
2774
+ () => allHeaders.filter((h) => h.column.getIsPinned() === "right"),
2775
+ [allHeaders]
2776
+ );
2777
+ const { getUnpinnedColumnWidth, totalUnpinnedWidth, totalTableWidth } = useResponsiveColumnLayout({
2778
+ unpinnedColumns,
2779
+ leftPinnedColumns,
2780
+ rightPinnedColumns,
2781
+ viewportWidth
2782
+ });
2783
+ const [headerHeight, setHeaderHeight] = React3__default.default.useState(48);
2784
+ React3__default.default.useEffect(() => {
2785
+ if (headerRef.current) {
2786
+ const updateHeaderHeight = () => {
2787
+ if (headerRef.current) {
2788
+ const firstRow = headerRef.current.querySelector("div > div");
2789
+ if (firstRow) {
2790
+ const height = firstRow.getBoundingClientRect().height;
2791
+ if (height > 0) {
2792
+ setHeaderHeight(height);
2793
+ }
2794
+ } else {
2795
+ const height = headerRef.current.getBoundingClientRect().height;
2796
+ if (height > 0) {
2797
+ setHeaderHeight(height);
2798
+ }
2799
+ }
2800
+ }
2801
+ };
2802
+ const timeoutId = setTimeout(updateHeaderHeight, 0);
2803
+ const resizeObserver = new ResizeObserver(() => {
2804
+ updateHeaderHeight();
2805
+ });
2806
+ resizeObserver.observe(headerRef.current);
2807
+ return () => {
2808
+ clearTimeout(timeoutId);
2809
+ resizeObserver.disconnect();
2810
+ };
2811
+ }
2812
+ }, [headerRef]);
2813
+ const estimateSize = React3.useCallback((index) => getUnpinnedColumnWidth(index), [getUnpinnedColumnWidth]);
2814
+ const columnVirtualizer = reactVirtual.useVirtualizer({
2815
+ // 헤더와 동일: flushSync 경고 방지
2816
+ // useFlushSync: false,
2817
+ count: unpinnedColumns.length,
2818
+ getScrollElement: () => headerRef.current || bodyRef.current,
2819
+ estimateSize,
2820
+ horizontal: true,
2821
+ overscan: 5
2822
+ });
2823
+ const getItemKey = React3.useCallback(
2824
+ (index) => {
2825
+ const row = rows[index];
2826
+ return (row == null ? void 0 : row.id) || `row-${index}`;
2827
+ },
2828
+ [rows]
2829
+ );
2830
+ const rowVirtualizer = reactVirtual.useVirtualizer({
2831
+ // useFlushSync: false,
2832
+ count: rows.length,
2833
+ getScrollElement: () => (scrollViewportRef == null ? void 0 : scrollViewportRef.current) || tableContainerRef.current,
2834
+ estimateSize: (index) => {
2835
+ var _a2;
2836
+ return resolveBodyRowStyle(bodyRowStyle, index, (_a2 = rows[index]) == null ? void 0 : _a2.original).heightPx;
2837
+ },
2838
+ overscan: 10,
2839
+ // row의 안정적인 key를 제공하여 sync 상태 변경 시에도 row 추적 안정화
2840
+ getItemKey
2841
+ // 실제 row 높이를 측정하여 깜빡임 방지 (DOM layout 측정 비활성화)
2842
+ // measureElement,
2843
+ });
2844
+ const virtualRows = rowVirtualizer.getVirtualItems();
2845
+ React3__default.default.useEffect(() => {
2846
+ const scrollElement = (scrollViewportRef == null ? void 0 : scrollViewportRef.current) || tableContainerRef.current;
2847
+ if (scrollElement) {
2848
+ const timeoutId = setTimeout(() => {
2849
+ rowVirtualizer.measure();
2850
+ columnVirtualizer.measure();
2851
+ }, 0);
2852
+ return () => clearTimeout(timeoutId);
2853
+ }
2854
+ }, [rowVirtualizer, columnVirtualizer, scrollViewportRef, tableContainerRef]);
2855
+ const handleBodyScroll = React3.useCallback(() => {
2856
+ if (!onBodyScroll)
2857
+ return;
2858
+ onBodyScroll();
2859
+ }, [onBodyScroll]);
2860
+ const bodyGridHeightPx = rowVirtualizer.getTotalSize();
2861
+ return /* @__PURE__ */ jsxRuntime.jsx(VirtualTableBodyGrid, { ref: bodyRef, $totalHeightPx: bodyGridHeightPx, onScroll: handleBodyScroll, children: /* @__PURE__ */ jsxRuntime.jsx(VirtualTableVerticalVirtualTrack, { $translateY: (_b = (_a = virtualRows[0]) == null ? void 0 : _a.start) != null ? _b : 0, children: virtualRows.map((virtualRow) => {
2862
+ const row = rows[virtualRow.index];
2863
+ const rowKey = row.id || `row-${virtualRow.index}`;
2864
+ return /* @__PURE__ */ jsxRuntime.jsx(
2865
+ TableBodyRow,
2866
+ {
2867
+ row,
2868
+ isRowSelected: row.getIsSelected(),
2869
+ virtualRow,
2870
+ rowVirtualizer,
2871
+ getFixedCellStyle,
2872
+ tableContainerRef,
2873
+ columnVirtualizer,
2874
+ bodyRowStyle,
2875
+ unpinnedColumns,
2876
+ scrollMargin: headerHeight,
2877
+ totalUnpinnedWidth,
2878
+ totalTableWidth,
2879
+ getUnpinnedColumnWidth,
2880
+ headerVirtualItems,
2881
+ isLoading
2882
+ },
2883
+ rowKey
2884
+ );
2885
+ }) }) });
2886
+ }
2887
+ );
2888
+ if (typeof VirtualTableBody === "object" && VirtualTableBody !== null) {
2889
+ VirtualTableBody.displayName = "VirtualTableBody";
2890
+ }
2891
+ function VirtualTable({
2892
+ maxHeight = "800px",
2893
+ bodyRowStyle
2894
+ }) {
2895
+ const tableContainerRef = React3.useRef(null);
2896
+ const scrollAreaRef = React3.useRef(null);
2897
+ const scrollViewportRef = React3.useRef(null);
2898
+ const { table, tableScrollRef, bodyRef, headerRef } = useTable();
2899
+ const [headerVirtualItems, setHeaderVirtualItems] = React3__default.default.useState([]);
2900
+ const viewportWidth = useResponsiveViewportWidth(tableContainerRef, headerRef);
2901
+ React3__default.default.useEffect(() => {
2902
+ var _a;
2903
+ if ((_a = scrollAreaRef.current) == null ? void 0 : _a.view) {
2904
+ scrollViewportRef.current = scrollAreaRef.current.view;
2905
+ scrollViewportRef.current.dispatchEvent(new Event("scroll", { bubbles: true }));
2906
+ }
2907
+ }, []);
2908
+ const handleBodyScroll = React3.useCallback(() => {
2909
+ if (!bodyRef.current)
2910
+ return;
2911
+ const bodyScrollLeft = bodyRef.current.scrollLeft;
2912
+ if (headerRef.current) {
2913
+ headerRef.current.scrollLeft = bodyScrollLeft;
2914
+ }
2915
+ if (tableScrollRef == null ? void 0 : tableScrollRef.current) {
2916
+ tableScrollRef.current.scrollLeft = bodyScrollLeft;
2917
+ }
2918
+ }, [tableScrollRef]);
2919
+ const handleHeaderScroll = React3.useCallback(() => {
2920
+ if (!headerRef.current)
2921
+ return;
2922
+ const headerScrollLeft = headerRef.current.scrollLeft;
2923
+ if (bodyRef.current) {
2924
+ bodyRef.current.scrollLeft = headerScrollLeft;
2925
+ }
2926
+ if (tableScrollRef == null ? void 0 : tableScrollRef.current) {
2927
+ tableScrollRef.current.scrollLeft = headerScrollLeft;
2928
+ }
2929
+ }, [tableScrollRef]);
2930
+ const columnStyleCacheRef = React3.useRef(/* @__PURE__ */ new WeakMap());
2931
+ const getColumnStyle = React3.useCallback(
2932
+ (column, isHeader) => {
2933
+ var _a, _b, _c, _d;
2934
+ const cached = columnStyleCacheRef.current.get(column);
2935
+ if (cached) {
2936
+ return isHeader ? cached.header : cached.cell;
2937
+ }
2938
+ const pinningStyles = getCommonPinningStyles(column);
2939
+ const size = column.columnDef.size;
2940
+ const minSize = column.columnDef.minSize;
2941
+ const maxSize = column.columnDef.maxSize;
2942
+ const widthStyle = size === 0 ? { width: "100%" } : {
2943
+ width: pinningStyles.width || `${size}px`,
2944
+ minWidth: `${minSize}px`,
2945
+ maxWidth: `${maxSize}px`
2946
+ };
2947
+ const headerStyle = __spreadValues(__spreadValues(__spreadValues({}, pinningStyles), ((_b = (_a = column.columnDef.meta) == null ? void 0 : _a.headerProps) == null ? void 0 : _b.style) || {}), widthStyle);
2948
+ const cellStyle = __spreadValues(__spreadValues(__spreadValues({}, pinningStyles), ((_d = (_c = column.columnDef.meta) == null ? void 0 : _c.cellProps) == null ? void 0 : _d.style) || {}), widthStyle);
2949
+ columnStyleCacheRef.current.set(column, {
2950
+ header: headerStyle,
2951
+ cell: cellStyle
2952
+ });
2953
+ return isHeader ? headerStyle : cellStyle;
2954
+ },
2955
+ []
2956
+ // 의존성 없음 - 컬럼 객체 자체가 변경되면 WeakMap에서 자동으로 가비지 컬렉션됨
2957
+ );
2958
+ const getFixedCellStyle = React3.useCallback(
2959
+ (column, isHeader = false) => {
2960
+ return getColumnStyle(column, isHeader);
2961
+ },
2962
+ [getColumnStyle]
2963
+ );
2964
+ return /* @__PURE__ */ jsxRuntime.jsxs(VirtualTableRoot, { children: [
2965
+ /* @__PURE__ */ jsxRuntime.jsx(
2966
+ VirtualTableHeader,
2967
+ {
2968
+ table,
2969
+ headerRef,
2970
+ getFixedCellStyle,
2971
+ tableContainerRef,
2972
+ scrollViewportRef,
2973
+ onVirtualItemsChange: setHeaderVirtualItems,
2974
+ onHeaderScroll: handleHeaderScroll,
2975
+ viewportWidth
2976
+ }
2977
+ ),
2978
+ /* @__PURE__ */ jsxRuntime.jsx("div", { ref: scrollViewportRef, style: { maxHeight, overflowY: "auto", overflowX: "hidden" }, children: /* @__PURE__ */ jsxRuntime.jsx(VirtualTableScrollAreaInner, { ref: tableContainerRef, children: /* @__PURE__ */ jsxRuntime.jsx(
2979
+ VirtualTableBody,
2980
+ {
2981
+ table,
2982
+ tableContainerRef,
2983
+ getFixedCellStyle,
2984
+ headerRef,
2985
+ headerVirtualItems,
2986
+ bodyRef,
2987
+ scrollViewportRef,
2988
+ onBodyScroll: handleBodyScroll,
2989
+ viewportWidth,
2990
+ bodyRowStyle
2991
+ }
2992
+ ) }) })
2993
+ ] });
2994
+ }
2995
+ var TableMain = (props) => {
2996
+ const {
2997
+ fixedColumns = [],
2998
+ useVirtualization = false,
2999
+ isSticky = true,
3000
+ stickyHeaderTopPosition = 120,
3001
+ children,
3002
+ maxHeight,
3003
+ emptyRowCount = 8,
3004
+ enableDragDrop = false,
3005
+ dragColWidth = 40,
3006
+ onRowReorder,
3007
+ footerRowProps,
3008
+ headerRowStyle,
3009
+ bodyRowStyle,
3010
+ containerStyle
3011
+ } = props;
3012
+ const { table, hasToolbar, hasFilterBar, columnResizing } = useTable();
3013
+ const { rows } = table.getRowModel();
3014
+ const shouldFixDragHandle = enableDragDrop && fixedColumns.some((fc) => fc.index === 0 && fc.position === "left");
3015
+ React3.useEffect(() => {
3016
+ const pinningState = {
3017
+ left: [],
3018
+ right: []
3019
+ };
3020
+ fixedColumns.forEach(({ index, position }) => {
3021
+ if (enableDragDrop && index === 0) {
3022
+ return;
3023
+ }
3024
+ const actualIndex = enableDragDrop ? index - 1 : index;
3025
+ const column = table.getAllLeafColumns()[actualIndex];
3026
+ if (column == null ? void 0 : column.id) {
3027
+ pinningState[position].push(column.id);
3028
+ }
3029
+ });
3030
+ table.setColumnPinning(pinningState);
3031
+ }, []);
3032
+ const isEmpty = rows.length === 0;
3033
+ let emptyElement;
3034
+ React3__default.default.Children.forEach(children, (child) => {
3035
+ if (React3__default.default.isValidElement(child) && child.type === TableEmpty) {
3036
+ emptyElement = child;
3037
+ }
3038
+ });
3039
+ const nonVirtualizedRows = rows.map((row) => __spreadValues({ row }, row));
3040
+ const tableState = {
3041
+ displayedRows: nonVirtualizedRows,
3042
+ paddingTop: 0,
3043
+ paddingBottom: 0,
3044
+ isEmpty,
3045
+ emptyElement,
3046
+ children,
3047
+ maxHeight,
3048
+ hasToolbar,
3049
+ isSticky,
3050
+ stickyHeaderTopPosition,
3051
+ emptyRowCount,
3052
+ enableDragDrop,
3053
+ dragColWidth,
3054
+ shouldFixDragHandle,
3055
+ onRowReorder,
3056
+ footerRowProps,
3057
+ headerRowStyle,
3058
+ bodyRowStyle
3059
+ };
3060
+ return /* @__PURE__ */ jsxRuntime.jsx(TableRootContainer, { hasFilterBar, hasToolbar, style: containerStyle, children: useVirtualization ? /* @__PURE__ */ jsxRuntime.jsx(VirtualTable, { maxHeight, bodyRowStyle }) : (
3061
+ // <VirtualizedContent
3062
+ // {...props}
3063
+ // rows={rows}
3064
+ // emptyElement={emptyElement}
3065
+ // isEmpty={isEmpty}
3066
+ // enableDragDrop={enableDragDrop}
3067
+ // />
3068
+ columnResizing ? /* @__PURE__ */ jsxRuntime.jsx(ResizableTable, { tableState }) : /* @__PURE__ */ jsxRuntime.jsx(FixedTable, { tableState })
3069
+ ) });
3070
+ };
3071
+ var useIntersectionObserver = (target, callback, options) => {
3072
+ React3.useEffect(() => {
3073
+ if (!target.current) {
3074
+ return;
3075
+ }
3076
+ const observer = new IntersectionObserver(callback, options);
3077
+ observer.observe(target.current);
3078
+ return () => observer.disconnect();
3079
+ }, [callback]);
3080
+ };
3081
+ var TablePagination = ({
3082
+ total,
3083
+ defaultPageSize,
3084
+ leftSource,
3085
+ children,
3086
+ pageSizeList = PAGE_SIZE,
3087
+ setCurrentPage,
3088
+ notSizeOption = false,
3089
+ currentPage,
3090
+ showPagination = true,
3091
+ sizeVar = "S",
3092
+ hasPaddingInline = true
3093
+ }) => {
3094
+ const { table, headerRef, bodyRef, tableScrollRef, footerRef, hasFilterBar, hasToolbar, isVirtualTableLayout } = useTable();
3095
+ const { pageSize, pageIndex } = table.getState().pagination;
3096
+ const [isEndOfPage, setIsEndOfPage] = React3.useState(false);
3097
+ const handleScroll = React3.useCallback(() => {
3098
+ if (!headerRef.current || !bodyRef.current || !tableScrollRef.current) {
3099
+ return;
3100
+ }
3101
+ const scrollLeft = tableScrollRef.current.scrollLeft;
3102
+ headerRef.current.scrollLeft = scrollLeft;
3103
+ bodyRef.current.scrollLeft = scrollLeft;
3104
+ }, []);
3105
+ const onIntersect = React3.useCallback(
3106
+ (entries) => __async(void 0, null, function* () {
3107
+ const entry = entries[0];
3108
+ entry.isIntersecting ? setIsEndOfPage(true) : setIsEndOfPage(false);
3109
+ }),
3110
+ [isEndOfPage]
3111
+ );
3112
+ useIntersectionObserver(footerRef, onIntersect, {
3113
+ threshold: 1,
3114
+ rootMargin: "0px 0px -1px"
3115
+ });
3116
+ const handlePageChange = React3.useCallback(
3117
+ (updater) => {
3118
+ const newPage = typeof updater === "function" ? updater(pageIndex) : updater;
3119
+ table.setPageIndex(newPage);
3120
+ setCurrentPage == null ? void 0 : setCurrentPage({ pageIndex: newPage, pageSize });
3121
+ },
3122
+ [pageIndex, pageSize, table, setCurrentPage]
3123
+ );
3124
+ const handlePageSizeChange = React3.useCallback(
3125
+ (value) => {
3126
+ const newSize = Number(value);
3127
+ table.setPageSize(newSize);
3128
+ table.setPageIndex(0);
3129
+ setCurrentPage == null ? void 0 : setCurrentPage({ pageIndex: 0, pageSize: newSize });
3130
+ },
3131
+ [table, setCurrentPage]
3132
+ );
3133
+ const TableColumns = () => {
3134
+ const leafColumns = table.getVisibleLeafColumns();
3135
+ return /* @__PURE__ */ jsxRuntime.jsx("colgroup", { children: leafColumns.map((column) => {
3136
+ const size = column.columnDef.size;
3137
+ const minSize = column.columnDef.minSize;
3138
+ const maxSize = column.columnDef.maxSize;
3139
+ const style = size === 0 ? { width: "100%" } : {
3140
+ width: `${size}px`,
3141
+ minWidth: `${minSize}px`,
3142
+ maxWidth: `${maxSize}px`
3143
+ };
3144
+ return /* @__PURE__ */ jsxRuntime.jsx("col", { style }, column.id);
3145
+ }) });
3146
+ };
3147
+ const renderRightSource = () => {
3148
+ if (sizeVar === "XS") {
3149
+ return null;
3150
+ }
3151
+ if (notSizeOption) {
3152
+ return;
3153
+ }
3154
+ return /* @__PURE__ */ jsxRuntime.jsx(PaginationSizeSelectorSlot, { children: /* @__PURE__ */ jsxRuntime.jsx(
3155
+ base.Pagination.SizeSelector,
3156
+ {
3157
+ data: pageSizeList.map((item) => ({ label: item.label, value: item.key })),
3158
+ pageSize: `${pageSize}`,
3159
+ setPageSize: handlePageSizeChange,
3160
+ middlewares: [
3161
+ base.flip({ padding: 8, rootBoundary: "viewport" }),
3162
+ base.shift({ padding: 8, rootBoundary: "viewport" })
3163
+ ]
3164
+ }
3165
+ ) });
3166
+ };
3167
+ React3.useEffect(() => {
3168
+ table.setPageSize(defaultPageSize);
3169
+ }, [defaultPageSize, table]);
3170
+ React3.useEffect(() => {
3171
+ table.setPageIndex(currentPage != null ? currentPage : 0);
3172
+ }, [table, currentPage]);
3173
+ React3.useEffect(() => {
3174
+ if (table.options.manualPagination) {
3175
+ return;
3176
+ }
3177
+ const pageCount = Math.max(1, Math.ceil(total / Number(pageSize)));
3178
+ if (pageIndex > pageCount - 1) {
3179
+ table.setPageIndex(pageCount - 1);
3180
+ }
3181
+ }, [total, pageSize, pageIndex, table]);
3182
+ const scrollbarTableWidth = table.getTotalSize() || "100%";
3183
+ const leftSlotContent = leftSource != null ? leftSource : children;
3184
+ return /* @__PURE__ */ jsxRuntime.jsxs(
3185
+ BottomContainer,
3186
+ {
3187
+ ref: footerRef,
3188
+ isEndOfPage,
3189
+ hasFilterBar,
3190
+ hasToolbar,
3191
+ disableStickyFooter: Boolean(isVirtualTableLayout),
3192
+ children: [
3193
+ /* @__PURE__ */ jsxRuntime.jsx(ScrollContainer, { ref: tableScrollRef, onScroll: handleScroll, isPagination: showPagination, children: /* @__PURE__ */ jsxRuntime.jsx(
3194
+ "table",
3195
+ {
1412
3196
  style: {
1413
- height: "200px",
1414
- textAlign: "center",
1415
- verticalAlign: "middle"
3197
+ width: scrollbarTableWidth,
3198
+ height: "6px",
3199
+ tableLayout: "fixed"
1416
3200
  },
1417
- children: children || emptyElement
3201
+ children: /* @__PURE__ */ jsxRuntime.jsx(TableColumns, {})
1418
3202
  }
1419
- ) }) : /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
1420
- paddingTop > 0 && /* @__PURE__ */ jsxRuntime.jsx(TableRow, { children: /* @__PURE__ */ jsxRuntime.jsx("td", { style: { height: `${paddingTop}px` } }) }),
1421
- displayedRows.map((rowObj, i) => {
1422
- const isVirtual = "virtualRow" in rowObj && rowObj.virtualRow;
1423
- const row = rowObj.row;
1424
- const cells = typeof row.getVisibleCells === "function" ? row.getVisibleCells() : row;
1425
- return /* @__PURE__ */ jsxRuntime.jsx(
1426
- TableRow,
1427
- {
1428
- "data-index": isVirtual ? rowObj.virtualRow.index : i,
1429
- onClick: () => {
1430
- var _a;
1431
- if (typeof row.getVisibleCells === "function") {
1432
- onClickRow == null ? void 0 : onClickRow(row.original);
1433
- } else if (Array.isArray(row) && row.length > 0 && ((_a = row[0].row) == null ? void 0 : _a.original)) {
1434
- onClickRow == null ? void 0 : onClickRow(row[0].row.original);
1435
- }
1436
- },
1437
- className: onClickRow !== void 0 ? "clickable" : "",
1438
- children: cells.map((cell) => {
1439
- var _a;
1440
- const isPinned = cell.column.getIsPinned();
1441
- const isLastLeftPinned = isPinned === "left" && cell.column.getIsLastColumn("left");
1442
- const isFirstRightPinned = isPinned === "right" && cell.column.getIsFirstColumn("right");
1443
- return /* @__PURE__ */ jsxRuntime.jsx(
1444
- TableCell,
1445
- {
1446
- "data-last-left-pinned": isLastLeftPinned,
1447
- "data-first-right-pinned": isFirstRightPinned,
1448
- "data-no-hover": ((_a = cell.column.columnDef.meta) == null ? void 0 : _a.activeHover) ? "true" : void 0,
1449
- style: getResizableCellStyle(cell.column),
1450
- children: reactTable.flexRender(cell.column.columnDef.cell, cell.getContext())
1451
- },
1452
- cell.id
1453
- );
1454
- })
1455
- },
1456
- typeof row.id !== "undefined" ? row.id : i
1457
- );
1458
- }),
1459
- paddingBottom > 0 && /* @__PURE__ */ jsxRuntime.jsx(TableRow, { children: /* @__PURE__ */ jsxRuntime.jsx("td", { style: { height: `${paddingBottom}px` } }) }),
1460
- emptyRowCount !== 0 && displayedRows.length < emptyRowCount && Array.from({ length: emptyRowCount - displayedRows.length }).map((_, index) => /* @__PURE__ */ jsxRuntime.jsx(TableRow, { "data-empty": true, children: /* @__PURE__ */ jsxRuntime.jsx(
1461
- TableCell,
3203
+ ) }),
3204
+ /* @__PURE__ */ jsxRuntime.jsxs(PaginationWrapper, { sizeVar, isEndOfPage, children: [
3205
+ !showPagination && /* @__PURE__ */ jsxRuntime.jsx(PaginationLeftSlot, { children: leftSlotContent }),
3206
+ showPagination && /* @__PURE__ */ jsxRuntime.jsx(
3207
+ base.Pagination,
1462
3208
  {
1463
- colSpan: table.getAllColumns().length,
1464
- style: {
1465
- height: `${60}px`
1466
- }
1467
- }
1468
- ) }, `empty-row-${index}`))
1469
- ] }) })
1470
- }
1471
- ) }) })
1472
- ] });
3209
+ sizeVar,
3210
+ pageSize: `${pageSize}`,
3211
+ currentPage: pageIndex,
3212
+ itemsTotalCount: total,
3213
+ totalCount: Math.ceil(total / Number(pageSize)),
3214
+ previousPage: () => handlePageChange(pageIndex - 1),
3215
+ nextPage: () => handlePageChange(pageIndex + 1),
3216
+ style: { paddingInline: hasPaddingInline ? "16px" : "0px" },
3217
+ gotoPage: handlePageChange,
3218
+ rightSource: renderRightSource(),
3219
+ leftSource: leftSlotContent
3220
+ },
3221
+ Math.ceil(total / Number(pageSize))
3222
+ )
3223
+ ] })
3224
+ ]
3225
+ }
3226
+ );
3227
+ };
3228
+ var TableToolbar = ({
3229
+ children,
3230
+ filterAccessor,
3231
+ height = "56px",
3232
+ padding = "12px 20px",
3233
+ totalCount
3234
+ }) => {
3235
+ const { table, filterValue, setFilterValue } = useTable();
3236
+ const _totalCount = totalCount || table.getPrePaginationRowModel().rows.length;
3237
+ const onSearch = (value) => {
3238
+ var _a;
3239
+ if (!filterAccessor)
3240
+ return null;
3241
+ setFilterValue(value);
3242
+ (_a = table.getColumn(filterAccessor)) == null ? void 0 : _a.setFilterValue(value);
3243
+ };
3244
+ return /* @__PURE__ */ jsxRuntime.jsx(base.StackContainer.Horizontal, { width: "100%", height, align: "center", padding, justify: "space-between", children: children({
3245
+ totalCount: _totalCount,
3246
+ filterAccessor: filterAccessor != null ? filterAccessor : "",
3247
+ onSearch,
3248
+ filterValue
3249
+ }) });
1473
3250
  };
1474
- var TableMain = ({
1475
- fixedColumns = [],
1476
- useVirtualization = false,
1477
- isSticky = true,
1478
- stickyHeaderTopPosition = 120,
3251
+ var Table = ({
3252
+ data,
3253
+ columns,
3254
+ columnResizing = false,
1479
3255
  children,
1480
- maxHeight,
1481
- emptyRowCount = 8
3256
+ manualPagination = false,
3257
+ manualFiltering = false,
3258
+ manualSorting = true,
3259
+ selectedRows = [],
3260
+ onSelectedRowsChange,
3261
+ onClickRow,
3262
+ initPageSize = 100,
3263
+ noBorder = false,
3264
+ isLoading = false,
3265
+ getRowId,
3266
+ globalSorting,
3267
+ outsideFilters,
3268
+ autoResetPageIndex = false
1482
3269
  }) => {
1483
- const { table, hasToolbar, hasFilterBar, columnResizing } = useTable();
1484
- const { rows } = table.getRowModel();
1485
- const scrollToFn = React2.useCallback((offset) => {
1486
- window.scrollTo({
1487
- top: offset - 120,
1488
- behavior: "smooth"
3270
+ const [sorting, setSorting] = React3.useState([]);
3271
+ const [columnFilters, setColumnFilters] = React3.useState([]);
3272
+ const [globalFilter, setGlobalFilter] = React3.useState([]);
3273
+ const [columnVisibility, setColumnVisibility] = React3.useState({});
3274
+ const [columnPinning, setColumnPinning] = React3.useState({});
3275
+ const [rowSelection, setRowSelection] = React3.useState({});
3276
+ const [filterValue, setFilterValue] = React3.useState("");
3277
+ const currentSorting = globalSorting != null ? globalSorting : sorting;
3278
+ const rowIdMapRef = React3.useRef(/* @__PURE__ */ new WeakMap());
3279
+ const rowIdCounterRef = React3.useRef(0);
3280
+ const filterHiddenColumns = (cols) => {
3281
+ return cols.filter((column) => {
3282
+ var _a;
3283
+ return column && !((_a = column.meta) == null ? void 0 : _a.hiddenColumn);
3284
+ }).map((column) => {
3285
+ if ("columns" in column && Array.isArray(column.columns)) {
3286
+ return __spreadProps(__spreadValues({}, column), {
3287
+ columns: filterHiddenColumns(column.columns)
3288
+ });
3289
+ }
3290
+ return column;
3291
+ }).filter((column) => {
3292
+ if ("columns" in column && Array.isArray(column.columns)) {
3293
+ return column.columns.length > 0;
3294
+ }
3295
+ return true;
1489
3296
  });
1490
- }, []);
1491
- const rowVirtualizer = reactVirtual.useWindowVirtualizer({
1492
- estimateSize: () => 60,
1493
- // 각 행의 높이를 60px로 예측
1494
- count: rows.length,
1495
- overscan: 10,
1496
- // 실제 보이는 영역 외에 추가로 렌더링할 아이템 수
1497
- isScrollingResetDelay: 100,
1498
- // 스크롤이 멈추고 100ms 후에 스크롤 상태 초기화
1499
- observeElementOffset: (instance, cb) => reactVirtual.observeWindowOffset(instance, (offset, isScrolling) => cb(offset - 120, isScrolling)),
1500
- scrollToFn
1501
- });
1502
- const { getVirtualItems: virtualRows } = rowVirtualizer;
1503
- const displayedRows = useVirtualization ? virtualRows().map((virtualRow) => ({ row: rows[virtualRow.index], virtualRow })) : rows.map((row) => ({ row }));
1504
- const hasVirtualRow = (item) => {
1505
- return "virtualRow" in item;
1506
3297
  };
1507
- const paddingTop = displayedRows.length > 0 && hasVirtualRow(displayedRows[0]) ? displayedRows[0].virtualRow.start : 0;
1508
- const lastRow = displayedRows[displayedRows.length - 1];
1509
- const paddingBottom = displayedRows.length > 0 && lastRow && hasVirtualRow(lastRow) ? rowVirtualizer.getTotalSize() - lastRow.virtualRow.end : 0;
1510
- React2.useEffect(() => {
1511
- const pinningState = {
1512
- left: [],
1513
- right: []
3298
+ const visibleColumns = React3.useMemo(() => filterHiddenColumns(columns), [columns]);
3299
+ const safeGetRowId = React3.useMemo(() => {
3300
+ if (getRowId) {
3301
+ return (row) => {
3302
+ const id = getRowId(row);
3303
+ if (id === void 0 || id === null || id === "") {
3304
+ if (rowIdMapRef.current.has(row)) {
3305
+ return rowIdMapRef.current.get(row);
3306
+ }
3307
+ const newId = `row-${rowIdCounterRef.current++}`;
3308
+ rowIdMapRef.current.set(row, newId);
3309
+ return newId;
3310
+ }
3311
+ return String(id);
3312
+ };
3313
+ }
3314
+ return (row) => {
3315
+ if (typeof row === "object" && row !== null && "id" in row) {
3316
+ const id = row.id;
3317
+ if (id !== void 0 && id !== null && id !== "") {
3318
+ return String(id);
3319
+ }
3320
+ }
3321
+ if (rowIdMapRef.current.has(row)) {
3322
+ return rowIdMapRef.current.get(row);
3323
+ }
3324
+ const newId = `row-${rowIdCounterRef.current++}`;
3325
+ rowIdMapRef.current.set(row, newId);
3326
+ return newId;
1514
3327
  };
1515
- fixedColumns.forEach(({ index, position }) => {
1516
- const column = table.getAllColumns()[index];
1517
- if (column == null ? void 0 : column.id) {
1518
- pinningState[position].push(column.id);
3328
+ }, [getRowId]);
3329
+ const table = reactTable.useReactTable({
3330
+ data,
3331
+ columns: visibleColumns,
3332
+ columnResizeMode: "onChange",
3333
+ getRowId: safeGetRowId,
3334
+ initialState: {
3335
+ pagination: {
3336
+ pageSize: initPageSize
1519
3337
  }
1520
- });
1521
- table.setColumnPinning(pinningState);
1522
- }, []);
1523
- const isEmpty = rows.length === 0;
1524
- let emptyElement;
1525
- React2__default.default.Children.forEach(children, (child) => {
1526
- if (React2__default.default.isValidElement(child) && child.type === TableEmpty) {
1527
- emptyElement = child;
1528
- }
3338
+ },
3339
+ state: {
3340
+ sorting: currentSorting,
3341
+ columnFilters,
3342
+ globalFilter,
3343
+ columnVisibility,
3344
+ columnPinning,
3345
+ rowSelection
3346
+ },
3347
+ defaultColumn: {
3348
+ size: 0,
3349
+ // TODO: 필터링 기능 추가 시 props로 옵션 처리
3350
+ enableColumnFilter: false,
3351
+ enableSorting: false,
3352
+ enableResizing: true
3353
+ },
3354
+ onSortingChange: (updater) => {
3355
+ var _a, _b;
3356
+ const newSorting = typeof updater === "function" ? updater(table.getState().sorting) : updater;
3357
+ if (!globalSorting) {
3358
+ setSorting(newSorting);
3359
+ }
3360
+ if (newSorting.length > 0) {
3361
+ const { id, desc } = newSorting[0];
3362
+ const column = table.getAllLeafColumns().find((col) => col.id === id);
3363
+ (_b = (_a = column == null ? void 0 : column.columnDef.meta) == null ? void 0 : _a.onSortChange) == null ? void 0 : _b.call(_a, desc ? "desc" : "asc");
3364
+ } else {
3365
+ table.getAllLeafColumns().forEach((column) => {
3366
+ var _a2, _b2;
3367
+ (_b2 = (_a2 = column.columnDef.meta) == null ? void 0 : _a2.onSortChange) == null ? void 0 : _b2.call(_a2, void 0);
3368
+ });
3369
+ }
3370
+ },
3371
+ onColumnFiltersChange: (updater) => {
3372
+ const newFilters = typeof updater === "function" ? updater(table.getState().columnFilters) : updater;
3373
+ setColumnFilters(newFilters);
3374
+ newFilters.forEach((filter) => {
3375
+ var _a, _b;
3376
+ const column = table.getColumn(filter.id);
3377
+ if ((_b = (_a = column == null ? void 0 : column.columnDef) == null ? void 0 : _a.meta) == null ? void 0 : _b.onFilterChange) {
3378
+ column.columnDef.meta.onFilterChange(filter.value || "");
3379
+ }
3380
+ });
3381
+ },
3382
+ onGlobalFilterChange: (updater) => {
3383
+ var _a;
3384
+ const newGlobalFilter = typeof updater === "function" ? updater(globalFilter) : updater;
3385
+ setGlobalFilter(newGlobalFilter);
3386
+ if ((_a = table.options.meta) == null ? void 0 : _a.onGlobalFilterChange) {
3387
+ table.options.meta.onGlobalFilterChange(newGlobalFilter || "");
3388
+ }
3389
+ if (newGlobalFilter) {
3390
+ table.getAllLeafColumns().forEach((column) => {
3391
+ var _a2;
3392
+ if (column.getCanFilter() && ((_a2 = column.columnDef.meta) == null ? void 0 : _a2.onFilterChange)) {
3393
+ column.columnDef.meta.onFilterChange(newGlobalFilter);
3394
+ }
3395
+ });
3396
+ }
3397
+ },
3398
+ onColumnVisibilityChange: setColumnVisibility,
3399
+ onColumnPinningChange: setColumnPinning,
3400
+ onRowSelectionChange: (updater) => {
3401
+ const newSelection = typeof updater === "function" ? updater(rowSelection) : updater;
3402
+ setRowSelection(newSelection);
3403
+ const selectedRowIds = Object.keys(newSelection).filter((id) => newSelection[id]);
3404
+ const newSelectedRows = selectedRowIds.map((rowId) => {
3405
+ const found = data.find((row) => safeGetRowId(row) === rowId);
3406
+ if (found)
3407
+ return found;
3408
+ return selectedRows.find((row) => safeGetRowId(row) === rowId);
3409
+ }).filter(Boolean);
3410
+ onSelectedRowsChange == null ? void 0 : onSelectedRowsChange(newSelectedRows, newSelection);
3411
+ },
3412
+ getCoreRowModel: reactTable.getCoreRowModel(),
3413
+ getFilteredRowModel: reactTable.getFilteredRowModel(),
3414
+ getPaginationRowModel: reactTable.getPaginationRowModel(),
3415
+ getSortedRowModel: reactTable.getSortedRowModel(),
3416
+ enableColumnResizing: columnResizing,
3417
+ manualPagination,
3418
+ manualFiltering,
3419
+ manualSorting,
3420
+ autoResetPageIndex
1529
3421
  });
1530
- const tableState = {
1531
- displayedRows,
1532
- paddingTop,
1533
- paddingBottom,
1534
- isEmpty,
1535
- emptyElement,
1536
- children,
1537
- maxHeight,
3422
+ const headerRef = React3.useRef(null);
3423
+ const bodyRef = React3.useRef(null);
3424
+ const footerRef = React3.useRef(null);
3425
+ const tableScrollRef = React3.useRef(null);
3426
+ const hasToolbar = React3.Children.toArray(children).some((child) => React3.isValidElement(child) && child.type === TableToolbar) || noBorder;
3427
+ const hasPagination = React3.Children.toArray(children).some((child) => {
3428
+ if (!React3.isValidElement(child))
3429
+ return false;
3430
+ if (child.type === TablePagination)
3431
+ return true;
3432
+ if (typeof child.type !== "function")
3433
+ return false;
3434
+ const component = child.type;
3435
+ const componentName = component.displayName || component.name || "";
3436
+ return componentName.includes("Pagination");
3437
+ });
3438
+ const hasFilterBar = React3.Children.toArray(children).some(
3439
+ (child) => React3.isValidElement(child) && child.type === TableFilterBar
3440
+ );
3441
+ const hasFooter = table.getVisibleFlatColumns().some((column) => column.columnDef.footer !== void 0);
3442
+ const isVirtualTableLayout = React3.useMemo(() => {
3443
+ let virtual = false;
3444
+ React3.Children.forEach(children, (child) => {
3445
+ if (React3.isValidElement(child) && child.type === TableMain) {
3446
+ const p = child.props;
3447
+ virtual = Boolean(p.useVirtualization);
3448
+ }
3449
+ });
3450
+ return virtual;
3451
+ }, [children]);
3452
+ const contextValue = {
3453
+ table,
3454
+ headerRef,
3455
+ bodyRef,
3456
+ footerRef,
3457
+ tableScrollRef,
3458
+ selectedRows,
3459
+ onClickRow,
1538
3460
  hasToolbar,
1539
- isSticky,
1540
- stickyHeaderTopPosition,
1541
- emptyRowCount
3461
+ hasFilterBar,
3462
+ hasPagination,
3463
+ columnResizing,
3464
+ filterValue,
3465
+ setFilterValue,
3466
+ outsideFilters,
3467
+ hasFooter,
3468
+ isLoading,
3469
+ isVirtualTableLayout
1542
3470
  };
1543
- return /* @__PURE__ */ jsxRuntime.jsx(TableRootContainer, { hasFilterBar, hasToolbar, children: columnResizing ? /* @__PURE__ */ jsxRuntime.jsx(ResizableTable, { tableState }) : /* @__PURE__ */ jsxRuntime.jsx(FixedTable, { tableState }) });
3471
+ React3.useEffect(() => {
3472
+ if (selectedRows.length === 0) {
3473
+ table.resetRowSelection();
3474
+ }
3475
+ }, [onSelectedRowsChange, selectedRows.length, table]);
3476
+ return /* @__PURE__ */ jsxRuntime.jsx(TableContainer, { hasToolbar: hasToolbar || hasFilterBar, children: /* @__PURE__ */ jsxRuntime.jsx(TableProvider, { value: contextValue, children }) });
1544
3477
  };
1545
3478
  var TableColumnVisibility = () => {
1546
3479
  const { table } = useTable();
@@ -1548,7 +3481,7 @@ var TableColumnVisibility = () => {
1548
3481
  var _a;
1549
3482
  const header = column.columnDef.header;
1550
3483
  if (typeof header === "function") {
1551
- const headerContent = header();
3484
+ const headerContent = header({ table, column, header: column.columnDef.header });
1552
3485
  if (typeof headerContent === "string") {
1553
3486
  return headerContent;
1554
3487
  }
@@ -1569,37 +3502,6 @@ var TableColumnVisibility = () => {
1569
3502
  }) })
1570
3503
  ] });
1571
3504
  };
1572
- var TableBtn = styled2__default.default.button`
1573
- display: flex;
1574
- align-items: center;
1575
- gap: 2px;
1576
- border: 1px solid ${base.colorTokens.neutral200};
1577
- border-radius: 4px;
1578
- padding: 4px;
1579
- background: ${base.colorTokens.neutral150};
1580
- color: ${base.colorTokens.neutral700};
1581
- cursor: ${({ onClick }) => onClick ? "pointer" : "default"};
1582
-
1583
- &:hover {
1584
- background: ${({ disabled }) => disabled ? base.colorTokens.neutral150 : base.colorTokens.neutral200};
1585
- }
1586
-
1587
- &:disabled {
1588
- cursor: not-allowed;
1589
- opacity: 0.5;
1590
- }
1591
- `;
1592
- exports.TableButton = (_a) => {
1593
- var _b = _a, { children, leftSource, rightSource } = _b, buttonProps = __objRest(_b, ["children", "leftSource", "rightSource"]);
1594
- return /* @__PURE__ */ jsxRuntime.jsxs(TableBtn, __spreadProps(__spreadValues({}, buttonProps), { children: [
1595
- leftSource && leftSource,
1596
- /* @__PURE__ */ jsxRuntime.jsx(base.Text, { typography: "body2_500", lineClamp: 2, children }),
1597
- rightSource && rightSource
1598
- ] }));
1599
- };
1600
- exports.TableBadge = ({ children }) => {
1601
- return /* @__PURE__ */ jsxRuntime.jsx(base.StackContainer, { radius: "borderRadius04", background: "neutral150", padding: "2px 4px", children: /* @__PURE__ */ jsxRuntime.jsx(base.Text, { typography: "body2_400", children }) });
1602
- };
1603
3505
 
1604
3506
  // src/components/Table/components/Table/index.ts
1605
3507
  exports.Table = Object.assign(Table, {
@@ -1612,7 +3514,7 @@ exports.Table = Object.assign(Table, {
1612
3514
  Button: exports.TableButton,
1613
3515
  Badge: exports.TableBadge
1614
3516
  });
1615
- var AttachmentListContext = React2.createContext({});
3517
+ var AttachmentListContext = React3.createContext({});
1616
3518
  var AttachmentList = (_a) => {
1617
3519
  var _b = _a, {
1618
3520
  onClick,
@@ -1630,7 +3532,7 @@ var AttachmentList = (_a) => {
1630
3532
  return /* @__PURE__ */ jsxRuntime.jsx(AttachmentListContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsxRuntime.jsx(base.StackContainer.Horizontal, __spreadProps(__spreadValues({ spacing: "spacing08" }, rest), { children })) });
1631
3533
  };
1632
3534
  exports.AttachmentList = AttachmentList;
1633
- var StyledSeparator = styled2__default.default.div`
3535
+ var StyledSeparator = styled3__default.default.div`
1634
3536
  width: 2px;
1635
3537
  height: 2px;
1636
3538
  background-color: var(--neutral400);