@bundle-stats/ui 4.13.0-beta.8 → 4.13.0-rc.0

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.
Files changed (227) hide show
  1. package/lib/app/app.js +4 -8
  2. package/lib/app/app.js.map +1 -1
  3. package/lib/app/app.module.css +2 -2
  4. package/lib/assets/icons.svg +70 -67
  5. package/lib/assets/icons.svg.js +14 -12
  6. package/lib/assets/icons.svg.js.map +1 -1
  7. package/lib/components/bundle-assets/bundle-assets.js +44 -10
  8. package/lib/components/bundle-assets/bundle-assets.js.map +1 -1
  9. package/lib/components/bundle-assets/bundle-assets.module.css +0 -5
  10. package/lib/components/bundle-assets-totals/bundle-assets-totals.js +14 -12
  11. package/lib/components/bundle-assets-totals/bundle-assets-totals.js.map +1 -1
  12. package/lib/components/bundle-modules/bundle-modules.i18n.js +1 -1
  13. package/lib/components/bundle-modules/bundle-modules.js +39 -15
  14. package/lib/components/bundle-modules/bundle-modules.js.map +1 -1
  15. package/lib/components/bundle-modules/bundle-modules.module.css +0 -5
  16. package/lib/components/bundle-packages/bundle-packages.js +43 -9
  17. package/lib/components/bundle-packages/bundle-packages.js.map +1 -1
  18. package/lib/components/bundle-packages/bundle-packages.module.css +0 -5
  19. package/lib/components/delta/delta.js +1 -1
  20. package/lib/components/delta/delta.js.map +1 -1
  21. package/lib/components/delta/delta.module.css +10 -1
  22. package/lib/components/jobs-header/jobs-header.module.css +0 -4
  23. package/lib/components/metrics-display-selector/metrics-display-selector.js +42 -5
  24. package/lib/components/metrics-display-selector/metrics-display-selector.js.map +1 -1
  25. package/lib/components/metrics-display-selector/metrics-display-selector.module.css +15 -7
  26. package/lib/components/metrics-table-header/metrics-table-header.js +7 -7
  27. package/lib/components/metrics-table-header/metrics-table-header.js.map +1 -1
  28. package/lib/components/metrics-table-header/metrics-table-header.module.css +11 -4
  29. package/lib/components/metrics-table-options/metrics-table-options.js +2 -2
  30. package/lib/components/metrics-table-options/metrics-table-options.js.map +1 -1
  31. package/lib/components/metrics-table-title/metrics-table-title.js +1 -1
  32. package/lib/components/metrics-table-title/metrics-table-title.js.map +1 -1
  33. package/lib/components/metrics-table-title/metrics-table-title.module.css +1 -0
  34. package/lib/components/metrics-treemap/index.js +4 -0
  35. package/lib/components/metrics-treemap/index.js.map +1 -1
  36. package/lib/components/metrics-treemap/metrics-treemap.constants.js +3 -0
  37. package/lib/components/metrics-treemap/metrics-treemap.constants.js.map +1 -0
  38. package/lib/components/metrics-treemap/metrics-treemap.i18n.js +6 -0
  39. package/lib/components/metrics-treemap/metrics-treemap.i18n.js.map +1 -0
  40. package/lib/components/metrics-treemap/metrics-treemap.js +100 -62
  41. package/lib/components/metrics-treemap/metrics-treemap.js.map +1 -1
  42. package/lib/components/metrics-treemap/metrics-treemap.module.css +139 -51
  43. package/lib/components/metrics-treemap/metrics-treemap.utils.js +109 -0
  44. package/lib/components/metrics-treemap/metrics-treemap.utils.js.map +1 -0
  45. package/lib/components/module-info/module-info.js +1 -2
  46. package/lib/components/module-info/module-info.js.map +1 -1
  47. package/lib/components/run-info/run-info.module.css +7 -7
  48. package/lib/css/variables.css +14 -13
  49. package/lib/hooks/metrics-display-type.js +45 -24
  50. package/lib/hooks/metrics-display-type.js.map +1 -1
  51. package/lib/hooks/search-params.js +1 -0
  52. package/lib/hooks/search-params.js.map +1 -1
  53. package/lib/layout/box/box.module.css +4 -2
  54. package/lib/layout/flex-stack/flex-stack.js +3 -4
  55. package/lib/layout/flex-stack/flex-stack.js.map +1 -1
  56. package/lib/layout/flex-stack/flex-stack.module.css +19 -23
  57. package/lib/ui/button/button.js +5 -4
  58. package/lib/ui/button/button.js.map +1 -1
  59. package/lib/ui/button/button.module.css +55 -53
  60. package/lib/ui/dropdown/dropdown.js +10 -40
  61. package/lib/ui/dropdown/dropdown.js.map +1 -1
  62. package/lib/ui/dropdown/index.js.map +1 -1
  63. package/lib/ui/filters/filters.js +33 -35
  64. package/lib/ui/filters/filters.js.map +1 -1
  65. package/lib/ui/filters/filters.module.css +55 -67
  66. package/lib/ui/hover-card/hover-card.js +1 -1
  67. package/lib/ui/hover-card/hover-card.js.map +1 -1
  68. package/lib/ui/icon/icon.js +2 -1
  69. package/lib/ui/icon/icon.js.map +1 -1
  70. package/lib/ui/input-search/input-search.js +1 -1
  71. package/lib/ui/input-search/input-search.js.map +1 -1
  72. package/lib/ui/loader/loader.js +1 -1
  73. package/lib/ui/loader/loader.js.map +1 -1
  74. package/lib/ui/table/table.module.css +30 -0
  75. package/lib/ui/tag/tag.module.css +3 -3
  76. package/lib/ui/toolbar/toolbar.module.css +1 -3
  77. package/lib-esm/app/app.js +4 -8
  78. package/lib-esm/app/app.js.map +1 -1
  79. package/lib-esm/app/app.module.css +2 -2
  80. package/lib-esm/assets/icons.svg +70 -67
  81. package/lib-esm/assets/icons.svg.js +14 -12
  82. package/lib-esm/assets/icons.svg.js.map +1 -1
  83. package/lib-esm/components/bundle-assets/bundle-assets.js +45 -11
  84. package/lib-esm/components/bundle-assets/bundle-assets.js.map +1 -1
  85. package/lib-esm/components/bundle-assets/bundle-assets.module.css +0 -5
  86. package/lib-esm/components/bundle-assets-totals/bundle-assets-totals.js +15 -13
  87. package/lib-esm/components/bundle-assets-totals/bundle-assets-totals.js.map +1 -1
  88. package/lib-esm/components/bundle-modules/bundle-modules.i18n.js +1 -1
  89. package/lib-esm/components/bundle-modules/bundle-modules.js +40 -16
  90. package/lib-esm/components/bundle-modules/bundle-modules.js.map +1 -1
  91. package/lib-esm/components/bundle-modules/bundle-modules.module.css +0 -5
  92. package/lib-esm/components/bundle-packages/bundle-packages.js +44 -10
  93. package/lib-esm/components/bundle-packages/bundle-packages.js.map +1 -1
  94. package/lib-esm/components/bundle-packages/bundle-packages.module.css +0 -5
  95. package/lib-esm/components/delta/delta.js +1 -1
  96. package/lib-esm/components/delta/delta.js.map +1 -1
  97. package/lib-esm/components/delta/delta.module.css +10 -1
  98. package/lib-esm/components/jobs-header/jobs-header.module.css +0 -4
  99. package/lib-esm/components/metrics-display-selector/metrics-display-selector.js +42 -5
  100. package/lib-esm/components/metrics-display-selector/metrics-display-selector.js.map +1 -1
  101. package/lib-esm/components/metrics-display-selector/metrics-display-selector.module.css +15 -7
  102. package/lib-esm/components/metrics-table-header/metrics-table-header.js +7 -7
  103. package/lib-esm/components/metrics-table-header/metrics-table-header.js.map +1 -1
  104. package/lib-esm/components/metrics-table-header/metrics-table-header.module.css +11 -4
  105. package/lib-esm/components/metrics-table-options/metrics-table-options.js +3 -3
  106. package/lib-esm/components/metrics-table-options/metrics-table-options.js.map +1 -1
  107. package/lib-esm/components/metrics-table-title/metrics-table-title.js +1 -1
  108. package/lib-esm/components/metrics-table-title/metrics-table-title.js.map +1 -1
  109. package/lib-esm/components/metrics-table-title/metrics-table-title.module.css +1 -0
  110. package/lib-esm/components/metrics-treemap/index.js +1 -0
  111. package/lib-esm/components/metrics-treemap/index.js.map +1 -1
  112. package/lib-esm/components/metrics-treemap/metrics-treemap.constants.js +2 -0
  113. package/lib-esm/components/metrics-treemap/metrics-treemap.constants.js.map +1 -0
  114. package/lib-esm/components/metrics-treemap/metrics-treemap.i18n.js +3 -0
  115. package/lib-esm/components/metrics-treemap/metrics-treemap.i18n.js.map +1 -0
  116. package/lib-esm/components/metrics-treemap/metrics-treemap.js +102 -63
  117. package/lib-esm/components/metrics-treemap/metrics-treemap.js.map +1 -1
  118. package/lib-esm/components/metrics-treemap/metrics-treemap.module.css +139 -51
  119. package/lib-esm/components/metrics-treemap/metrics-treemap.utils.js +105 -0
  120. package/lib-esm/components/metrics-treemap/metrics-treemap.utils.js.map +1 -0
  121. package/lib-esm/components/module-info/module-info.js +1 -2
  122. package/lib-esm/components/module-info/module-info.js.map +1 -1
  123. package/lib-esm/components/run-info/run-info.module.css +7 -7
  124. package/lib-esm/css/variables.css +14 -13
  125. package/lib-esm/hooks/metrics-display-type.js +46 -24
  126. package/lib-esm/hooks/metrics-display-type.js.map +1 -1
  127. package/lib-esm/hooks/search-params.js +1 -0
  128. package/lib-esm/hooks/search-params.js.map +1 -1
  129. package/lib-esm/layout/box/box.module.css +4 -2
  130. package/lib-esm/layout/flex-stack/flex-stack.js +3 -4
  131. package/lib-esm/layout/flex-stack/flex-stack.js.map +1 -1
  132. package/lib-esm/layout/flex-stack/flex-stack.module.css +19 -23
  133. package/lib-esm/ui/button/button.js +5 -4
  134. package/lib-esm/ui/button/button.js.map +1 -1
  135. package/lib-esm/ui/button/button.module.css +55 -53
  136. package/lib-esm/ui/dropdown/dropdown.js +8 -39
  137. package/lib-esm/ui/dropdown/dropdown.js.map +1 -1
  138. package/lib-esm/ui/dropdown/index.js.map +1 -1
  139. package/lib-esm/ui/filters/filters.js +34 -36
  140. package/lib-esm/ui/filters/filters.js.map +1 -1
  141. package/lib-esm/ui/filters/filters.module.css +55 -67
  142. package/lib-esm/ui/hover-card/hover-card.js +1 -1
  143. package/lib-esm/ui/hover-card/hover-card.js.map +1 -1
  144. package/lib-esm/ui/icon/icon.js +2 -1
  145. package/lib-esm/ui/icon/icon.js.map +1 -1
  146. package/lib-esm/ui/input-search/input-search.js +1 -1
  147. package/lib-esm/ui/input-search/input-search.js.map +1 -1
  148. package/lib-esm/ui/loader/loader.js +1 -1
  149. package/lib-esm/ui/loader/loader.js.map +1 -1
  150. package/lib-esm/ui/table/table.module.css +30 -0
  151. package/lib-esm/ui/tag/tag.module.css +3 -3
  152. package/lib-esm/ui/toolbar/toolbar.module.css +1 -3
  153. package/package.json +9 -9
  154. package/src/app/app.jsx +4 -12
  155. package/src/app/app.module.css +2 -2
  156. package/src/assets/icons/check.svg +4 -0
  157. package/src/assets/icons.svg +70 -67
  158. package/src/assets/icons.svg.jsx +12 -12
  159. package/src/components/bundle-assets/bundle-assets.jsx +82 -25
  160. package/src/components/bundle-assets/bundle-assets.module.css +0 -5
  161. package/src/components/bundle-assets-totals/bundle-assets-totals.jsx +53 -46
  162. package/src/components/bundle-modules/bundle-modules.i18n.ts +1 -1
  163. package/src/components/bundle-modules/bundle-modules.module.css +0 -5
  164. package/src/components/bundle-modules/bundle-modules.tsx +117 -53
  165. package/src/components/bundle-packages/bundle-packages.jsx +77 -20
  166. package/src/components/bundle-packages/bundle-packages.module.css +0 -5
  167. package/src/components/delta/delta.jsx +1 -1
  168. package/src/components/delta/delta.module.css +10 -1
  169. package/src/components/jobs-header/jobs-header.module.css +0 -4
  170. package/src/components/metrics-display-selector/metrics-display-selector.module.css +15 -7
  171. package/src/components/metrics-display-selector/metrics-display-selector.stories.tsx +33 -0
  172. package/src/components/metrics-display-selector/metrics-display-selector.tsx +86 -28
  173. package/src/components/metrics-table-header/metrics-table-header.module.css +11 -4
  174. package/src/components/metrics-table-header/metrics-table-header.tsx +7 -7
  175. package/src/components/metrics-table-options/metrics-table-options.jsx +4 -10
  176. package/src/components/metrics-table-title/metrics-table-title.jsx +1 -1
  177. package/src/components/metrics-table-title/metrics-table-title.module.css +1 -0
  178. package/src/components/metrics-treemap/__tests__/metrics-treemap.utils.ts +188 -0
  179. package/src/components/metrics-treemap/index.ts +1 -0
  180. package/src/components/metrics-treemap/metrics-treemap.constants.ts +52 -0
  181. package/src/components/metrics-treemap/metrics-treemap.i18n.ts +2 -0
  182. package/src/components/metrics-treemap/metrics-treemap.module.css +139 -51
  183. package/src/components/metrics-treemap/metrics-treemap.stories.tsx +44 -10
  184. package/src/components/metrics-treemap/metrics-treemap.tsx +329 -120
  185. package/src/components/metrics-treemap/metrics-treemap.utils.ts +162 -0
  186. package/src/components/module-info/module-info.tsx +1 -1
  187. package/src/components/run-info/run-info.module.css +7 -7
  188. package/src/css/variables.css +14 -13
  189. package/src/hooks/metrics-display-type.ts +79 -29
  190. package/src/hooks/search-params.js +1 -0
  191. package/src/layout/box/box.module.css +4 -2
  192. package/src/layout/flex-stack/flex-stack.module.css +19 -23
  193. package/src/layout/flex-stack/flex-stack.tsx +2 -8
  194. package/src/ui/button/button.module.css +55 -53
  195. package/src/ui/button/button.stories.tsx +16 -9
  196. package/src/ui/button/button.tsx +8 -7
  197. package/src/ui/dropdown/dropdown.stories.tsx +25 -0
  198. package/src/ui/dropdown/dropdown.tsx +66 -0
  199. package/src/ui/filters/filters.module.css +55 -67
  200. package/src/ui/filters/filters.stories.tsx +109 -0
  201. package/src/ui/filters/filters.tsx +128 -167
  202. package/src/ui/hover-card/hover-card.tsx +1 -1
  203. package/src/ui/icon/icon.tsx +2 -1
  204. package/src/ui/input-search/input-search.tsx +1 -0
  205. package/src/ui/loader/loader.jsx +1 -1
  206. package/src/ui/table/table.module.css +30 -0
  207. package/src/ui/tag/tag.module.css +3 -3
  208. package/src/ui/toolbar/toolbar.module.css +1 -3
  209. package/types/components/bundle-modules/bundle-modules.i18n.d.ts +1 -1
  210. package/types/components/delta/delta.d.ts +2 -2
  211. package/types/components/metrics-display-selector/metrics-display-selector.d.ts +5 -3
  212. package/types/components/metrics-treemap/index.d.ts +1 -0
  213. package/types/components/metrics-treemap/metrics-treemap.constants.d.ts +20 -0
  214. package/types/components/metrics-treemap/metrics-treemap.d.ts +7 -5
  215. package/types/components/metrics-treemap/metrics-treemap.i18n.d.ts +2 -0
  216. package/types/components/metrics-treemap/metrics-treemap.utils.d.ts +5 -0
  217. package/types/hooks/metrics-display-type.d.ts +8 -2
  218. package/types/ui/dropdown/dropdown.d.ts +12 -47
  219. package/types/ui/dropdown/index.d.ts +1 -1
  220. package/types/ui/filters/filters.d.ts +2 -7
  221. package/types/ui/icon/icon.d.ts +4 -2
  222. package/types/ui/loader/loader.d.ts +2 -2
  223. package/lib/components/bundle-assets-totals/bundle-assets-totals.module.css +0 -7
  224. package/lib-esm/components/bundle-assets-totals/bundle-assets-totals.module.css +0 -7
  225. package/src/components/bundle-assets-totals/bundle-assets-totals.module.css +0 -7
  226. package/src/ui/dropdown/dropdown.jsx +0 -88
  227. /package/src/ui/dropdown/{index.js → index.ts} +0 -0
