@homebound/beam 2.102.3 → 2.102.7

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.
@@ -41,6 +41,6 @@ function IconButton(props) {
41
41
  }
42
42
  exports.IconButton = IconButton;
43
43
  const iconButtonStylesReset = Css_1.Css.hPx(28).wPx(28).br8.bTransparent.bsSolid.bw2.bgTransparent.cursorPointer.outline0.p0.dif.aic.jcc.transition.$;
44
- exports.iconButtonStylesHover = Css_1.Css.bgGray100.$;
44
+ exports.iconButtonStylesHover = Css_1.Css.bgGray200.$;
45
45
  const iconButtonStylesFocus = Css_1.Css.bLightBlue700.$;
46
46
  const iconButtonStylesDisabled = Css_1.Css.cursorNotAllowed.$;
@@ -109,7 +109,6 @@ function GridTable(props) {
109
109
  // changes, and so by not passing the sortProps, it means the data rows' React.memo will still cache them.
110
110
  const sortProps = row.kind === "header" ? { sorting, sortState, setSortKey } : { sorting };
111
111
  const RowComponent = observeRows ? ObservedGridRow : MemoizedGridRow;
112
- const openCards = row.kind === "header" ? headerCards : rowCards;
113
112
  return ((0, jsx_runtime_1.jsx)(exports.GridCollapseContext.Provider, Object.assign({ value: row.kind === "header" ? collapseAllContext : collapseRowContext }, { children: (0, jsx_runtime_1.jsx)(RowComponent, Object.assign({}, {
114
113
  as,
115
114
  columns,
@@ -118,7 +117,7 @@ function GridTable(props) {
118
117
  rowStyles,
119
118
  stickyHeader,
120
119
  stickyOffset,
121
- openCards: openCards ? openCards.currentOpenCards() : undefined,
120
+ openCards: nestedCards ? nestedCards.currentOpenCards() : undefined,
122
121
  columnSizes,
123
122
  ...sortProps,
124
123
  }), void 0) }), `${row.kind}-${row.id}`));
@@ -127,9 +126,7 @@ function GridTable(props) {
127
126
  const headerRows = [];
128
127
  const filteredRows = [];
129
128
  // Misc state to track our nested card-ification, i.e. interleaved actual rows + chrome rows
130
- // for the header and row (non-header rows) cards.
131
- const headerCards = !!style.nestedCards && new nestedCards_1.NestedCards(columns, headerRows, style.nestedCards);
132
- const rowCards = !!style.nestedCards && new nestedCards_1.NestedCards(columns, filteredRows, style.nestedCards);
129
+ const nestedCards = !!style.nestedCards && new nestedCards_1.NestedCards(columns, filteredRows, style.nestedCards);
133
130
  // Depth-first to filter
134
131
  function visit(row) {
135
132
  var _a;
@@ -139,38 +136,30 @@ function GridTable(props) {
139
136
  // Even if we don't pass the filter, one of our children might, so we continue on after this check
140
137
  let isCard = false;
141
138
  if (matches) {
142
- isCard = rowCards && rowCards.maybeOpenCard(row);
139
+ isCard = nestedCards && nestedCards.maybeOpenCard(row);
143
140
  filteredRows.push([row, makeRowComponent(row)]);
144
141
  }
145
142
  const isCollapsed = collapsedIds.includes(row.id);
146
143
  if (!isCollapsed && !!((_a = row.children) === null || _a === void 0 ? void 0 : _a.length)) {
147
- rowCards && matches && rowCards.addSpacer();
144
+ nestedCards && matches && nestedCards.addSpacer();
148
145
  visitRows(row.children, isCard);
149
146
  }
150
- isCard && rowCards && rowCards.closeCard();
147
+ !(0, nestedCards_1.isLeafRow)(row) && isCard && nestedCards && nestedCards.closeCard();
151
148
  }
152
149
  function visitRows(rows, addSpacer) {
153
150
  const length = rows.length;
154
151
  rows.forEach((row, i) => {
155
- var _a;
156
152
  if (row.kind === "header") {
157
- // Flag to determine if the header has nested card styles.
158
- // This will determine if we should include opening and closing
159
- // Chrome rows.
160
- const isHeaderNested = !!((_a = style.nestedCards) === null || _a === void 0 ? void 0 : _a.kinds["header"]);
161
- isHeaderNested && headerCards && headerCards.maybeOpenCard(row);
162
153
  headerRows.push([row, makeRowComponent(row)]);
163
- isHeaderNested && headerCards && headerCards.closeCard();
164
- isHeaderNested && headerCards && headerCards.done();
165
154
  return;
166
155
  }
167
156
  visit(row);
168
- addSpacer && rowCards && i !== length - 1 && rowCards.addSpacer();
157
+ addSpacer && nestedCards && i !== length - 1 && nestedCards.addSpacer();
169
158
  });
170
159
  }
171
160
  // If nestedCards is set, we assume the top-level kind is a card, and so should add spacers between them
172
- visitRows(maybeSorted, !!rowCards);
173
- rowCards && rowCards.done();
161
+ visitRows(maybeSorted, !!nestedCards);
162
+ nestedCards && nestedCards.done();
174
163
  return [headerRows, filteredRows];
175
164
  }, [
176
165
  as,
@@ -221,49 +210,19 @@ const renders = {
221
210
  };
222
211
  /** Renders table using divs with flexbox rows, which is the default render */
223
212
  function renderDiv(style, id, columns, headerRows, filteredRows, firstRowMessage, _stickyHeader, firstLastColumnWidth, xss, _virtuosoRef) {
224
- var _a;
225
- // We must determine if the header is using nested card styles to account for
226
- // the opening and closing Chrome rows.
227
- const isNestedCardStyleHeader = !!((_a = style.nestedCards) === null || _a === void 0 ? void 0 : _a.kinds["header"]);
228
- /*
229
- Determine at what CSS selector index is the first non header row. Note that
230
- CSS selectors are not zero-based, unlike JavaScript, so we must add 1 to
231
- what we'd normally expect.
232
-
233
- Ex: When we don't have nestedCard styled headers, then we don't have opening
234
- and closing Chrome rows. Therefore, the first non-header row is the second
235
- row and since CSS selectors are not zero-based, we are aiming for a value
236
- of 2 (1 + 1).
237
-
238
- Ex: When we have nestedCard styled headers, then we have opening and closing
239
- Chrome rows. Therefore, the first non-header row is the fourth row because:
240
- - Row 1 is the opening Chrome Row
241
- - Row 2 is the header
242
- - Row 3 is the closing Chrome Row
243
- - Row 4 is the first non-header row
244
- And since CSS selectors are not zero-based, we are aiming for a value of 4
245
- (3 + 1).
246
- */
247
- const firstNonHeaderRowIndex = (!isNestedCardStyleHeader ? 1 : 3) + 1;
248
213
  return ((0, jsx_runtime_1.jsxs)("div", Object.assign({ css: {
249
214
  // Ensure all rows extend the same width
250
215
  ...Css_1.Css.mw("fit-content").$,
251
216
  /*
252
- Using n + (firstNonHeaderRowIndex + 1) here to target all rows that
253
- are after the first non-header row. Since n starts at 0, we can use
217
+ Using (n + 3) here to target all rows that are after the first non-header row. Since n starts at 0, we can use
254
218
  the + operator as an offset.
255
-
256
219
  Inspired by: https://stackoverflow.com/a/25005740/2551333
257
220
  */
258
- ...(style.betweenRowsCss
259
- ? Css_1.Css.addIn(`& > div:nth-of-type(n + ${firstNonHeaderRowIndex + 1}) > *`, style.betweenRowsCss).$
260
- : {}),
261
- ...(style.firstNonHeaderRowCss
262
- ? Css_1.Css.addIn(`& > div:nth-of-type(${firstNonHeaderRowIndex}) > *`, style.firstNonHeaderRowCss).$
263
- : {}),
221
+ ...(style.betweenRowsCss ? Css_1.Css.addIn(`& > div:nth-of-type(n+3) > *`, style.betweenRowsCss).$ : {}),
222
+ ...(style.firstNonHeaderRowCss ? Css_1.Css.addIn(`& > div:nth-of-type(2) > *`, style.firstNonHeaderRowCss).$ : {}),
264
223
  ...style.rootCss,
265
224
  ...xss,
266
- }, "data-testid": id }, { children: [headerRows.map(([, node]) => node), firstRowMessage && (0, jsx_runtime_1.jsx)("div", Object.assign({ css: { ...style.firstRowMessageCss } }, { children: firstRowMessage }), void 0), filteredRows.map(([, node]) => node)] }), void 0));
225
+ }, "data-testid": id }, { children: [headerRows.map(([, node]) => node), firstRowMessage && ((0, jsx_runtime_1.jsx)("div", Object.assign({ css: { ...style.firstRowMessageCss }, "data-gridrow": true }, { children: firstRowMessage }), void 0)), filteredRows.map(([, node]) => node)] }), void 0));
267
226
  }
