playbook_ui 14.12.0.pre.rc.11 → 14.12.0.pre.rc.12

Sign up to get free protection for your applications and to get access to all the features.
Files changed (98) hide show
  1. checksums.yaml +4 -4
  2. data/app/pb_kits/playbook/_playbook.scss +2 -0
  3. data/app/pb_kits/playbook/pb_advanced_table/Components/CustomCell.tsx +18 -2
  4. data/app/pb_kits/playbook/pb_advanced_table/Components/TableHeaderCell.tsx +27 -5
  5. data/app/pb_kits/playbook/pb_advanced_table/SubKits/TableBody.tsx +17 -2
  6. data/app/pb_kits/playbook/pb_advanced_table/SubKits/TableHeader.tsx +23 -1
  7. data/app/pb_kits/playbook/pb_advanced_table/_advanced_table.scss +29 -0
  8. data/app/pb_kits/playbook/pb_advanced_table/_advanced_table.tsx +61 -4
  9. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_no_subrows.jsx +50 -0
  10. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_pagination.jsx +1 -0
  11. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_pagination_with_props.jsx +1 -0
  12. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_selectable_rows.jsx +60 -0
  13. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_selectable_rows.md +5 -0
  14. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_selectable_rows_actions.jsx +78 -0
  15. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_selectable_rows_actions.md +1 -0
  16. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_selectable_rows_header.jsx +53 -0
  17. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_selectable_rows_header.md +1 -0
  18. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_selectable_rows_no_subrows.jsx +52 -0
  19. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_selectable_rows_no_subrows.md +1 -0
  20. data/app/pb_kits/playbook/pb_advanced_table/docs/_advanced_table_sort_control.md +2 -2
  21. data/app/pb_kits/playbook/pb_advanced_table/docs/advanced_table_mock_data_no_subrows.json +42 -0
  22. data/app/pb_kits/playbook/pb_advanced_table/docs/advanced_table_mock_data_with_id.json +299 -0
  23. data/app/pb_kits/playbook/pb_advanced_table/docs/example.yml +5 -0
  24. data/app/pb_kits/playbook/pb_advanced_table/docs/index.js +6 -1
  25. data/app/pb_kits/playbook/pb_collapsible/collapsible.html.erb +3 -1
  26. data/app/pb_kits/playbook/pb_collapsible/collapsible.rb +3 -0
  27. data/app/pb_kits/playbook/pb_date_picker/date_picker.html.erb +22 -10
  28. data/app/pb_kits/playbook/pb_date_picker/date_picker.rb +2 -0
  29. data/app/pb_kits/playbook/pb_date_picker/docs/_date_picker_turbo_frames.html.erb +13 -0
  30. data/app/pb_kits/playbook/pb_date_picker/docs/_date_picker_turbo_frames_rails.md +3 -0
  31. data/app/pb_kits/playbook/pb_date_picker/docs/example.yml +1 -0
  32. data/app/pb_kits/playbook/pb_drawer/_drawer.scss +145 -183
  33. data/app/pb_kits/playbook/pb_drawer/_drawer.tsx +158 -268
  34. data/app/pb_kits/playbook/pb_drawer/context.ts +11 -0
  35. data/app/pb_kits/playbook/pb_drawer/docs/_drawer_behavior.jsx +38 -0
  36. data/app/pb_kits/playbook/pb_drawer/docs/_drawer_borders.jsx +3 -45
  37. data/app/pb_kits/playbook/pb_drawer/docs/_drawer_breakpoints.jsx +0 -1
  38. data/app/pb_kits/playbook/pb_drawer/docs/_drawer_default.jsx +9 -16
  39. data/app/pb_kits/playbook/pb_drawer/docs/_drawer_menu.jsx +44 -19
  40. data/app/pb_kits/playbook/pb_drawer/docs/_drawer_menu.md +21 -3
  41. data/app/pb_kits/playbook/pb_drawer/docs/_drawer_overlay.jsx +16 -21
  42. data/app/pb_kits/playbook/pb_drawer/docs/_drawer_sizes.jsx +2 -19
  43. data/app/pb_kits/playbook/pb_drawer/docs/example.yml +2 -1
  44. data/app/pb_kits/playbook/pb_drawer/docs/index.js +1 -0
  45. data/app/pb_kits/playbook/pb_drawer/drawer.test.jsx +5 -5
  46. data/app/pb_kits/playbook/pb_drawer/hooks/useBreakpoint.tsx +60 -0
  47. data/app/pb_kits/playbook/pb_drawer/hooks/useDrawerAnimation.tsx +21 -0
  48. data/app/pb_kits/playbook/pb_dropdown/docs/_dropdown_subtle_variant.md +1 -1
  49. data/app/pb_kits/playbook/pb_icon_button/_icon_button.scss +78 -0
  50. data/app/pb_kits/playbook/pb_icon_button/docs/_icon_button_default.html.erb +3 -0
  51. data/app/pb_kits/playbook/pb_icon_button/docs/example.yml +7 -0
  52. data/app/pb_kits/playbook/pb_icon_button/icon_button.html.erb +16 -0
  53. data/app/pb_kits/playbook/pb_icon_button/icon_button.rb +22 -0
  54. data/app/pb_kits/playbook/pb_loading_inline/_loading_inline.tsx +6 -1
  55. data/app/pb_kits/playbook/pb_multiple_users/_multiple_users.scss +4 -0
  56. data/app/pb_kits/playbook/pb_multiple_users/_multiple_users.tsx +1 -0
  57. data/app/pb_kits/playbook/pb_multiple_users/multiple_users.html.erb +1 -1
  58. data/app/pb_kits/playbook/pb_radio/_radio.scss +12 -8
  59. data/app/pb_kits/playbook/pb_radio/docs/_radio_custom_children.jsx +8 -3
  60. data/app/pb_kits/playbook/pb_select/_select.scss +3 -5
  61. data/app/pb_kits/playbook/pb_select/_select.tsx +5 -1
  62. data/app/pb_kits/playbook/pb_select/select.html.erb +2 -2
  63. data/app/pb_kits/playbook/pb_selectable_icon/_selectable_icon.tsx +9 -1
  64. data/app/pb_kits/playbook/pb_selectable_icon/docs/_selectable_icon_default.jsx +4 -1
  65. data/app/pb_kits/playbook/pb_selectable_icon/docs/_selectable_icon_single_select.jsx +4 -1
  66. data/app/pb_kits/playbook/pb_table/docs/_table_with_collapsible.html.erb +47 -0
  67. data/app/pb_kits/playbook/pb_table/docs/_table_with_collapsible_rails.md +2 -0
  68. data/app/pb_kits/playbook/pb_table/docs/example.yml +1 -0
  69. data/app/pb_kits/playbook/pb_table/index.ts +177 -137
  70. data/app/pb_kits/playbook/pb_table/styles/_collapsible.scss +12 -0
  71. data/app/pb_kits/playbook/pb_table/table_row.html.erb +20 -1
  72. data/app/pb_kits/playbook/pb_table/table_row.rb +5 -0
  73. data/app/pb_kits/playbook/pb_text_input/docs/_text_input_mask.html.erb +46 -0
  74. data/app/pb_kits/playbook/pb_text_input/docs/_text_input_mask_rails.md +3 -0
  75. data/app/pb_kits/playbook/pb_text_input/docs/example.yml +2 -1
  76. data/app/pb_kits/playbook/pb_text_input/index.js +103 -0
  77. data/app/pb_kits/playbook/pb_text_input/text_input.html.erb +4 -0
  78. data/app/pb_kits/playbook/pb_text_input/text_input.rb +33 -3
  79. data/app/pb_kits/playbook/pb_typeahead/docs/_typeahead_truncated_text.html.erb +19 -0
  80. data/app/pb_kits/playbook/pb_typeahead/docs/_typeahead_truncated_text.jsx +27 -0
  81. data/app/pb_kits/playbook/pb_typeahead/docs/_typeahead_truncated_text.md +1 -0
  82. data/app/pb_kits/playbook/pb_typeahead/docs/example.yml +2 -0
  83. data/app/pb_kits/playbook/pb_typeahead/docs/index.js +1 -0
  84. data/dist/chunks/_typeahead-BWwaAo_0.js +36 -0
  85. data/dist/chunks/_weekday_stacked-zyBCd1s8.js +45 -0
  86. data/dist/chunks/{lib-OFT985dg.js → lib-kMuhBuU7.js} +1 -1
  87. data/dist/chunks/{pb_form_validation-CrsXd1-Y.js → pb_form_validation-DBJ0wZuS.js} +1 -1
  88. data/dist/chunks/vendor.js +1 -1
  89. data/dist/menu.yml +6 -0
  90. data/dist/playbook-doc.js +1 -1
  91. data/dist/playbook-rails-react-bindings.js +1 -1
  92. data/dist/playbook-rails.js +1 -1
  93. data/dist/playbook.css +1 -1
  94. data/lib/playbook/version.rb +1 -1
  95. metadata +37 -7
  96. data/dist/chunks/_typeahead-TN5aDUj9.js +0 -36
  97. data/dist/chunks/_weekday_stacked-en9fB1YM.js +0 -45
  98. /data/app/pb_kits/playbook/pb_table/docs/{_table_with_collapsible.md → _table_with_collapsible_react.md} +0 -0
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 3d0900eaee4ff9082d0442fd1029f6d4f78404bb47c7da45af313d0dabd07790
4
- data.tar.gz: f4ee1854238c899ea7c38cfe9cac6adbaf5ea8c7f449bbccbfe1d3711c712c85
3
+ metadata.gz: b01422970c47b5ac3d53ad0fa10ea7cb9bbb8be651852f4c2ee25b2d51379ee7
4
+ data.tar.gz: 4a196fb9aa2fc4eea20c60530f607c89313ba0e7b36baab2915dfa1be31ceda0
5
5
  SHA512:
6
- metadata.gz: 1be3b40e615409b191e1b758bdf1d0553a98807494ebbc658615d7b744352e512dc48648fad9b370efb557f2455ed08a30e2d4cf7e41c6de172bb96def467478
7
- data.tar.gz: dfa3aaa3815ebd24c37a235e75906bf8c1b16d710c5e0237f5dbf32dc792988e6c7652c45b42e5d3e28546c4bea4699ce14723d8c8ce646809a3ca57003ede0a
6
+ metadata.gz: c240f23324bd2e796025ce55b2c4d71b24c40591bee4ae0b9f769a54907b0933874f875b0c9f16630c5e1801a882fc54278041fc612655872ab36418ddc8f62e
7
+ data.tar.gz: 3c9a91daa012c834a2cdef8b4be88f97df70c48b6f4bfe6b545622b80f0ca4661563b91eeaac4e9288a06f9d3c2fd998ae2890f2d918504d7accca57f1aa8748
@@ -1,3 +1,4 @@
1
+
1
2
  @import 'pb_advanced_table/advanced_table';
2
3
  @import 'pb_avatar/avatar';
3
4
  @import 'pb_avatar_action_button/avatar_action_button';
@@ -108,6 +109,7 @@
108
109
  @import 'pb_user_badge/user_badge';