@@ -5,90 +5,55 @@ import type { FilterFieldsData, FilterGroupFieldData } from '../../types';
5
5
  import { FlexStack } from '../../layout/flex-stack';
6
6
  import { Stack } from '../../layout/stack';
7
7
  import { Button } from '../button';
8
- import { Dropdown } from '../dropdown';
8
+ import { ControlGroup } from '../control-group';
9
+ import { Dropdown, DropdownItem } from '../dropdown';
9
10
  import { InputSearch } from '../input-search';
10
11
  import * as I18N from './filters.i18n';
11
12
  import { getGroupFiltersLabelSuffix, LABELS } from './filters.utils';
12
13
  import css from './filters.module.css';
13
14
 
14
- interface FilterProps extends React.ComponentProps<'input'> {
15
- as?: React.ElementType;
16
- buttonClassName?: string;
15
+ interface FilterBooleanProps extends React.ComponentProps<'input'> {
17
16
  label: string;
18
- name: string;
19
- getOnOnlyClick?: (name: string) => () => void;
20
17
  }
21
18
 
22
- const Filter = (props: FilterProps) => {
23
- const {
24
- className = '',
25
- as: Component = 'div',
26
- buttonClassName = '',
27
- label,
28
- name,
29
- getOnOnlyClick,
30
- ...inputProps
31
- } = props;
32
-
33
- const id = `filter-${name}`;
34
- const rootClassName = cx(css.filter, className);
19
+ const Filter = (props: FilterBooleanProps) => {
20
+ const { className = '', label, name, ...inputProps } = props;
35
21
 
36
22
  return (
37
- <Component className={rootClassName}>
38
- {/* eslint-disable */}
39
- <FlexStack
40
- space="xxxsmall"
41
- alignItems="center"
42
- as="label"
43
- className={cx(css.filterCheckbox, buttonClassName)}
44
- >
45
- {/* eslint-enabled */}
46
- <input type="checkbox" id={id} name={name} {...inputProps} className={css.filterInput} />
47
- <span title={label} className={css.filterLabel}>
48
- {label}
49
- </span>
50
- </FlexStack>
51
-
52
- {getOnOnlyClick && (
53
- <Button
54
- kind="info"
55
- solid
56
- size="small"
57
- type="button"
58
- onClick={getOnOnlyClick(name)}
59
- className={css.filterOnlyButton}
60
- >
61
- {I18N.ONLY}
62
- </Button>
63
- )}
64
- </Component>
23
+ <FlexStack
24
+ space="xxxsmall"
25
+ alignItems="center"
26
+ as="label"
27
+ className={cx(css.filter, className)}
28
+ >
29
+ <input
30
+ type="checkbox"
31
+ id={`filter-${name}`}
32
+ name={name}
33
+ {...inputProps}
34
+ className={css.filterControl}
35
+ />
36
+ <span title={label} className={css.filterLabel}>
37
+ {label}
38
+ </span>
39
+ </FlexStack>
65
40
  );
66
41
  };
67
42
 
68
43
  interface FilterGroupProps extends React.ComponentProps<'div'> {
69
- buttonClassName?: string;
70
44
  groupKey: string;
71
45
  data: FilterGroupFieldData;
72
46
  values: Record<string, boolean>;
73
- onCheckboxChange: FilterProps['onChange'];
47
+ onCheckboxChange: FilterBooleanProps['onChange'];
74
48
  toggleFilters: (newFilters: Record<string, boolean>) => void;
75
49
  }
76
50
 
77
51
  const FilterGroup = (props: FilterGroupProps) => {
78
- const {
79
- className = '',
80
- buttonClassName = '',
81
- groupKey,
82
- data,
83
- values,
84
- onCheckboxChange,
85
- toggleFilters,
86
- } = props;
52
+ const { className = '', groupKey, data, values, onCheckboxChange, toggleFilters } = props;
53
+ const { label: groupLabel, children: groupItems } = data;
87
54
 
88
55
  const [search, setSearch] = useState('');
89
56
 
90
- const { label: groupLabel, children: groupItems } = data;
91
-
92
57
  const areAllGroupItemsChecked = groupItems
93
58
  .map(({ key: itemKey }) => values?.[`${groupKey}.${itemKey}`])
94
59
  .reduce((agg, val) => agg && val, true);
@@ -99,7 +64,9 @@ const FilterGroup = (props: FilterGroupProps) => {
99
64
  <>
100
65
  {`${groupLabel}:`}
101
66
  &nbsp;
102
- <span className={cx(hasCustomFilterSuffix && css.labelSuffixCustom)}>{filterSuffix}</span>
67
+ <span className={cx(hasCustomFilterSuffix && css.filterGroupLabelSuffixCustom)}>
68
+ {filterSuffix}
69
+ </span>
103
70
  </>
104
71
  );
105
72
 
@@ -131,87 +98,78 @@ const FilterGroup = (props: FilterGroupProps) => {
131
98
  return (
132
99
  <Dropdown
133
100
  className={className}
134
- buttonClassName={buttonClassName}
135
101
  label={dropdownLabel}
136
102
  ariaLabel={`${groupLabel}: ${filterSuffix}`}
137
103
  >
138
- {({ MenuItem, menuItemClassName }) => {
139
- return (
140
- <>
141
- {groupItems.length > 10 && (
142
- <div className={css.filterGroupSearchWrapper}>
143
- <InputSearch
144
- defaultValue={search}
145
- onChange={setSearch}
146
- placeholder={I18N.GROUP_SEARCH}
147
- debounceWait={0}
148
- />
149
- </div>
150
- )}
151
- <div className={css.filterGroupItems}>
152
- {filteredGroupItems.length === 0 && (
153
- <Stack className={css.filterGroupSearchNotFound}>
154
- <p>{I18N.GROUP_NOT_FOUND}</p>
155
- <div>
156
- <Button
157
- size="small"
158
- kind="primary"
159
- type="button"
160
- onClick={() => setSearch('')}
161
- className={css.filterGroupSearchNotFoundClear}
162
- >
163
- {I18N.GROUP_SEARCH_CLEAR}
164
- </Button>
165
- </div>
166
- </Stack>
167
- )}
168
- {filteredGroupItems.map(({ key: itemKey, ...itemData }) => {
169
- const id = [groupKey, itemKey].join('.');
170
- const getOnOnlyClick = () => getOnGroupCheck(false, { [id]: true });
171
-
172
- return (
173
- <Filter
174
- key={id}
175
- className={menuItemClassName}
176
- as={MenuItem}
177
- name={id}
178
- label={itemData.label}
179
- onChange={onCheckboxChange}
180
- checked={values[id]}
181
- disabled={itemData.disabled}
182
- getOnOnlyClick={getOnOnlyClick}
183
- />
184
- );
185
- })}
104
+ {groupItems.length > 10 && (
105
+ <div className={css.filterGroupSearchWrapper}>
106
+ <InputSearch
107
+ defaultValue={search}
108
+ onChange={setSearch}
109
+ placeholder={I18N.GROUP_SEARCH}
110
+ debounceWait={0}
111
+ />
112
+ </div>
113
+ )}
114
+ <div className={css.filterGroupItems}>
115
+ {filteredGroupItems.length === 0 && (
116
+ <Stack className={css.filterGroupSearchNotFound}>
117
+ <p>{I18N.GROUP_NOT_FOUND}</p>
118
+ <div>
119
+ <Button
120
+ size="small"
121
+ kind="primary"
122
+ type="button"
123
+ onClick={() => setSearch('')}
124
+ className={css.filterGroupSearchNotFoundClear}
125
+ >
126
+ {I18N.GROUP_SEARCH_CLEAR}
127
+ </Button>
186
128
  </div>
187
- {filteredGroupItems.length !== 0 && (
188
- <div className={css.filterGroupActions}>
189
- {areAllGroupItemsChecked ? (
190
- <MenuItem
191
- id="clear-all"
192
- as="button"
193
- className={menuItemClassName}
194
- type="button"
195
- onClick={getOnGroupCheck(false)}
196
- >
197
- {I18N.CLEAR}
198
- </MenuItem>
199
- ) : (
200
- <MenuItem
201
- id="clear-all"
202
- as="button"
203
- className={menuItemClassName}
204
- type="button"
205
- onClick={getOnGroupCheck(true)}
206
- >
207
- {I18N.CHECK}
208
- </MenuItem>
209
- )}
210
- </div>
211
- )}
212
- </>
213
- );
214
- }}
129
+ </Stack>
130
+ )}
131
+ {filteredGroupItems.map(({ key: itemKey, ...itemData }) => {
132
+ const id = [groupKey, itemKey].join('.');
133
+ const getOnOnlyClick = () => getOnGroupCheck(false, { [id]: true });
134
+
135
+ return (
136
+ <DropdownItem key={id} className={css.filterGroupItem}>
137
+ <Filter
138
+ label={itemData.label}
139
+ name={id}
140
+ onChange={onCheckboxChange}
141
+ checked={values[id]}
142
+ disabled={itemData.disabled}
143
+ className={css.filterGroupItemFilter}
144
+ />
145
+ <Button
146
+ kind="info"
147
+ solid
148
+ size="small"
149
+ type="button"
150
+ onClick={getOnOnlyClick()}
151
+ disabled={itemData.disabled}
152
+ className={css.filterGroupOnlyButton}
153
+ >
154
+ {I18N.ONLY}
155
+ </Button>
156
+ </DropdownItem>
157
+ );
158
+ })}
159
+ </div>
160
+ {filteredGroupItems.length !== 0 && (
161
+ <div className={css.filterGroupActions}>
162
+ {areAllGroupItemsChecked ? (
163
+ <DropdownItem id="clear-all" onClick={getOnGroupCheck(false)} role="button">
164
+ {I18N.CLEAR}
165
+ </DropdownItem>
166
+ ) : (
167
+ <DropdownItem id="clear-all" onClick={getOnGroupCheck(true)} role="button">
168
+ {I18N.CHECK}
169
+ </DropdownItem>
170
+ )}
171
+ </div>
172
+ )}
215
173
  </Dropdown>
216
174
  );
217
175
  };
@@ -226,6 +184,9 @@ interface FiltersProps extends React.ComponentProps<'div'> {
226
184
  export const Filters = (props: FiltersProps) => {
227
185
  const { className = '', values, filters, toggleFilter, toggleFilters } = props;
228
186
 
187
+ /**
188
+ * Toggle filter value on checkbox change
189
+ */
229
190
  const onCheckboxChange = useCallback(
230
191
  (event: any) => {
231
192
  const { name } = event.target;
@@ -233,41 +194,41 @@ export const Filters = (props: FiltersProps) => {
233
194
  },
234
195
  [toggleFilter, values],
235
196
  );
236
- const rootClassName = cx(css.root, className);
197
+
198
+ const filterList = Object.entries(filters);
199
+ const filterCount = filterList.length;
237
200
 
238
201
  return (
239
- <form className={rootClassName}>
240
- <FlexStack space="xxsmall" alignItems="top" className={css.items}>
241
- {Object.entries(filters).map(([name, data]) => {
242
- if ('defaultValue' in data) {
243
- return (
244
- <Filter
245
- key={name}
246
- className={cx(css.item, css.filterStandalone)}
247
- buttonClassName={css.itemButton}
248
- name={name}
249
- label={data.label}
250
- onChange={onCheckboxChange}
251
- checked={values[name]}
252
- disabled={data.disabled as boolean}
253
- />
254
- );
255
- }
202
+ <ControlGroup className={cx(css.root, className)}>
203
+ {filterList.map(([name, data], index) => {
204
+ const lastItem = index === filterCount - 1;
256
205
 
206
+ if ('defaultValue' in data) {
257
207
  return (
258
- <FilterGroup
259
- className={css.item}
260
- buttonClassName={css.itemButton}
208
+ <Filter
209
+ name={name}
210
+ label={data.label}
211
+ onChange={onCheckboxChange}
212
+ checked={values[name]}
213
+ disabled={data.disabled as boolean}
261
214
  key={name}
262
- groupKey={name}
263
- data={data}
264
- values={values}
265
- onCheckboxChange={onCheckboxChange}
266
- toggleFilters={toggleFilters}
215
+ className={cx(css.filterSingle, lastItem && css.itemLast)}
267
216
  />
268
217
  );
269
- })}
270
- </FlexStack>
271
- </form>
218
+ }
219
+
220
+ return (
221
+ <FilterGroup
222
+ groupKey={name}
223
+ data={data}
224
+ values={values}
225
+ onCheckboxChange={onCheckboxChange}
226
+ toggleFilters={toggleFilters}
227
+ className={cx(lastItem && css.itemLast)}
228
+ key={name}
229
+ />
230
+ );
231
+ })}
232
+ </ControlGroup>
272
233
  );
273
234
  };
@@ -31,7 +31,7 @@ export const HoverCard = (props: HoverCardProps) => {
31
31
  children,
32
32
  } = props;
33
33
 
34
- const state = useHovercardState({ gutter: 8, timeout: 300 });
34
+ const state = useHovercardState({ gutter: 8, timeout: 300, placement: 'top' });
35
35
  const hovercardProps = useHovercard({ state, portal: true });
36
36
 
37
37
  // Fallback to span if no href
@@ -5,10 +5,11 @@ import css from './icon.module.css';
5
5
 
6
6
  const ICONS = {
7
7
  ARROW: 'arrow',
8
- ARROW_RIGHT_CIRLCE: 'arrow-right-circle',
8
+ ARROW_RIGHT_CIRCLE: 'arrow-right-circle',
9
9
  CANCEL: 'close',
10
10
  CHEVRON_DOWN: 'chevron-down',
11
11
  CHEVRON_UP: 'chevron-up',
12
+ CHECK: 'check',
12
13
  CLOSE: 'close',
13
14
  CLOCK: 'clock',
14
15
  COMMIT: 'commit',
@@ -70,6 +70,7 @@ export const InputSearch = (
70
70
  />
71
71
  {value && (
72
72
  <Button
73
+ size="small"
73
74
  radius="circle"
74
75
  glyph={Icon.ICONS.CANCEL}
75
76
  type="button"
@@ -4,7 +4,7 @@ import cx from 'classnames';
4
4
 
5
5
  import css from './loader.module.css';
6
6
 
7
- export const Loader = ({ className, size, ...restProps }) => (
7
+ export const Loader = ({ className = '', size = 'medium', ...restProps }) => (
8
8
  <span className={cx(css.root, className, css[size])} {...restProps} />
9
9
  );
10
10
 
@@ -89,6 +89,36 @@
89
89
  border-width: 1px;
90
90
  }
91
91
 
92
+ /** cascade border radius */
93
+ .root thead,
94
+ .root thead tr:first-child {
95
+ border-top-left-radius: inherit;
96
+ border-top-right-radius: inherit;
97
+ }
98
+
99
+ .root thead tr:first-child th:first-child {
100
+ border-top-left-radius: inherit;
101
+ }
102
+
103
+ .root thead tr:first-child th:last-child {
104
+ border-top-right-radius: inherit;
105
+ }
106
+
107
+ .root tbody:last-child,
108
+ .root tbody:last-child tr:last-child {
109
+ border-bottom-left-radius: inherit;
110
+ border-bottom-right-radius: inherit;
111
+ }
112
+
113
+ .root tbody:last-child tr:last-child th:first-child,
114
+ .root tbody:last-child tr:last-child td:first-child {
115
+ border-bottom-left-radius: inherit;
116
+ }
117
+
118
+ .root tbody:last-child tr:last-child td:last-child {
119
+ border-bottom-right-radius: inherit;
120
+ }
121
+
92
122
  /* compact variation */
93
123
  .compact td,
94
124
  .compact th {
@@ -42,7 +42,7 @@ a.root:active {
42
42
  /** Size variation */
43
43
  /** default: medium */
44
44
  .root {
45
- border-radius: var(--radius-medium);
45
+ border-radius: var(--radius-small);
46
46
  padding: calc(var(--space-xxxsmall) / 2) var(--space-xxxsmall);
47
47
  min-width: var(--space-small);
48
48
  height: var(--space-small);
@@ -51,7 +51,7 @@ a.root:active {
51
51
  }
52
52
 
53
53
  .small {
54
- border-radius: var(--radius-small);
54
+ border-radius: var(--radius-xsmall);
55
55
  padding: calc(var(--space-xxxsmall) / 2);
56
56
  height: var(--space-xsmall);
57
57
  min-width: var(--space-xsmall);
@@ -60,7 +60,7 @@ a.root:active {
60
60
  }
61
61
 
62
62
  .large {
63
- border-radius: var(--radius-large);
63
+ border-radius: var(--radius-medium);
64
64
  padding: var(--space-xxxsmall) var(--space-xxsmall);
65
65
  min-width: var(--space-medium);
66
66
  height: var(--space-medium);
@@ -1,6 +1,4 @@
1
- .root {
2
- padding: var(--space-small);
3
- }
1
+ .root { }
4
2
 
5
3
  .content {}
6
4
 
@@ -1,4 +1,4 @@
1
- export declare const SEARCH = "Search by module name";
1
+ export declare const SEARCH = "Search by module path";
2
2
  export declare const CHANGED = "Changed";
3
3
  export declare const DUPLICATE = "Duplicate";
4
4
  export declare const CHUNK = "Chunk";
@@ -1,8 +1,8 @@
1
1
  export function Delta({ className, displayValue, deltaType, inverted }: {
2
- className: any;
2
+ className?: string | undefined;
3
3
  displayValue: any;
4
4
  deltaType: any;
5
- inverted: any;
5
+ inverted?: boolean | undefined;
6
6
  }): React.JSX.Element;
7
7
  export namespace Delta {
8
8
  namespace defaultProps {
@@ -1,9 +1,11 @@
1
1
  import React from 'react';
2
2
  import { MetricsDisplayType } from '../../constants';
3
- import { FlexStack } from '../../layout/flex-stack';
3
+ import { ControlGroup } from '../../ui/control-group';
4
4
  interface MetricsDisplaySelectorProps {
5
5
  value: MetricsDisplayType;
6
- onSelect: (newValue: MetricsDisplayType) => void;
6
+ groupBy?: string;
7
+ groups?: Partial<Record<MetricsDisplayType, Array<string>>>;
8
+ onSelect: (newValue: MetricsDisplayType, groupBy?: string) => void;
7
9
  }
8
- export declare const MetricsDisplaySelector: (props: MetricsDisplaySelectorProps & Omit<React.ComponentProps<typeof FlexStack>, 'onSelect' | 'value'>) => React.JSX.Element;
10
+ export declare const MetricsDisplaySelector: (props: MetricsDisplaySelectorProps & Omit<React.ComponentProps<typeof ControlGroup>, 'onSelect' | 'value'>) => React.JSX.Element;
9
11
  export {};
@@ -1 +1,2 @@
1
1
  export * from './metrics-treemap';
2
+ export { getTreemapNodes, getTreemapNodesGroupedByPath } from './metrics-treemap.utils';
@@ -0,0 +1,20 @@
1
+ import type { ReportMetricRow } from '@bundle-stats/utils';
2
+ export interface TreeTotal {
3
+ current: number;
4
+ baseline: number;
5
+ }
6
+ export interface TreeLeaf {
7
+ id: string;
8
+ label: string;
9
+ value: number;
10
+ item: ReportMetricRow;
11
+ }
12
+ export interface Tree {
13
+ id: string;
14
+ label: string;
15
+ value: number;
16
+ children: TreeNodeChildren;
17
+ total?: TreeTotal;
18
+ }
19
+ export type TreeNode = Tree | TreeLeaf;
20
+ export type TreeNodeChildren = Array<TreeNode>;
@@ -1,9 +1,11 @@
1
- import React from 'react';
2
- import type { ReportMetricRow } from '@bundle-stats/utils';
1
+ import React, { type ComponentProps, type ReactNode } from 'react';
2
+ import type { Tree } from './metrics-treemap.constants';
3
3
  interface MetricsTreemapProps {
4
- items: Array<ReportMetricRow>;
5
- emptyMessage?: React.ReactNode;
4
+ treeNodes: Tree;
5
+ emptyMessage?: ReactNode;
6
+ nested?: boolean;
6
7
  onItemClick?: (entryId: string) => void;
8
+ onGroupClick?: (entryId: string) => void;
7
9
  }
8
- export declare const MetricsTreemap: (props: MetricsTreemapProps & React.ComponentProps<'div'>) => React.JSX.Element;
10
+ export declare const MetricsTreemap: (props: MetricsTreemapProps & ComponentProps<'div'>) => React.JSX.Element;
9
11
  export {};
@@ -0,0 +1,2 @@
1
+ export declare const TILE_GROUP_LABEL = "View children entries";
2
+ export declare const TILE_LABEL = "View entry info";
@@ -0,0 +1,5 @@
1
+ import { DeltaType, type MetricRunInfoBaseline, type MetricRunInfo, type ReportMetricRow } from '@bundle-stats/utils';
2
+ import type { Tree } from './metrics-treemap.constants';
3
+ export declare function getTreemapNodes(items: Array<ReportMetricRow>): Tree;
4
+ export declare function getTreemapNodesGroupedByPath(items: Array<ReportMetricRow>): Tree;
5
+ export declare function resolveGroupDeltaType(metricRunInfo?: MetricRunInfo | MetricRunInfoBaseline): DeltaType.NO_CHANGE | DeltaType.NEGATIVE | DeltaType.POSITIVE;
@@ -1,4 +1,10 @@
1
1
  import { MetricsDisplayType } from '../constants';
2
- type UseMetricsDisplayType = [MetricsDisplayType, (value: MetricsDisplayType) => void];
3
- export declare const useMetricsDisplayType: () => UseMetricsDisplayType;
2
+ type UseMetricsDisplayType = [
3
+ {
4
+ value: MetricsDisplayType;
5
+ groupBy?: string;
6
+ },
7
+ (newDisplayType: MetricsDisplayType, newGroupBy?: string) => void
8
+ ];
9
+ export declare const useMetricsDisplayType: (groups?: Partial<Record<MetricsDisplayType, Array<string>>>) => UseMetricsDisplayType;
4
10
  export {};
@@ -1,50 +1,15 @@
1
- export function Dropdown(props: any): React.JSX.Element;
2
- export namespace Dropdown {
3
- export namespace defaultProps {
4
- let className: string;
5
- let buttonClassName: string;
6
- let label: null;
7
- let ariaLabel: string;
8
- let glyph: null;
9
- let disabled: boolean;
10
- }
11
- export namespace propTypes {
12
- let className_1: PropTypes.Requireable<string>;
13
- export { className_1 as className };
14
- let buttonClassName_1: PropTypes.Requireable<string>;
15
- export { buttonClassName_1 as buttonClassName };
16
- let label_1: PropTypes.Requireable<PropTypes.ReactNodeLike>;
17
- export { label_1 as label };
18
- let ariaLabel_1: PropTypes.Requireable<string>;
19
- export { ariaLabel_1 as ariaLabel };
20
- let glyph_1: PropTypes.Requireable<NonNullable<PropTypes.ReactNodeLike>>;
21
- export { glyph_1 as glyph };
22
- let disabled_1: PropTypes.Requireable<boolean>;
23
- export { disabled_1 as disabled };
24
- export let children: PropTypes.Validator<NonNullable<NonNullable<string | PropTypes.ReactElementLike | ((...args: any[]) => any) | null | undefined>>>;
25
- }
26
- export { Item };
27
- }
28
1
  import React from 'react';
29
- import PropTypes from 'prop-types';
30
- declare function Item({ className, isActive, ...restProps }: {
31
- [x: string]: any;
32
- className?: string | undefined;
33
- isActive?: boolean | undefined;
34
- }): React.JSX.Element;
35
- declare namespace Item {
36
- export namespace propTypes_1 {
37
- let className_2: PropTypes.Requireable<string>;
38
- export { className_2 as className };
39
- export let isActive: PropTypes.Requireable<boolean>;
40
- }
41
- export { propTypes_1 as propTypes };
42
- export namespace defaultProps_1 {
43
- let className_3: string;
44
- export { className_3 as className };
45
- let isActive_1: boolean;
46
- export { isActive_1 as isActive };
47
- }
48
- export { defaultProps_1 as defaultProps };
2
+ import { MenuItem } from 'ariakit/menu';
3
+ interface DropdownItemProps {
4
+ isActive?: boolean;
5
+ }
6
+ export declare const DropdownItem: (props: DropdownItemProps & React.ComponentProps<typeof MenuItem>) => React.JSX.Element;
7
+ interface DropdownProps {
8
+ dropdownClassName?: string;
9
+ label?: React.ReactNode;
10
+ ariaLabel?: string;
11
+ glyph?: string;
12
+ disabled?: boolean;
49
13
  }
14
+ export declare const Dropdown: (props: DropdownProps & React.ComponentProps<'div'>) => React.JSX.Element;
50
15
  export {};
@@ -1 +1 @@
1
- export * from "./dropdown";
1
+ export * from './dropdown';