268
227
  /** Renders as a table, primarily/solely for good print support. */
269
228
  function renderTable(style, id, columns, headerRows, filteredRows, firstRowMessage, _stickyHeader, _firstLastColumnWidth, xss, _virtuosoRef) {
@@ -310,16 +269,7 @@ function renderVirtual(style, id, columns, headerRows, filteredRows, firstRowMes
310
269
  Footer: () => (0, jsx_runtime_1.jsx)("div", { css: footerStyle }, void 0),
311
270
  },
312
271
  // Pin/sticky both the header row(s) + firstRowMessage to the top
313
- topItemCount: (stickyHeader ? headerRows.length : 0) + (firstRowMessage ? 1 : 0), itemSize: (el) => {
314
- const maybeContentsDiv = el.firstElementChild;
315
- // If it is a chrome row, then we are not using `display: contents;`, return the height of this element.
316
- if ("chrome" in maybeContentsDiv.dataset) {
317
- return maybeContentsDiv.getBoundingClientRect().height || 1;
318
- }
319
- // Both the `Item` and `itemContent` use `display: contents`, so their height is 0,
320
- // so instead drill into the 1st real content cell.
321
- return maybeContentsDiv.firstElementChild.getBoundingClientRect().height;
322
- }, itemContent: (index) => {
272
+ topItemCount: (stickyHeader ? headerRows.length : 0) + (firstRowMessage ? 1 : 0), itemContent: (index) => {
323
273
  // Since we have two arrays of rows: `headerRows` and `filteredRow` we
324
274
  // must determine which one to render.
325
275
  // Determine if we need to render a header row
@@ -407,7 +357,7 @@ function calcColumnSizes(columns, firstLastColumnWidth) {
407
357
  else {
408
358
  throw new Error("Beam Table column width definition only supports px, percentage, or fr units");
409
359
  }
410
- }, { claimedPercentages: 0, claimedPixels: firstLastColumnWidth ? firstLastColumnWidth * 2 : 0, totalFr: 0 });
360
+ }, { claimedPercentages: 0, claimedPixels: 0, totalFr: 0 });
411
361
  // This is our "fake but for some reason it lines up better" fr calc