109
110
  @import 'pb_walkthrough/walkthrough';
110
111
  @import 'pb_weekday_stacked/weekday_stacked';
112
+ @import 'pb_icon_button/icon_button';
111
113
  @import 'utilities/mixins';
112
114
  @import 'utilities/spacing';
113
115
  @import 'utilities/cursor';
@@ -8,6 +8,7 @@ import { GlobalProps } from "../../utilities/globalProps"
8
8
  import Flex from "../../pb_flex/_flex"
9
9
  import FlexItem from "../../pb_flex/_flex_item"
10
10
  import Icon from "../../pb_icon/_icon"
11
+ import Checkbox from "../../pb_checkbox/_checkbox"
11
12
 
12
13
  import AdvancedTableContext from "../Context/AdvancedTableContext"
13
14
 
@@ -17,6 +18,7 @@ interface CustomCellProps {
17
18
  row: Row<GenericObject>
18
19
  value?: string
19
20
  customRenderer?: (row: Row<GenericObject>, value: string | undefined) => React.ReactNode
21
+ selectableRows?: boolean
20
22
  }
21
23
 
22
24
  export const CustomCell = ({
@@ -25,8 +27,9 @@ export const CustomCell = ({
25
27
  row,
26
28
  value,
27
29
  customRenderer,
30
+ selectableRows,
28
31
  }: CustomCellProps & GlobalProps) => {
29
- const { setExpanded, expanded, expandedControl, inlineRowLoading } = useContext(AdvancedTableContext);
32
+ const { setExpanded, expanded, expandedControl, inlineRowLoading, hasAnySubRows } = useContext(AdvancedTableContext);
30
33
 
31
34
  const handleOnExpand = (row: Row<GenericObject>) => {
32
35
  onRowToggleClick && onRowToggleClick(row);
@@ -41,10 +44,23 @@ export const CustomCell = ({
41
44
 
42
45
  return (
43
46
  <div style={{ paddingLeft: `${row.depth * 1.25}em` }}>
44
- <Flex alignItems="center"
47
+ <Flex
48
+ alignItems="center"
45
49
  columnGap="xs"
50
+ justify={!hasAnySubRows ? "end" : "start"}
46
51
  orientation="row"
47
52
  >
53
+ {
54
+ selectableRows && hasAnySubRows && (
55
+ <Checkbox
56
+ checked={row.getIsSelected()}
57
+ disabled={!row.getCanSelect()}
58
+ indeterminate={row.getIsSomeSelected()}
59
+ name={row.id}
60
+ onChange={row.getToggleSelectedHandler()}
61
+ />
62
+ )
63
+ }
48
64
  {renderButton ? (
49
65
  <button
50
66
  className="gray-icon expand-toggle-icon"
@@ -1,12 +1,13 @@
1
1
  import React, { useContext } from "react"
2
2
  import classnames from "classnames"
3
- import { flexRender, Header } from "@tanstack/react-table"
3
+ import { flexRender, Header, Table } from "@tanstack/react-table"
4
4
 
5
5
  import { GenericObject } from "../../types"
6
6
 
7
7
  import { GlobalProps } from "../../utilities/globalProps"
8
8
 
9
9
  import Flex from "../../pb_flex/_flex"
10
+ import Checkbox from "../../pb_checkbox/_checkbox"
10
11
 
11
12
  import { SortIconButton } from "./SortIconButton"
12
13
  import { ToggleIconButton } from "./ToggleIconButton"
@@ -24,6 +25,7 @@ type TableHeaderCellProps = {
24
25
  isPinnedLeft?: boolean
25
26
  loading?: boolean
26
27
  sortIcon?: string | string[]
28
+ table?: Table<GenericObject>
27
29
  } & GlobalProps
28
30
 
29
31
  export const TableHeaderCell = ({
@@ -35,9 +37,13 @@ export const TableHeaderCell = ({
35
37
  isPinnedLeft = false,
36
38
  loading,
37
39
  sortIcon,
40
+ table
38
41
  }: TableHeaderCellProps) => {
39
- const { sortControl, responsive } = useContext(AdvancedTableContext)
42
+ const { sortControl, responsive, selectableRows, hasAnySubRows, showActionsBar } =
43
+ useContext(AdvancedTableContext);
40
44
 
45
+ type justifyTypes = "none" | "center" | "start" | "end" | "between" | "around" | "evenly"
46
+
41
47
  const toggleSortButton = (event: React.SyntheticEvent) => {
42
48
  if (sortControl) {
43
49
  const sortIsDesc = header?.column.getIsSorted() === "desc"
@@ -59,6 +65,7 @@ export const TableHeaderCell = ({
59
65
 
60
66
  const cellClassName = classnames(
61
67
  "table-header-cells",
68
+ `${showActionsBar && "header-cells-with-actions"}`,
62
69
  `${isChrome() ? "chrome-styles" : ""}`,
63
70
  `${enableSorting ? "table-header-cells-active" : ""}`,
64
71
  { "pinned-left": responsive === "scroll" && isPinnedLeft },
@@ -82,8 +89,14 @@ const isToggleExpansionEnabled =
82
89
  (enableToggleExpansion === "all" || "header") &&
83
90
  enableToggleExpansion !== "none"
84
91
 
85
- const justifyHeader = isLeafColumn ? "end" : "center"
92
+ let justifyHeader:justifyTypes;
86
93
 
94
+ if (header?.index === 0 && hasAnySubRows) {
95
+ justifyHeader = enableSorting ? "between" : "start";
96
+ } else {
97
+ justifyHeader = isLeafColumn ? "end" : "center";
98
+ }
99
+
87
100
  return (
88
101
  <th
89
102
  align="right"
@@ -102,9 +115,18 @@ const justifyHeader = isLeafColumn ? "end" : "center"
102
115
  ) : (
103
116
  <Flex
104
117
  alignItems="center"
105
- justify={header?.index === 0 && enableSorting ? "between" : header?.index === 0 && !enableSorting ? "start" : justifyHeader}
118
+ justify={justifyHeader}
106
119
  >
107
- {isToggleExpansionEnabled && (
120
+ {
121
+ selectableRows && header?.index === 0 && hasAnySubRows && (
122
+ <Checkbox
123
+ checked={table?.getIsAllRowsSelected()}
124
+ indeterminate={table?.getIsSomeRowsSelected()}
125
+ onChange={table?.getToggleAllRowsSelectedHandler()}
126
+ />
127
+ )
128
+ }
129
+ {isToggleExpansionEnabled && hasAnySubRows && (
108
130
  <ToggleIconButton onClick={handleExpandOrCollapse} />
109
131
  )}
110
132
 
@@ -9,6 +9,7 @@ import { globalProps } from "../../utilities/globalProps"
9
9
  import { isChrome } from "../Utilities/BrowserCheck"
10
10
 
11
11
  import LoadingInline from "../../pb_loading_inline/_loading_inline"
12
+ import Checkbox from "../../pb_checkbox/_checkbox"
12
13
 
13
14
  import { SubRowHeaderRow } from "../Components/SubRowHeaderRow"
14
15
  import { LoadingCell } from "../Components/LoadingCell"
@@ -42,6 +43,8 @@ export const TableBody = ({
42
43
  loading,
43
44
  responsive,
44
45
  table,
46
+ selectableRows,
47
+ hasAnySubRows
45
48
  } = useContext(AdvancedTableContext)
46
49
 
47
50
  const classes = classnames(
@@ -65,7 +68,7 @@ export const TableBody = ({
65
68
  const numberOfColumns = table.getAllFlatColumns().length
66
69
  const isDataLoading = isExpandable && (inlineRowLoading && rowHasNoChildren) && (row.depth < columnDefinitions[0].cellAccessors?.length)
67
70
  const rowBackground = isExpandable && ((!inlineRowLoading && row.getCanExpand()) || (inlineRowLoading && rowHasNoChildren))
68
-
71
+ const rowColor = row.getIsSelected() ? "bg-row-selection" : rowBackground ? "bg-silver" : "bg-white"
69
72
  return (
70
73
  <React.Fragment key={`${row.index}-${row.id}-${row.depth}-row`}>
71
74
  {isFirstChildofSubrow && subRowHeaders && (
@@ -79,11 +82,23 @@ export const TableBody = ({
79
82
  />
80
83
  )}
81
84
  <tr
82
- className={`${rowBackground ? "bg-silver" : "bg-white"} ${
85
+ className={`${rowColor} ${
83
86
  row.depth > 0 ? `depth-sub-row-${row.depth}` : ""
84
87
  }`}
85
88
  id={`${row.index}-${row.id}-${row.depth}-row`}
86
89
  >
90
+ {/* Render custom checkbox column when we want selectableRows for non-expanding tables */}
91
+ {selectableRows && !hasAnySubRows && (
92
+ <td className="checkbox-cell">
93
+ <Checkbox
94
+ checked={row.getIsSelected()}
95
+ disabled={!row.getCanSelect()}
96
+ indeterminate={row.getIsSomeSelected()}
97
+ name={row.id}
98
+ onChange={row.getToggleSelectedHandler()}
99
+ />
100
+ </td>
101
+ )}
87
102
  {row.getVisibleCells().map((cell, i) => {
88
103
  const isPinnedLeft = columnPinning.left.includes(cell.column.id)
89
104
  const isLastCell = cell.column.parent?.columns.at(-1)?.id === cell.column.id
@@ -7,8 +7,10 @@ import { GenericObject } from "../../types"
7
7
  import { buildCss } from "../../utilities/props"
8
8
  import { globalProps } from "../../utilities/globalProps"
9
9
 
10
- import { TableHeaderCell } from "../Components/TableHeaderCell"
10
+ import Checkbox from "../../pb_checkbox/_checkbox"
11
11
 
12
+ import { TableHeaderCell } from "../Components/TableHeaderCell"
13
+ import { isChrome } from "../Utilities/BrowserCheck"
12
14
  import AdvancedTableContext from "../Context/AdvancedTableContext"
13
15
 
14
16
  type TableHeaderProps = {
@@ -34,6 +36,10 @@ export const TableHeader = ({
34
36
  handleExpandOrCollapse,
35
37
  loading,
36
38
  table,
39
+ hasAnySubRows,
40
+ showActionsBar,
41
+ selectableRows,
42
+ responsive
37
43
  } = useContext(AdvancedTableContext)
38
44
 
39
45
  const classes = classnames(
@@ -44,6 +50,12 @@ export const TableHeader = ({
44
50
 
45
51
  const columnPinning = table.getState().columnPinning;
46
52
 
53
+ const customCellClassnames = classnames(
54
+ "table-header-cells-custom",
55
+ `${showActionsBar && "header-cells-with-actions"}`,
56
+ `${isChrome() ? "chrome-styles" : ""}`,
57
+ `${responsive === "scroll" && "pinned-left"}`,
58
+ );
47
59
  return (
48
60
  <>
49
61
  <thead className={classes}
@@ -52,6 +64,15 @@ export const TableHeader = ({
52
64
  {/* Get the header groups (only one in this example) */}
53
65
  {table.getHeaderGroups().map((headerGroup: HeaderGroup<GenericObject>) => (
54
66
  <tr key={`${headerGroup.id}-headerGroup`}>
67
+ {!hasAnySubRows && selectableRows && (
68
+ <th className={customCellClassnames}>
69
+ <Checkbox
70
+ checked={table?.getIsAllRowsSelected()}
71
+ indeterminate={table?.getIsSomeRowsSelected()}
72
+ onChange={table?.getToggleAllRowsSelectedHandler()}
73
+ />
74
+ </th>
75
+ )}
55
76
  {headerGroup.headers.map(header => {
56
77
  const isPinnedLeft = columnPinning.left.includes(header.id)
57
78
  return (
@@ -65,6 +86,7 @@ export const TableHeader = ({
65
86
  key={`${header.id}-header`}
66
87
  loading={loading}
67
88
  sortIcon={sortIcon}
89
+ table={table}
68
90
  />
69
91
  )
70
92
  })}
@@ -23,10 +23,20 @@
23
23
  background-color: $white;
24
24
  }
25
25
 
26
+ .bg-row-selection {
27
+ background-color: $info_subtle;
28
+ }
29
+
26
30
  .full-width {
27
31
  width: 100%;
28
32
  }
29
33
 
34
+ .row-selection-actions-card {
35
+ border-bottom-right-radius: 0px !important;
36
+ border-bottom-left-radius: 0px !important;
37
+ border-bottom-color: transparent;
38
+ }
39
+
30
40
  .table-header-cells:first-child {
31
41
  min-width: 180px;
32
42
  }
@@ -47,6 +57,16 @@
47
57
  th[colspan]:not([colspan="1"]) {
48
58
  border-right: 1px solid $border_light !important;
49
59
  }
60
+ .table-header-cells-custom {
61
+ text-align:center;
62
+ [class^=pb_checkbox_kit] .pb_checkbox_label {
63
+ padding-left: 0px;
64
+ }
65
+ }
66
+ .header-cells-with-actions {
67
+ border-top-left-radius: 0px !important;
68
+ border-top-right-radius: 0px !important;
69
+ }
50
70
  }
51
71
 
52
72
  .pb_advanced_table_body {
@@ -59,6 +79,14 @@
59
79
  tr .pb_table_td:last-child {
60
80
  padding-right: 8px !important;
61
81
  }
82
+
83
+ .checkbox-cell {
84
+ display: flex;
85
+ justify-content: center;
86
+ [class^=pb_checkbox_kit] .pb_checkbox_label {
87
+ padding-left: 0px;
88
+ }
89
+ }
62
90
  }
63
91
 
64
92
 
@@ -116,6 +144,7 @@
116
144
 
117
145
  // Vertical separator
118
146
  .table-header-cells:first-child,
147
+ .table-header-cells-custom:first-child,
119
148
  td:first-child,
120
149
  .pb_table_td:first-child {
121
150
  box-shadow: 1px 0px 0px 0px $border_light !important;
@@ -12,12 +12,17 @@ import {
12
12
  Row,
13
13
  useReactTable,
14
14
  Getter,
15
+ RowSelectionState
15
16
  } from "@tanstack/react-table"
16
17
 
17
18
  import { buildAriaProps, buildCss, buildDataProps, buildHtmlProps } from "../utilities/props"
18
19
  import { globalProps, GlobalProps } from "../utilities/globalProps"
19
20
 
20
21
  import Table from "../pb_table/_table"
22
+ import Card from "../pb_card/_card"
23
+ import Caption from "../pb_caption/_caption"
24
+ import Flex from "../pb_flex/_flex"
25
+ import FlexItem from "../pb_flex/_flex_item"
21
26
 
22
27
  import AdvancedTableContext from "./Context/AdvancedTableContext"
23
28
 
@@ -30,6 +35,7 @@ import Pagination from "../pb_pagination/_pagination"
30
35
 
31
36
  type AdvancedTableProps = {
32
37
  aria?: { [key: string]: string }
38
+ actions?: React.ReactNode[] | React.ReactNode
33
39
  children?: React.ReactNode | React.ReactNode[]
34
40
  className?: string
35
41
  columnDefinitions: GenericObject[]
@@ -47,16 +53,20 @@ type AdvancedTableProps = {
47
53
  pagination?: boolean,
48
54
  paginationProps?: GenericObject
49
55
  responsive?: "scroll" | "none",
56
+ selectableRows?: boolean,
57
+ showActionsBar?: boolean,
50
58
  sortControl?: GenericObject
51
59
  tableData: GenericObject[]
52
60
  tableOptions?: GenericObject
53
61
  tableProps?: GenericObject
54
62
  toggleExpansionIcon?: string | string[]
63
+ onRowSelectionChange?: (arg: RowSelectionState) => void
55
64
  } & GlobalProps
56
65
 
57
66
  const AdvancedTable = (props: AdvancedTableProps) => {
58
67
  const {
59
68
  aria = {},
69
+ actions,
60
70
  children,
61
71
  className,
62
72
  columnDefinitions,
@@ -74,11 +84,14 @@ const AdvancedTable = (props: AdvancedTableProps) => {
74
84
  pagination = false,
75
85
  paginationProps,
76
86
  responsive = "scroll",
87
+ showActionsBar = true,
88
+ selectableRows,
77
89
  sortControl,
78
90
  tableData,
79
91
  tableOptions,
80
92
  tableProps,
81
93
  toggleExpansionIcon = "arrows-from-line",
94
+ onRowSelectionChange,
82
95
  } = props
83
96
 
84
97
  const [loadingStateRowCount, setLoadingStateRowCount] = useState(
@@ -96,6 +109,9 @@ const AdvancedTable = (props: AdvancedTableProps) => {
96
109
 
97
110
  const columnHelper = createColumnHelper()
98
111
 
112
+ //Row Selection
113
+ const [rowSelection, setRowSelection] = useState<RowSelectionState>({})
114
+
99
115
  //Create cells for columns, with customization for first column
100
116
  const createCellFunction = (cellAccessors: string[], customRenderer?: (row: Row<GenericObject>, value: any) => JSX.Element, index?: number) => {
101
117
  const columnCells = ({
@@ -116,6 +132,7 @@ const AdvancedTable = (props: AdvancedTableProps) => {
116
132
  getValue={getValue}
117
133
  onRowToggleClick={onRowToggleClick}
118
134
  row={row}
135
+ selectableRows={selectableRows}
119
136
  />
120
137
  )
121
138
  }
@@ -128,6 +145,7 @@ const AdvancedTable = (props: AdvancedTableProps) => {
128
145
  customRenderer={customRenderer}
129
146
  onRowToggleClick={onRowToggleClick}
130
147
  row={row}
148
+ selectableRows={selectableRows}
131
149
  value={accessorValue}
132
150
  />
133
151
  ) : (
@@ -189,9 +207,13 @@ const AdvancedTable = (props: AdvancedTableProps) => {
189
207
  },
190
208
  ]
191
209
 
192
- const expandAndSortState = () => {
193
- if (sortControl) {
210
+ const customState = () => {
211
+ if (sortControl && selectableRows) {
212
+ return { state: { expanded, sorting, rowSelection } }
213
+ } else if (sortControl) {
194
214
  return { state: { expanded, sorting } }
215
+ } else if (selectableRows) {
216
+ return { state: { expanded, rowSelection } }
195
217
  } else {
196
218
  return { state: { expanded } }
197
219
  }
@@ -219,13 +241,24 @@ const AdvancedTable = (props: AdvancedTableProps) => {
219
241
  getSortedRowModel: getSortedRowModel(),
220
242
  enableSortingRemoval: false,
221
243
  sortDescFirst: true,
222
- ...expandAndSortState(),
223
- ... paginationInitializer,
244
+ onRowSelectionChange: setRowSelection,
245
+ getRowId: selectableRows ? row => row.id : undefined,
246
+ ...customState(),
247
+ ...paginationInitializer,
224
248
  ...tableOptions,
225
249
  })
226
250
 
227
251
  const tableRows = table.getRowModel()
228
252
 
253
+ const hasAnySubRows = tableRows.rows.some(row => row.subRows && row.subRows.length > 0);
254
+ const selectedRowsLength = Object.keys(table.getState().rowSelection).length
255
+
256
+ useEffect(() => {
257
+ if (onRowSelectionChange) {
258
+ onRowSelectionChange(table.getState().rowSelection)
259
+ }
260
+ } , [table.getState().rowSelection, onRowSelectionChange])
261
+
229
262
  // Set table row count for loading state
230
263
  const updateLoadingStateRowCount = useCallback(() => {
231
264
  const rowsCount = table.getRowModel().rows.length
@@ -284,6 +317,9 @@ const AdvancedTable = (props: AdvancedTableProps) => {
284
317
  sortControl,
285
318
  table,
286
319
  toggleExpansionIcon,
320
+ showActionsBar,
321
+ selectableRows,
322
+ hasAnySubRows
287
323
  }}
288
324
  >
289
325
  <>
@@ -297,6 +333,27 @@ const AdvancedTable = (props: AdvancedTableProps) => {
297
333
  total={table.getPageCount()}
298
334
  />
299
335
  }
336
+ {
337
+ selectableRows && showActionsBar && (
338
+ <Card className="row-selection-actions-card"
339
+ padding="xs"
340
+ >
341
+ <Flex alignItems="center"
342
+ justify="between"
343
+ >
344
+ <Caption color="light"
345
+ paddingLeft="xs"
346
+ size="xs"
347
+ >
348
+ {selectedRowsLength} Selected
349
+ </Caption>
350
+ <FlexItem>
351
+ {actions}
352
+ </FlexItem>
353
+ </Flex>
354
+ </Card>
355
+ )
356
+ }
300
357
  <Table
301
358
  className={`${loading ? "content-loading" : ""}`}
302
359
  dark={dark}
@@ -0,0 +1,50 @@
1
+ import React from "react"
2
+ import { AdvancedTable } from "playbook-ui"
3
+ import MOCK_DATA from "./advanced_table_mock_data_no_subrows.json"
4
+
5
+ const AdvancedTableNoSubrows = (props) => {
6
+ const columnDefinitions = [
7
+ {
8
+ accessor: "year",
9
+ label: "Year",
10
+ cellAccessors: ["quarter", "month", "day"],
11
+ },
12
+ {
13
+ accessor: "newEnrollments",
14
+ label: "New Enrollments",
15
+ },
16
+ {
17
+ accessor: "scheduledMeetings",
18
+ label: "Scheduled Meetings",
19
+ },
20
+ {
21
+ accessor: "attendanceRate",
22
+ label: "Attendance Rate",
23
+ },
24
+ {
25
+ accessor: "completedClasses",
26
+ label: "Completed Classes",
27
+ },
28
+ {
29
+ accessor: "classCompletionRate",
30
+ label: "Class Completion Rate",
31
+ },
32
+ {
33
+ accessor: "graduatedStudents",
34
+ label: "Graduated Students",
35
+ },
36
+ ]
37
+
38
+ return (
39
+ <div>
40
+ <AdvancedTable
41
+ columnDefinitions={columnDefinitions}
42
+ enableToggleExpansion="all"
43
+ tableData={MOCK_DATA}
44
+ {...props}
45
+ />
46
+ </div>
47
+ )
48
+ }
49
+
50
+ export default AdvancedTableNoSubrows
@@ -40,6 +40,7 @@ const AdvancedTablePagination = (props) => {
40
40
  <AdvancedTable
41
41
  columnDefinitions={columnDefinitions}
42
42
  pagination
43
+ responsive="none"
43
44
  tableData={PAGINATION_MOCK_DATA}
44
45
  {...props}
45
46
  />
@@ -47,6 +47,7 @@ const AdvancedTablePaginationWithProps = (props) => {
47
47
  columnDefinitions={columnDefinitions}
48
48
  pagination
49
49
  paginationProps={paginationProps}
50
+ responsive="none"
50
51
  tableData={PAGINATION_MOCK_DATA}
51
52
  {...props}
52
53
  />
@@ -0,0 +1,60 @@
1
+ import React from "react"
2
+ import { AdvancedTable } from "playbook-ui"
3
+ import MOCK_DATA from "./advanced_table_mock_data_with_id.json"
4
+
5
+ const AdvancedTableSelectableRows = (props) => {
6
+ const columnDefinitions = [
7
+ {
8
+ accessor: "year",
9
+ label: "Year",
10
+ cellAccessors: ["quarter", "month", "day"],
11
+ },
12
+ {
13
+ accessor: "newEnrollments",
14
+ label: "New Enrollments",
15
+ },
16
+ {
17
+ accessor: "scheduledMeetings",
18
+ label: "Scheduled Meetings",
19
+ },
20
+ {
21
+ accessor: "attendanceRate",
22
+ label: "Attendance Rate",
23
+ },
24
+ {
25
+ accessor: "completedClasses",
26
+ label: "Completed Classes",
27
+ },
28
+ {
29
+ accessor: "classCompletionRate",
30
+ label: "Class Completion Rate",
31
+ },
32
+ {
33
+ accessor: "graduatedStudents",
34
+ label: "Graduated Students",
35
+ },
36
+ ]
37
+
38
+ //Render the subRow header rows
39
+ const subRowHeaders = ["Quarter", "Month", "Day"]
40
+
41
+
42
+ return (
43
+ <div>
44
+ <AdvancedTable
45
+ columnDefinitions={columnDefinitions}
46
+ enableToggleExpansion="all"
47
+ onRowSelectionChange={(selectedRows) => console.log(selectedRows)}
48
+ selectableRows
49
+ tableData={MOCK_DATA}
50
+
51
+ {...props}
52
+ >
53
+ <AdvancedTable.Header />
54
+ <AdvancedTable.Body subRowHeaders={subRowHeaders}/>
55
+ </AdvancedTable>
56
+ </div>
57
+ )
58
+ }
59
+
60
+ export default AdvancedTableSelectableRows
@@ -0,0 +1,5 @@
1
+ `selectableRows` is a boolean prop that if present will add checkboxes to all rows that will allow for selecting rows.
2
+
3
+ When a parent row is clicked, it will check all nested children rows, Children rows can be manually checked or unchecked as well.
4
+
5
+ The `onRowSelectionChange` prop returns an array of ids of all Rows that have been selected. Open the console on this example and check and uncheck checkboxes to see this is action! __NOTE__: Each object within the `tableData`Array must contain a unique id in order to attach an id to all Rows for this to function.