412
362
  function fr(myFr) {
413
363
  return `((100% - ${claimedPercentages}% - ${claimedPixels}px) * (${myFr} / ${totalFr}))`;
@@ -455,93 +405,84 @@ function GridRow(props) {
455
405
  // We treat the "header" kind as special for "good defaults" styling
456
406
  const isHeader = row.kind === "header";
457
407
  const rowStyle = rowStyles === null || rowStyles === void 0 ? void 0 : rowStyles[row.kind];
408
+ const Row = as === "table" ? "tr" : "div";
409
+ const openCardStyles = typeof openCards === "string"
410
+ ? openCards
411
+ .split(":")
412
+ .map((openCardKind) => style.nestedCards.kinds[openCardKind])
413
+ .filter((style) => style)
414
+ : undefined;
458
415
  const rowStyleCellCss = maybeApplyFunction(row, rowStyle === null || rowStyle === void 0 ? void 0 : rowStyle.cellCss);
459
416
  const rowCss = {
460
- // For virtual tables use `display: flex` to keep all cells on the same row, but use `flexNone` to ensure the cells stay their defined widths
461
- ...(as === "table" ? {} : Css_1.Css.df.addIn("&>*", Css_1.Css.flexNone.$).$),
417
+ // For virtual tables use `display: flex` to keep all cells on the same row. For each cell in the row use `flexNone` to ensure they stay their defined widths
418
+ ...(as === "table" ? {} : Css_1.Css.relative.df.fg1.fs1.addIn("&>*", Css_1.Css.flexNone.$).$),
462
419
  ...(((rowStyle === null || rowStyle === void 0 ? void 0 : rowStyle.rowLink) || (rowStyle === null || rowStyle === void 0 ? void 0 : rowStyle.onClick)) &&
463
420
  style.rowHoverColor && {
464
421
  // Even though backgroundColor is set on the cellCss (due to display: content), the hover target is the row.
465
422
  "&:hover > *": Css_1.Css.cursorPointer.bgColor(maybeDarken(rowStyleCellCss === null || rowStyleCellCss === void 0 ? void 0 : rowStyleCellCss.backgroundColor, style.rowHoverColor)).$,
466
423
  }),
467
424
  ...maybeApplyFunction(row, rowStyle === null || rowStyle === void 0 ? void 0 : rowStyle.rowCss),
425
+ // Maybe add the sticky header styles
468
426
  ...(isHeader && stickyHeader ? Css_1.Css.sticky.top(stickyOffset).z1.$ : undefined),
427
+ ...(0, nestedCards_1.getNestedCardStyles)(row, openCardStyles, style),
469
428
  };
470
- const Row = as === "table" ? "tr" : "div";
471
- const openCardStyles = typeof openCards === "string"
472
- ? openCards
473
- .split(":")
474
- .map((openCardKind) => style.nestedCards.kinds[openCardKind])
475
- .filter((style) => style)
476
- : undefined;
477
- const currentCard = openCardStyles && openCardStyles[openCardStyles.length - 1];
478
429
  let currentColspan = 1;
479
- const maybeStickyHeaderStyles = isHeader && stickyHeader ? Css_1.Css.sticky.top(stickyOffset).z1.$ : undefined;
480
- return ((0, jsx_runtime_1.jsxs)(Row, Object.assign({ css: rowCss }, others, { children: [openCardStyles &&
481
- (0, nestedCards_1.maybeAddCardPadding)(openCardStyles, "first", {
482
- ...maybeStickyHeaderStyles,
483
- ...(columnSizes ? Css_1.Css.w(columnSizes[0]).$ : {}),
484
- }), columns.map((column, columnIndex) => {
485
- var _a;
486
- // Decrement colspan count and skip if greater than 1.
487
- if (currentColspan > 1) {
488
- currentColspan -= 1;
489
- return;
490
- }
491
- const maybeContent = applyRowFn(column, row);
492
- currentColspan = isGridCellContent(maybeContent) ? (_a = maybeContent.colspan) !== null && _a !== void 0 ? _a : 1 : 1;
493
- const canSortColumn = ((sorting === null || sorting === void 0 ? void 0 : sorting.on) === "client" && column.clientSideSort !== false) ||
494
- ((sorting === null || sorting === void 0 ? void 0 : sorting.on) === "server" && !!column.serverSideSortKey);
495
- const alignment = getAlignment(column, maybeContent);
496
- const justificationCss = getJustification(column, maybeContent, as, alignment);
497
- const content = toContent(maybeContent, isHeader, canSortColumn, (sorting === null || sorting === void 0 ? void 0 : sorting.on) === "client", style, as, alignment);
498
- (0, sortRows_1.ensureClientSideSortValueIsSortable)(sorting, isHeader, column, columnIndex, maybeContent);
499
- const maybeNestedCardColumnIndex = columnIndex + (style.nestedCards ? 1 : 0);
500
- // Note that it seems expensive to calc a per-cell class name/CSS-in-JS output,
501
- // vs. setting global/table-wide CSS like `style.cellCss` on the root grid div with
502
- // a few descendent selectors. However, that approach means the root grid-applied
503
- // CSS has a high-specificity and so its harder for per-page/per-cell business logic
504
- // to override it. So, we just calc the combined table-wide+per-cell-overridden CSS here,
505
- // in a very CSS-in-JS idiomatic manner.
506
- //
507
- // In practice we've not seen any performance issues with this from our "large but
508
- // not Google spreadsheets" tables.
509
- const cellCss = {
510
- // Adding display flex so we can align content within the cells
511
- ...Css_1.Css.df.$,
512
- // Apply any static/all-cell styling
513
- ...style.cellCss,
514
- // Then override with first/last cell styling
515
- ...getFirstOrLastCellCss(style, columnIndex, columns),
516
- // Then override with per-cell/per-row justification/indentation
517
- ...justificationCss,
518
- ...getIndentationCss(style, rowStyle, columnIndex, maybeContent),
519
- // Then apply any header-specific override
520
- ...(isHeader && style.headerCellCss),
521
- // If we're within a card, use its background color
522
- ...(currentCard && Css_1.Css.bgColor(currentCard.bgColor).$),
523
- // And finally the specific cell's css (if any from GridCellContent)
524
- ...rowStyleCellCss,
525
- // Define the width of the column on each cell. Supports col spans.
526
- ...(columnSizes && {
527
- width: `calc(${columnSizes
528
- .slice(maybeNestedCardColumnIndex, maybeNestedCardColumnIndex + currentColspan)
529
- .join(" + ")})`,
530
- }),
531
- };
532
- const renderFn = (rowStyle === null || rowStyle === void 0 ? void 0 : rowStyle.renderCell) || (rowStyle === null || rowStyle === void 0 ? void 0 : rowStyle.rowLink)
533
- ? rowLinkRenderFn(as)
534
- : isHeader
535
- ? headerRenderFn(columns, column, sortState, setSortKey, as)
536
- : (rowStyle === null || rowStyle === void 0 ? void 0 : rowStyle.onClick)
537
- ? rowClickRenderFn(as)
538
- : defaultRenderFn(as);
539
- return renderFn(columnIndex, cellCss, content, row, rowStyle);
540
- }), openCardStyles &&
541
- (0, nestedCards_1.maybeAddCardPadding)(openCardStyles, "final", {
542
- ...maybeStickyHeaderStyles,
543
- ...(columnSizes ? Css_1.Css.w(columnSizes[columnSizes.length - 1]).$ : {}),
544
- })] }), void 0));
430
+ const rowNode = ((0, jsx_runtime_1.jsx)(Row, Object.assign({ css: rowCss }, others, { "data-gridrow": true }, { children: columns.map((column, columnIndex) => {
431
+ var _a;
432
+ // Decrement colspan count and skip if greater than 1.
433
+ if (currentColspan > 1) {
434
+ currentColspan -= 1;
435
+ return;
436
+ }
437
+ const maybeContent = applyRowFn(column, row);
438
+ currentColspan = isGridCellContent(maybeContent) ? (_a = maybeContent.colspan) !== null && _a !== void 0 ? _a : 1 : 1;
439
+ const canSortColumn = ((sorting === null || sorting === void 0 ? void 0 : sorting.on) === "client" && column.clientSideSort !== false) ||
440
+ ((sorting === null || sorting === void 0 ? void 0 : sorting.on) === "server" && !!column.serverSideSortKey);
441
+ const alignment = getAlignment(column, maybeContent);
442
+ const justificationCss = getJustification(column, maybeContent, as, alignment);
443
+ const content = toContent(maybeContent, isHeader, canSortColumn, (sorting === null || sorting === void 0 ? void 0 : sorting.on) === "client", style, as, alignment);
444
+ (0, sortRows_1.ensureClientSideSortValueIsSortable)(sorting, isHeader, column, columnIndex, maybeContent);
445
+ const maybeNestedCardColumnIndex = columnIndex + (style.nestedCards ? 1 : 0);
446
+ // Note that it seems expensive to calc a per-cell class name/CSS-in-JS output,
447
+ // vs. setting global/table-wide CSS like `style.cellCss` on the root grid div with
448
+ // a few descendent selectors. However, that approach means the root grid-applied
449
+ // CSS has a high-specificity and so its harder for per-page/per-cell business logic
450
+ // to override it. So, we just calc the combined table-wide+per-cell-overridden CSS here,
451
+ // in a very CSS-in-JS idiomatic manner.
452
+ //
453
+ // In practice we've not seen any performance issues with this from our "large but
454
+ // not Google spreadsheets" tables.
455
+ const cellCss = {
456
+ // Adding display flex so we can align content within the cells
457
+ ...Css_1.Css.df.$,
458
+ // Apply any static/all-cell styling
459
+ ...style.cellCss,
460
+ // Then override with first/last cell styling
461
+ ...getFirstOrLastCellCss(style, columnIndex, columns),
462
+ // Then override with per-cell/per-row justification/indentation
463
+ ...justificationCss,
464
+ ...getIndentationCss(style, rowStyle, columnIndex, maybeContent),
465
+ // Then apply any header-specific override
466
+ ...(isHeader && style.headerCellCss),
467
+ // And finally the specific cell's css (if any from GridCellContent)
468
+ ...rowStyleCellCss,
469
+ // Define the width of the column on each cell. Supports col spans.
470
+ ...(columnSizes && {
471
+ width: `calc(${columnSizes
472
+ .slice(maybeNestedCardColumnIndex, maybeNestedCardColumnIndex + currentColspan)
473
+ .join(" + ")})`,
474
+ }),
475
+ };
476
+ const renderFn = (rowStyle === null || rowStyle === void 0 ? void 0 : rowStyle.renderCell) || (rowStyle === null || rowStyle === void 0 ? void 0 : rowStyle.rowLink)
477
+ ? rowLinkRenderFn(as)
478
+ : isHeader
479
+ ? headerRenderFn(columns, column, sortState, setSortKey, as)
480
+ : (rowStyle === null || rowStyle === void 0 ? void 0 : rowStyle.onClick)
481
+ ? rowClickRenderFn(as)
482
+ : defaultRenderFn(as);
483
+ return renderFn(columnIndex, cellCss, content, row, rowStyle);
484
+ }) }), void 0));
485
+ return openCardStyles && openCardStyles.length > 0 ? (0, nestedCards_1.wrapCard)(openCardStyles, rowNode) : rowNode;
545
486
  }
546
487
  // Fix to work with generics, see https://github.com/DefinitelyTyped/DefinitelyTyped/issues/37087#issuecomment-656596623
547
488
  const MemoizedGridRow = react_1.default.memo(GridRow);
@@ -1,5 +1,5 @@
1
1
  import { ReactElement } from "react";
2
- import { GridColumn, GridDataRow, Kinded, NestedCardsStyle, NestedCardStyle, NestedCardStyleByKind, RowTuple } from "./GridTable";
2
+ import { GridColumn, GridDataRow, GridStyle, Kinded, NestedCardsStyle, NestedCardStyle, NestedCardStyleByKind, RowTuple } from "./GridTable";
3
3
  declare type Chrome = () => JSX.Element;
4
4
  declare type ChromeBuffer = Chrome[];
5
5
  /**
@@ -71,10 +71,23 @@ export declare class NestedCards {
71
71
  */
72
72
  export declare function makeOpenOrCloseCard(openCards: string[], cardStyles: NestedCardStyleByKind, kind: "open" | "close"): Chrome;
73
73
  /**
74
- * For the first or last cell of actual content, wrap them in divs that re-create the
75
- * outer cards' padding + background.
74
+ * Wraps a row within its parent cards. Creates a wrapping div to add the card padding.
75
+ * Adds non-leaf card padding and borders, e.g. if the current row is a non-leaf then it will already be in `openCards`
76
+ * Example:
77
+ * <div parent> <div child> <div grandchild /> </div> </div>
76
78
  */
77
- export declare function maybeAddCardPadding(openCards: NestedCardStyle[], column: "first" | "final", styles?: {}): any;
79
+ export declare function wrapCard(openCards: NestedCardStyle[], row: JSX.Element): JSX.Element;
80
+ export declare function getNestedCardStyles(row: GridDataRow<any>, openCardStyles: NestedCardStyle[] | undefined, style: GridStyle): {
81
+ paddingTop?: import("csstype").Property.PaddingTop<0 | (string & {})> | undefined;
82
+ paddingBottom?: import("csstype").Property.PaddingBottom<0 | (string & {})> | undefined;
83
+ borderRadius?: import("csstype").Property.BorderRadius<0 | (string & {})> | undefined;
84
+ backgroundColor?: import("csstype").Property.BackgroundColor | undefined;
85
+ borderColor?: import("csstype").Property.BorderColor | undefined;
86
+ borderStyle?: import("csstype").Property.BorderStyle | undefined;
87
+ borderWidth?: import("csstype").Property.BorderWidth<0 | (string & {})> | undefined;
88
+ paddingLeft?: import("csstype").Property.PaddingLeft<0 | (string & {})> | undefined;
89
+ paddingRight?: import("csstype").Property.PaddingRight<0 | (string & {})> | undefined;
90
+ };
78
91
  /**
79
92
  * Create a spacer between rows of children.
80
93
  *
@@ -88,4 +101,5 @@ interface ChromeRowProps {
88
101
  }
89
102
  export declare function ChromeRow({ chromeBuffer, columns }: ChromeRowProps): import("@emotion/react/jsx-runtime").JSX.Element;
90
103
  export declare function dropChromeRows<R extends Kinded>(rows: RowTuple<R>[]): [GridDataRow<R>, ReactElement][];
104
+ export declare function isLeafRow<R extends Kinded>(row: GridDataRow<R>): boolean;
91
105
  export {};
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.dropChromeRows = exports.ChromeRow = exports.makeSpacer = exports.maybeAddCardPadding = exports.makeOpenOrCloseCard = exports.NestedCards = void 0;
3
+ exports.isLeafRow = exports.dropChromeRows = exports.ChromeRow = exports.makeSpacer = exports.getNestedCardStyles = exports.wrapCard = exports.makeOpenOrCloseCard = exports.NestedCards = void 0;
4
4
  const jsx_runtime_1 = require("@emotion/react/jsx-runtime");
5
5
  const react_1 = require("react");
6
6
  const Css_1 = require("../../Css");
@@ -37,8 +37,8 @@ class NestedCards {
37
37
  */
38
38
  maybeOpenCard(row) {
39
39
  const card = this.styles.kinds[row.kind];
40
- // If this kind doesn't have a card defined, don't put it on the card stack
41
- if (card) {
40
+ // If this kind doesn't have a card defined or is a leaf card (which handle their own card styles in GridRow), then don't put it on the card stack
41
+ if (card && !isLeafRow(row)) {
42
42
  this.openCards.push(row.kind);
43
43
  this.chromeBuffer.push(makeOpenOrCloseCard(this.openCards, this.styles.kinds, "open"));
44
44
  }
@@ -138,21 +138,47 @@ function makeOpenOrCloseCard(openCards, cardStyles, kind) {
138
138
  }
139
139
  exports.makeOpenOrCloseCard = makeOpenOrCloseCard;
140
140
  /**
141
- * For the first or last cell of actual content, wrap them in divs that re-create the
142
- * outer cards' padding + background.
141
+ * Wraps a row within its parent cards. Creates a wrapping div to add the card padding.
142
+ * Adds non-leaf card padding and borders, e.g. if the current row is a non-leaf then it will already be in `openCards`
143
+ * Example:
144
+ * <div parent> <div child> <div grandchild /> </div> </div>
143
145
  */
144
- function maybeAddCardPadding(openCards, column, styles) {
145
- let div = undefined;
146
+ function wrapCard(openCards, row) {
147
+ let div = row;
146
148
  [...openCards].reverse().forEach((card) => {
147
149
  div = ((0, jsx_runtime_1.jsx)("div", Object.assign({ css: {
148
- ...Css_1.Css.h100.bgColor(card.bgColor).if(!!card.bColor).bc(card.bColor).$,
149
- ...(column === "first" && Css_1.Css.plPx(card.pxPx).if(!!card.bColor).bl.$),
150
- ...(column === "final" && Css_1.Css.prPx(card.pxPx).if(!!card.bColor).br.$),
150
+ ...Css_1.Css.h100.pxPx(card.pxPx).bgColor(card.bgColor).if(!!card.bColor).bc(card.bColor).bl.br.$,
151
151
  } }, { children: div }), void 0));
152
152
  });
153
- return ((0, jsx_runtime_1.jsx)("div", Object.assign({ "data-cardpadding": "true" }, (styles ? { css: styles } : {}), { children: div }), void 0));
153
+ return div;
154
154
  }
155
- exports.maybeAddCardPadding = maybeAddCardPadding;
155
+ exports.wrapCard = wrapCard;
156
+ function getNestedCardStyles(row, openCardStyles, style) {
157
+ var _a, _b, _c;
158
+ const leafCardStyles = isLeafRow(row) ? (_a = style.nestedCards) === null || _a === void 0 ? void 0 : _a.kinds[row.kind] : undefined;
159
+ // Calculate the horizontal space already allocated by the open cards (paddings and borders)
160
+ const openCardWidth = openCardStyles ? openCardStyles.reduce((acc, o) => acc + o.pxPx + (o.bColor ? 1 : 0), 0) : 0;
161
+ // Subtract the openCardWidth from the `firstLastColumnWidth` to determine the amount of padding to add to this card.
162
+ // Also if it is a leaf card, then we need to additionally subtract out the border width to have it properly line up with the chrome rows
163
+ const currentCardPaddingWidth = ((_c = (_b = style.nestedCards) === null || _b === void 0 ? void 0 : _b.firstLastColumnWidth) !== null && _c !== void 0 ? _c : 0) - openCardWidth - ((leafCardStyles === null || leafCardStyles === void 0 ? void 0 : leafCardStyles.bColor) ? 1 : 0);
164
+ return {
165
+ // Card styles apply a calculated padding to ensure the content lines up properly across all columns
166
+ ...(currentCardPaddingWidth ? Css_1.Css.pxPx(currentCardPaddingWidth).$ : undefined),
167
+ // Leaf cards define their own borders + padding
168
+ ...(leafCardStyles
169
+ ? // We can have versions of the same card as a leaf and not as a leaf.
170
+ // When it is not a leaf then it has chrome rows that create the top and bottom "padding" based on border-radius size. (brPx = "chrome" row height)
171
+ // When it is a leaf, then we need to apply the brPx to the row to ensure consistent spacing between leaf & non-leaf renders
172
+ // Additionally, if the leaf card has a border, then subtract the 1px border width from the padding to keep consistent with the "chrome" row
173
+ Css_1.Css.pyPx(leafCardStyles.brPx - (leafCardStyles.bColor ? 1 : 0))
174
+ .borderRadius(`${leafCardStyles.brPx}px`)
175
+ .bgColor(leafCardStyles.bgColor)
176
+ .if(!!leafCardStyles.bColor)
177
+ .bc(leafCardStyles.bColor).ba.$
178
+ : undefined),
179
+ };
180
+ }
181
+ exports.getNestedCardStyles = getNestedCardStyles;
156
182
  /**
157
183
  * Create a spacer between rows of children.
158
184
  *
@@ -178,10 +204,14 @@ exports.makeSpacer = makeSpacer;
178
204
  function ChromeRow({ chromeBuffer, columns }) {
179
205
  return (
180
206
  // We add 2 to account for our dedicated open/close columns
181
- (0, jsx_runtime_1.jsx)("div", Object.assign({ css: Css_1.Css.gc(`span ${columns + 2}`).$, "data-chrome": "true" }, { children: chromeBuffer.map((c, i) => ((0, jsx_runtime_1.jsx)(react_1.Fragment, { children: c() }, i))) }), void 0));
207
+ (0, jsx_runtime_1.jsx)("div", Object.assign({ css: Css_1.Css.gc(`span ${columns + 2}`).$ }, { children: chromeBuffer.map((c, i) => ((0, jsx_runtime_1.jsx)(react_1.Fragment, { children: c() }, i))) }), void 0));
182
208
  }
183
209
  exports.ChromeRow = ChromeRow;
184
210
  function dropChromeRows(rows) {
185
211
  return rows.filter(([r]) => !!r);
186
212
  }
187
213
  exports.dropChromeRows = dropChromeRows;
214
+ function isLeafRow(row) {
215
+ return row.children === undefined || row.children.length === 0;
216
+ }
217
+ exports.isLeafRow = isLeafRow;
@@ -51,6 +51,11 @@ function deriveSortState(currentSortState, clickedKey, initialSortState) {
51
51
  if (!currentSortState || clickedKey !== currentKey) {
52
52
  return [clickedKey, GridTable_1.ASC];
53
53
  }
54
+ // If there is an `initialSortState` and we're clicking on that same key, then flip the sort.
55
+ // Handles cases where the initial sort is DESC so that we can allow for DESC to ASC sorting.
56
+ if (initialSortState && initialSortState[0] === clickedKey) {
57
+ return [clickedKey, currentDirection === GridTable_1.ASC ? GridTable_1.DESC : GridTable_1.ASC];
58
+ }
54
59
  // Otherwise when clicking the current column, toggle through sort states
55
60
  if (currentDirection === GridTable_1.ASC) {
56
61
  // if ASC -> go to desc
@@ -1,7 +1,6 @@
1
1
  export * from "./Chip";
2
2
  export * from "./Chips";
3
3
  export * from "./Table/GridTable";
4
- export { makeOpenOrCloseCard, makeSpacer, maybeAddCardPadding } from "./Table/nestedCards";
5
4
  export * from "./ToggleChip";
6
5
  export * from "./ToggleChips";
7
6
  export * from "./Alert";
@@ -10,14 +10,10 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
10
10
  for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
11
11
  };
12
12
  Object.defineProperty(exports, "__esModule", { value: true });
13
- exports.TabsWithContent = exports.Tabs = exports.TabContent = exports.PresentationProvider = exports.NavLink = exports.BeamProvider = exports.maybeAddCardPadding = exports.makeSpacer = exports.makeOpenOrCloseCard = void 0;
13
+ exports.TabsWithContent = exports.Tabs = exports.TabContent = exports.PresentationProvider = exports.NavLink = exports.BeamProvider = void 0;
14
14
  __exportStar(require("./Chip"), exports);
15
15
  __exportStar(require("./Chips"), exports);
16
16
  __exportStar(require("./Table/GridTable"), exports);
17
- var nestedCards_1 = require("./Table/nestedCards");
18
- Object.defineProperty(exports, "makeOpenOrCloseCard", { enumerable: true, get: function () { return nestedCards_1.makeOpenOrCloseCard; } });
19
- Object.defineProperty(exports, "makeSpacer", { enumerable: true, get: function () { return nestedCards_1.makeSpacer; } });
20
- Object.defineProperty(exports, "maybeAddCardPadding", { enumerable: true, get: function () { return nestedCards_1.maybeAddCardPadding; } });
21
17
  __exportStar(require("./ToggleChip"), exports);
22
18
  __exportStar(require("./ToggleChips"), exports);
23
19
  __exportStar(require("./Alert"), exports);
package/dist/utils/rtl.js CHANGED
@@ -38,8 +38,7 @@ function cell(r, row, column) {
38
38
  }
39
39
  exports.cell = cell;
40
40
  function cellOf(r, tableTestId, rowNum, column) {
41
- const nonPaddingColumns = Array.from(row(r, rowNum, tableTestId).childNodes).filter((node) => !("cardpadding" in node.dataset));
42
- return nonPaddingColumns[column];
41
+ return row(r, rowNum, tableTestId).childNodes[column];
43
42
  }
44
43
  exports.cellOf = cellOf;
45
44
  function cellAnd(r, row, column, testId) {
@@ -48,8 +47,8 @@ function cellAnd(r, row, column, testId) {
48
47
  }
49
48
  exports.cellAnd = cellAnd;
50
49
  function row(r, row, tableTestId = "gridTable") {
51
- const nonChromeRows = Array.from(r.getByTestId(tableTestId).childNodes).filter((node) => !("chrome" in node.dataset));
52
- return nonChromeRows[row];
50
+ const dataRows = Array.from(r.getByTestId(tableTestId).querySelectorAll("[data-gridrow]"));
51
+ return dataRows[row];
53
52
  }
54
53
  exports.row = row;
55
54
  function rowAnd(r, rowNum, testId) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@homebound/beam",
3
- "version": "2.102.3",
3
+ "version": "2.102.7",
4
4
  "author": "Homebound",
5
5
  "license": "MIT",
6
6
  "main": "dist/index.js",