@tcn/ui-table 2.3.14 → 2.4.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.
- package/dist/components/cells/header_cell.d.ts.map +1 -1
- package/dist/components/cells/header_cell.js +10 -9
- package/dist/components/cells/header_cell.js.map +1 -1
- package/dist/components/table_filter_panel/field_filters/number_field_filter.js +6 -6
- package/dist/components/table_filter_panel/field_filters/number_field_filter.js.map +1 -1
- package/dist/components/table_filter_panel/field_filters/string_field_filter.js +9 -9
- package/dist/components/table_filter_panel/field_filters/string_field_filter.js.map +1 -1
- package/dist/components/table_filter_panel/table_filter_panel.d.ts +2 -1
- package/dist/components/table_filter_panel/table_filter_panel.d.ts.map +1 -1
- package/dist/components/table_filter_panel/table_filter_panel.js +39 -44
- package/dist/components/table_filter_panel/table_filter_panel.js.map +1 -1
- package/dist/table_filter_panel.css +1 -1
- package/package.json +4 -4
- package/src/__stories__/table.stories.tsx +11 -18
- package/src/components/cells/header_cell.tsx +2 -1
- package/src/components/table_filter_panel/field_filters/number_field_filter.tsx +3 -3
- package/src/components/table_filter_panel/field_filters/string_field_filter.tsx +3 -3
- package/src/components/table_filter_panel/table_filter_panel.module.css +0 -5
- package/src/components/table_filter_panel/table_filter_panel.stories.tsx +4 -3
- package/src/components/table_filter_panel/table_filter_panel.tsx +17 -15
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"header_cell.d.ts","sourceRoot":"","sources":["../../../src/components/cells/header_cell.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAsB,MAAM,OAAO,CAAC;AAM3C,OAAO,EAAe,KAAK,gBAAgB,EAAE,MAAM,mBAAmB,CAAC;AAEvE,MAAM,WAAW,eAAgB,SAAQ,gBAAgB;IACvD,OAAO,EAAE,KAAK,CAAC,SAAS,CAAC;IACzB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,OAAO,GAAG,KAAK,CAAC;IACzB,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACnC,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,wBAAgB,UAAU,CAAC,EACzB,OAAO,EACP,MAAM,EACN,QAAQ,EACR,KAAK,EACL,QAAQ,EACR,gBAAgB,EAChB,OAAO,GACR,EAAE,eAAe,
|
|
1
|
+
{"version":3,"file":"header_cell.d.ts","sourceRoot":"","sources":["../../../src/components/cells/header_cell.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAsB,MAAM,OAAO,CAAC;AAM3C,OAAO,EAAe,KAAK,gBAAgB,EAAE,MAAM,mBAAmB,CAAC;AAEvE,MAAM,WAAW,eAAgB,SAAQ,gBAAgB;IACvD,OAAO,EAAE,KAAK,CAAC,SAAS,CAAC;IACzB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,OAAO,GAAG,KAAK,CAAC;IACzB,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACnC,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,wBAAgB,UAAU,CAAC,EACzB,OAAO,EACP,MAAM,EACN,QAAQ,EACR,KAAK,EACL,QAAQ,EACR,gBAAgB,EAChB,OAAO,GACR,EAAE,eAAe,2CA4CjB"}
|
|
@@ -3,14 +3,14 @@ import { useCallback as x } from "react";
|
|
|
3
3
|
import { Box as r, HStack as h } from "@tcn/ui/stacks";
|
|
4
4
|
import { TH as f } from "@tcn/ui/layouts";
|
|
5
5
|
import { c as u } from "../../cell.module-WpHnQBVu.js";
|
|
6
|
-
import { SortControl as
|
|
7
|
-
function
|
|
6
|
+
import { SortControl as C } from "./sort_control.js";
|
|
7
|
+
function H({
|
|
8
8
|
heading: n,
|
|
9
9
|
sticky: l,
|
|
10
10
|
onResize: i,
|
|
11
11
|
width: o,
|
|
12
|
-
sortMode:
|
|
13
|
-
onSortModeChange:
|
|
12
|
+
sortMode: a,
|
|
13
|
+
onSortModeChange: s,
|
|
14
14
|
canSort: d
|
|
15
15
|
}) {
|
|
16
16
|
const m = l != null ? 2 : 1, p = x(
|
|
@@ -31,9 +31,10 @@ function z({
|
|
|
31
31
|
padding: "0px 8px",
|
|
32
32
|
overflow: "hidden",
|
|
33
33
|
minWidth: "24px",
|
|
34
|
+
maxWidth: "unset",
|
|
35
|
+
width: o,
|
|
34
36
|
enableResizeOnEnd: !0,
|
|
35
37
|
onWidthResize: p,
|
|
36
|
-
style: { width: `${o}px`, minWidth: "20px" },
|
|
37
38
|
onClick: (t) => t.stopPropagation(),
|
|
38
39
|
children: /* @__PURE__ */ c(h, { children: [
|
|
39
40
|
/* @__PURE__ */ e(
|
|
@@ -46,11 +47,11 @@ function z({
|
|
|
46
47
|
}
|
|
47
48
|
),
|
|
48
49
|
/* @__PURE__ */ e(
|
|
49
|
-
|
|
50
|
+
C,
|
|
50
51
|
{
|
|
51
52
|
canSort: d,
|
|
52
|
-
onSortModeChange:
|
|
53
|
-
sortMode:
|
|
53
|
+
onSortModeChange: s,
|
|
54
|
+
sortMode: a
|
|
54
55
|
}
|
|
55
56
|
)
|
|
56
57
|
] })
|
|
@@ -60,6 +61,6 @@ function z({
|
|
|
60
61
|
);
|
|
61
62
|
}
|
|
62
63
|
export {
|
|
63
|
-
|
|
64
|
+
H as HeaderCell
|
|
64
65
|
};
|
|
65
66
|
//# sourceMappingURL=header_cell.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"header_cell.js","sources":["../../../src/components/cells/header_cell.tsx"],"sourcesContent":["import React, { useCallback } from 'react';\n\nimport { Box, HStack, type OnWidthResizePayload } from '@tcn/ui/stacks';\n\nimport { TH } from '@tcn/ui/layouts';\nimport cellStyles from './cell.module.css';\nimport { SortControl, type SortControlProps } from './sort_control.js';\n\nexport interface HeaderCellProps extends SortControlProps {\n heading: React.ReactNode;\n index: number;\n sticky?: 'start' | 'end';\n onResize?: (width: number) => void;\n width?: number;\n}\n\nexport function HeaderCell({\n heading,\n sticky,\n onResize,\n width,\n sortMode,\n onSortModeChange,\n canSort,\n}: HeaderCellProps) {\n const zIndex = sticky != null ? 2 : 1;\n\n const handleResize = useCallback(\n ({ width }: OnWidthResizePayload) => {\n onResize?.(Math.max(width, 20));\n },\n [onResize]\n );\n\n return (\n <TH\n className={cellStyles['table-cell']}\n data-stick-to={sticky}\n style={{ width: `${width}px`, zIndex }}\n >\n <Box\n padding=\"0px 8px\" // FIXME: should be on theme ideally.\n overflow=\"hidden\"\n minWidth=\"24px\"\n
|
|
1
|
+
{"version":3,"file":"header_cell.js","sources":["../../../src/components/cells/header_cell.tsx"],"sourcesContent":["import React, { useCallback } from 'react';\n\nimport { Box, HStack, type OnWidthResizePayload } from '@tcn/ui/stacks';\n\nimport { TH } from '@tcn/ui/layouts';\nimport cellStyles from './cell.module.css';\nimport { SortControl, type SortControlProps } from './sort_control.js';\n\nexport interface HeaderCellProps extends SortControlProps {\n heading: React.ReactNode;\n index: number;\n sticky?: 'start' | 'end';\n onResize?: (width: number) => void;\n width?: number;\n}\n\nexport function HeaderCell({\n heading,\n sticky,\n onResize,\n width,\n sortMode,\n onSortModeChange,\n canSort,\n}: HeaderCellProps) {\n const zIndex = sticky != null ? 2 : 1;\n\n const handleResize = useCallback(\n ({ width }: OnWidthResizePayload) => {\n onResize?.(Math.max(width, 20));\n },\n [onResize]\n );\n\n return (\n <TH\n className={cellStyles['table-cell']}\n data-stick-to={sticky}\n style={{ width: `${width}px`, zIndex }}\n >\n <Box\n padding=\"0px 8px\" // FIXME: should be on theme ideally.\n overflow=\"hidden\"\n minWidth=\"24px\"\n maxWidth=\"unset\"\n width={width}\n enableResizeOnEnd\n onWidthResize={handleResize}\n onClick={e => e.stopPropagation()}\n >\n <HStack>\n <Box\n minWidth=\"24px\"\n className=\"ellipsis\"\n style={{ alignItems: 'center', display: 'flex' }}\n >\n {heading}\n </Box>\n\n <SortControl\n canSort={canSort}\n onSortModeChange={onSortModeChange}\n sortMode={sortMode}\n />\n </HStack>\n </Box>\n </TH>\n );\n}\n"],"names":["HeaderCell","heading","sticky","onResize","width","sortMode","onSortModeChange","canSort","zIndex","handleResize","useCallback","jsx","TH","cellStyles","Box","e","HStack","SortControl"],"mappings":";;;;;;AAgBO,SAASA,EAAW;AAAA,EACzB,SAAAC;AAAA,EACA,QAAAC;AAAA,EACA,UAAAC;AAAA,EACA,OAAAC;AAAA,EACA,UAAAC;AAAA,EACA,kBAAAC;AAAA,EACA,SAAAC;AACF,GAAoB;AAClB,QAAMC,IAASN,KAAU,OAAO,IAAI,GAE9BO,IAAeC;AAAA,IACnB,CAAC,EAAE,OAAAN,QAAkC;AACnC,MAAAD,IAAW,KAAK,IAAIC,GAAO,EAAE,CAAC;AAAA,IAChC;AAAA,IACA,CAACD,CAAQ;AAAA,EAAA;AAGX,SACE,gBAAAQ;AAAA,IAACC;AAAA,IAAA;AAAA,MACC,WAAWC,EAAW,YAAY;AAAA,MAClC,iBAAeX;AAAA,MACf,OAAO,EAAE,OAAO,GAAGE,CAAK,MAAM,QAAAI,EAAA;AAAA,MAE9B,UAAA,gBAAAG;AAAA,QAACG;AAAA,QAAA;AAAA,UACC,SAAQ;AAAA,UACR,UAAS;AAAA,UACT,UAAS;AAAA,UACT,UAAS;AAAA,UACT,OAAAV;AAAA,UACA,mBAAiB;AAAA,UACjB,eAAeK;AAAA,UACf,SAAS,CAAAM,MAAKA,EAAE,gBAAA;AAAA,UAEhB,4BAACC,GAAA,EACC,UAAA;AAAA,YAAA,gBAAAL;AAAA,cAACG;AAAA,cAAA;AAAA,gBACC,UAAS;AAAA,gBACT,WAAU;AAAA,gBACV,OAAO,EAAE,YAAY,UAAU,SAAS,OAAA;AAAA,gBAEvC,UAAAb;AAAA,cAAA;AAAA,YAAA;AAAA,YAGH,gBAAAU;AAAA,cAACM;AAAA,cAAA;AAAA,gBACC,SAAAV;AAAA,gBACA,kBAAAD;AAAA,gBACA,UAAAD;AAAA,cAAA;AAAA,YAAA;AAAA,UACF,EAAA,CACF;AAAA,QAAA;AAAA,MAAA;AAAA,IACF;AAAA,EAAA;AAGN;"}
|
|
@@ -1,19 +1,19 @@
|
|
|
1
|
-
import { jsx as t, jsxs as
|
|
2
|
-
import { useSignalValue as
|
|
3
|
-
import {
|
|
1
|
+
import { jsx as t, jsxs as s } from "react/jsx-runtime";
|
|
2
|
+
import { useSignalValue as o } from "@tcn/state";
|
|
3
|
+
import { ControlSet as u, Select as m, Option as p, Input as c } from "@tcn/ui/inputs";
|
|
4
4
|
import { NumberFieldFilterPresenter as d } from "./number_field_filter_presenter.js";
|
|
5
5
|
import { useFieldFilterStrategy as b } from "./use_field_filter_strategy.js";
|
|
6
6
|
import { ClearableField as f } from "./clearable_field.js";
|
|
7
7
|
const h = [">=", ">", "<=", "<", "=", "!="];
|
|
8
|
-
function N({ fieldName:
|
|
9
|
-
const r = b(d,
|
|
8
|
+
function N({ fieldName: n, label: a }) {
|
|
9
|
+
const r = b(d, n), l = o(r.broadcasts.value), i = o(r.broadcasts.operator);
|
|
10
10
|
return /* @__PURE__ */ t(
|
|
11
11
|
f,
|
|
12
12
|
{
|
|
13
13
|
label: a,
|
|
14
14
|
onClear: () => r.setValue(null),
|
|
15
15
|
isClearable: l == null,
|
|
16
|
-
children: /* @__PURE__ */ u
|
|
16
|
+
children: /* @__PURE__ */ s(u, { children: [
|
|
17
17
|
/* @__PURE__ */ t(
|
|
18
18
|
m,
|
|
19
19
|
{
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"number_field_filter.js","sources":["../../../../src/components/table_filter_panel/field_filters/number_field_filter.tsx"],"sourcesContent":["import { useSignalValue } from '@tcn/state';\nimport { Input, Option, Select,
|
|
1
|
+
{"version":3,"file":"number_field_filter.js","sources":["../../../../src/components/table_filter_panel/field_filters/number_field_filter.tsx"],"sourcesContent":["import { useSignalValue } from '@tcn/state';\nimport { Input, Option, Select, ControlSet } from '@tcn/ui/inputs';\nimport { FieldFilterProps } from './field_filter_props.js';\nimport { NumberFieldFilterPresenter } from './number_field_filter_presenter.js';\nimport { useFieldFilterStrategy } from './use_field_filter_strategy.js';\nimport { ComparisonOperator } from '../types.js';\nimport { ClearableField } from './clearable_field.js';\n\nconst operators: ComparisonOperator[] = ['>=', '>', '<=', '<', '=', '!='];\n\nexport function NumberFieldFilter({ fieldName, label }: FieldFilterProps) {\n const presenter = useFieldFilterStrategy(NumberFieldFilterPresenter, fieldName);\n\n const value = useSignalValue(presenter.broadcasts.value);\n const operator = useSignalValue(presenter.broadcasts.operator);\n\n return (\n <ClearableField\n label={label}\n onClear={() => presenter.setValue(null)}\n isClearable={value == null}\n >\n <ControlSet>\n <Select\n value={operator}\n onChange={value => presenter.setOperator(value as ComparisonOperator)}\n width=\"55px\"\n >\n {operators.map(operator => (\n <Option key={operator} value={operator} label={operator}>\n {operator}\n </Option>\n ))}\n </Select>\n <Input\n type=\"number\"\n value={String(value ?? '')}\n onChange={value => presenter.setValue(Number(value))}\n />\n </ControlSet>\n </ClearableField>\n );\n}\n"],"names":["operators","NumberFieldFilter","fieldName","label","presenter","useFieldFilterStrategy","NumberFieldFilterPresenter","value","useSignalValue","operator","jsx","ClearableField","ControlSet","Select","Option","Input"],"mappings":";;;;;;AAQA,MAAMA,IAAkC,CAAC,MAAM,KAAK,MAAM,KAAK,KAAK,IAAI;AAEjE,SAASC,EAAkB,EAAE,WAAAC,GAAW,OAAAC,KAA2B;AACxE,QAAMC,IAAYC,EAAuBC,GAA4BJ,CAAS,GAExEK,IAAQC,EAAeJ,EAAU,WAAW,KAAK,GACjDK,IAAWD,EAAeJ,EAAU,WAAW,QAAQ;AAE7D,SACE,gBAAAM;AAAA,IAACC;AAAA,IAAA;AAAA,MACC,OAAAR;AAAA,MACA,SAAS,MAAMC,EAAU,SAAS,IAAI;AAAA,MACtC,aAAaG,KAAS;AAAA,MAEtB,4BAACK,GAAA,EACC,UAAA;AAAA,QAAA,gBAAAF;AAAA,UAACG;AAAA,UAAA;AAAA,YACC,OAAOJ;AAAA,YACP,UAAU,CAAAF,MAASH,EAAU,YAAYG,CAA2B;AAAA,YACpE,OAAM;AAAA,YAEL,UAAAP,EAAU,IAAI,CAAAS,MACb,gBAAAC,EAACI,GAAA,EAAsB,OAAOL,GAAU,OAAOA,GAC5C,UAAAA,EAAAA,GADUA,CAEb,CACD;AAAA,UAAA;AAAA,QAAA;AAAA,QAEH,gBAAAC;AAAA,UAACK;AAAA,UAAA;AAAA,YACC,MAAK;AAAA,YACL,OAAO,OAAOR,KAAS,EAAE;AAAA,YACzB,UAAU,CAAAA,MAASH,EAAU,SAAS,OAAOG,CAAK,CAAC;AAAA,UAAA;AAAA,QAAA;AAAA,MACrD,EAAA,CACF;AAAA,IAAA;AAAA,EAAA;AAGN;"}
|
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
import { jsx as r, jsxs as
|
|
1
|
+
import { jsx as r, jsxs as u } from "react/jsx-runtime";
|
|
2
2
|
import { useSignalValue as o } from "@tcn/state";
|
|
3
|
-
import {
|
|
3
|
+
import { ControlSet as m, Select as d, Option as h, Input as b } from "@tcn/ui/inputs";
|
|
4
4
|
import { StringFieldFilterPresenter as f } from "./string_field_filter_presenter.js";
|
|
5
5
|
import { useFieldFilterStrategy as F } from "./use_field_filter_strategy.js";
|
|
6
|
-
import { ClearableField as
|
|
7
|
-
const
|
|
6
|
+
import { ClearableField as S } from "./clearable_field.js";
|
|
7
|
+
const g = ["is", "isNot", "has"], v = {
|
|
8
8
|
is: "=",
|
|
9
9
|
isNot: "!=",
|
|
10
10
|
has: ":"
|
|
@@ -14,24 +14,24 @@ const v = ["is", "isNot", "has"], S = {
|
|
|
14
14
|
has: "has"
|
|
15
15
|
};
|
|
16
16
|
function j({ fieldName: a, label: i, operators: n }) {
|
|
17
|
-
const t = F(f, a), l = o(t.broadcasts.value), p = o(t.broadcasts.operator),
|
|
17
|
+
const t = F(f, a), l = o(t.broadcasts.value), p = o(t.broadcasts.operator), c = n || g;
|
|
18
18
|
return /* @__PURE__ */ r(
|
|
19
|
-
|
|
19
|
+
S,
|
|
20
20
|
{
|
|
21
21
|
label: i,
|
|
22
22
|
onClear: () => t.setValue(null),
|
|
23
23
|
isClearable: l == null,
|
|
24
|
-
children: /* @__PURE__ */
|
|
24
|
+
children: /* @__PURE__ */ u(m, { children: [
|
|
25
25
|
/* @__PURE__ */ r(
|
|
26
26
|
d,
|
|
27
27
|
{
|
|
28
28
|
value: p,
|
|
29
29
|
onChange: (e) => t.setOperator(e),
|
|
30
30
|
width: "65px",
|
|
31
|
-
children:
|
|
31
|
+
children: c.map((e) => /* @__PURE__ */ r(
|
|
32
32
|
h,
|
|
33
33
|
{
|
|
34
|
-
value:
|
|
34
|
+
value: v[e],
|
|
35
35
|
label: s[e],
|
|
36
36
|
children: s[e]
|
|
37
37
|
},
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"string_field_filter.js","sources":["../../../../src/components/table_filter_panel/field_filters/string_field_filter.tsx"],"sourcesContent":["import { useSignalValue } from '@tcn/state';\nimport { Input, Option, Select,
|
|
1
|
+
{"version":3,"file":"string_field_filter.js","sources":["../../../../src/components/table_filter_panel/field_filters/string_field_filter.tsx"],"sourcesContent":["import { useSignalValue } from '@tcn/state';\nimport { Input, Option, Select, ControlSet } from '@tcn/ui/inputs';\nimport { FieldFilterProps } from './field_filter_props.js';\nimport { StringFieldFilterPresenter } from './string_field_filter_presenter.js';\nimport { ComparisonOperator } from '../types.js';\n\nimport { useFieldFilterStrategy } from './use_field_filter_strategy.js';\nimport { ClearableField } from './clearable_field.js';\n\nconst allOperators: ('is' | 'isNot' | 'has')[] = ['is', 'isNot', 'has'];\nconst operatorSymbols: Record<'is' | 'isNot' | 'has', string> = {\n is: '=',\n isNot: '!=',\n has: ':',\n};\nconst operatorLabels: Record<'is' | 'isNot' | 'has', string> = {\n is: 'is',\n isNot: 'is not',\n has: 'has',\n};\n\nexport function StringFieldFilter({ fieldName, label, operators }: FieldFilterProps) {\n const presenter = useFieldFilterStrategy(StringFieldFilterPresenter, fieldName);\n\n const value = useSignalValue(presenter.broadcasts.value);\n const operator = useSignalValue(presenter.broadcasts.operator);\n\n const availableOperators = operators || allOperators;\n\n return (\n <ClearableField\n label={label}\n onClear={() => presenter.setValue(null)}\n isClearable={value == null}\n >\n <ControlSet>\n <Select\n value={operator}\n onChange={value => presenter.setOperator(value as ComparisonOperator)}\n width=\"65px\"\n >\n {availableOperators.map(operator => (\n <Option\n key={operator}\n value={operatorSymbols[operator]}\n label={operatorLabels[operator]}\n >\n {operatorLabels[operator]}\n </Option>\n ))}\n </Select>\n <Input\n type=\"text\"\n value={value ?? ''}\n onChange={value => presenter.setValue(value)}\n />\n </ControlSet>\n </ClearableField>\n );\n}\n"],"names":["allOperators","operatorSymbols","operatorLabels","StringFieldFilter","fieldName","label","operators","presenter","useFieldFilterStrategy","StringFieldFilterPresenter","value","useSignalValue","operator","availableOperators","jsx","ClearableField","ControlSet","Select","Option","Input"],"mappings":";;;;;;AASA,MAAMA,IAA2C,CAAC,MAAM,SAAS,KAAK,GAChEC,IAA0D;AAAA,EAC9D,IAAI;AAAA,EACJ,OAAO;AAAA,EACP,KAAK;AACP,GACMC,IAAyD;AAAA,EAC7D,IAAI;AAAA,EACJ,OAAO;AAAA,EACP,KAAK;AACP;AAEO,SAASC,EAAkB,EAAE,WAAAC,GAAW,OAAAC,GAAO,WAAAC,KAA+B;AACnF,QAAMC,IAAYC,EAAuBC,GAA4BL,CAAS,GAExEM,IAAQC,EAAeJ,EAAU,WAAW,KAAK,GACjDK,IAAWD,EAAeJ,EAAU,WAAW,QAAQ,GAEvDM,IAAqBP,KAAaN;AAExC,SACE,gBAAAc;AAAA,IAACC;AAAA,IAAA;AAAA,MACC,OAAAV;AAAA,MACA,SAAS,MAAME,EAAU,SAAS,IAAI;AAAA,MACtC,aAAaG,KAAS;AAAA,MAEtB,4BAACM,GAAA,EACC,UAAA;AAAA,QAAA,gBAAAF;AAAA,UAACG;AAAA,UAAA;AAAA,YACC,OAAOL;AAAA,YACP,UAAU,CAAAF,MAASH,EAAU,YAAYG,CAA2B;AAAA,YACpE,OAAM;AAAA,YAEL,UAAAG,EAAmB,IAAI,CAAAD,MACtB,gBAAAE;AAAA,cAACI;AAAA,cAAA;AAAA,gBAEC,OAAOjB,EAAgBW,CAAQ;AAAA,gBAC/B,OAAOV,EAAeU,CAAQ;AAAA,gBAE7B,YAAeA,CAAQ;AAAA,cAAA;AAAA,cAJnBA;AAAAA,YAAA,CAMR;AAAA,UAAA;AAAA,QAAA;AAAA,QAEH,gBAAAE;AAAA,UAACK;AAAA,UAAA;AAAA,YACC,MAAK;AAAA,YACL,OAAOT,KAAS;AAAA,YAChB,UAAU,CAAAA,MAASH,EAAU,SAASG,CAAK;AAAA,UAAA;AAAA,QAAA;AAAA,MAC7C,EAAA,CACF;AAAA,IAAA;AAAA,EAAA;AAGN;"}
|
|
@@ -7,7 +7,8 @@ export interface TableFilterPanelProps extends Omit<PanelProps, 'children'> {
|
|
|
7
7
|
children: ReactElement<FieldFilterProps>[] | ReactElement<FieldFilterProps>;
|
|
8
8
|
dataSource: DataSource<any>;
|
|
9
9
|
onClose?: () => void;
|
|
10
|
+
title?: string;
|
|
10
11
|
}
|
|
11
|
-
export declare function TableFilterPanel({ children, dataSource, className, onClose, ...props }: TableFilterPanelProps): import("react/jsx-runtime").JSX.Element;
|
|
12
|
+
export declare function TableFilterPanel({ children, dataSource, className, onClose, title, ...props }: TableFilterPanelProps): import("react/jsx-runtime").JSX.Element;
|
|
12
13
|
export declare const TableFilterPanelContext: import('react').Context<TableFilterPanelPresenter<unknown> | null>;
|
|
13
14
|
//# sourceMappingURL=table_filter_panel.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"table_filter_panel.d.ts","sourceRoot":"","sources":["../../../src/components/table_filter_panel/table_filter_panel.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AACjD,OAAO,EAAE,YAAY,EAA2B,MAAM,OAAO,CAAC;AAC9D,OAAO,EAAE,gBAAgB,EAAE,MAAM,uCAAuC,CAAC;AACzE,OAAO,EAAE,yBAAyB,EAAE,MAAM,mCAAmC,CAAC;AAC9E,OAAO,EAAS,KAAK,UAAU,EAAE,MAAM,kBAAkB,CAAC;
|
|
1
|
+
{"version":3,"file":"table_filter_panel.d.ts","sourceRoot":"","sources":["../../../src/components/table_filter_panel/table_filter_panel.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AACjD,OAAO,EAAE,YAAY,EAA2B,MAAM,OAAO,CAAC;AAC9D,OAAO,EAAE,gBAAgB,EAAE,MAAM,uCAAuC,CAAC;AACzE,OAAO,EAAE,yBAAyB,EAAE,MAAM,mCAAmC,CAAC;AAC9E,OAAO,EAAS,KAAK,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAQ1D,MAAM,WAAW,qBAAsB,SAAQ,IAAI,CAAC,UAAU,EAAE,UAAU,CAAC;IACzE,QAAQ,EAAE,YAAY,CAAC,gBAAgB,CAAC,EAAE,GAAG,YAAY,CAAC,gBAAgB,CAAC,CAAC;IAC5E,UAAU,EAAE,UAAU,CAAC,GAAG,CAAC,CAAC;IAC5B,OAAO,CAAC,EAAE,MAAM,IAAI,CAAC;IACrB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,wBAAgB,gBAAgB,CAAC,EAC/B,QAAQ,EACR,UAAU,EACV,SAAS,EACT,OAAO,EACP,KAAuB,EACvB,GAAG,KAAK,EACT,EAAE,qBAAqB,2CA+BvB;AAED,eAAO,MAAM,uBAAuB,oEAEnC,CAAC"}
|
|
@@ -1,53 +1,48 @@
|
|
|
1
|
-
import { jsx as e, jsxs as
|
|
2
|
-
import { createContext as
|
|
3
|
-
import { TableFilterPanelPresenter as
|
|
4
|
-
import {
|
|
5
|
-
import { Header as
|
|
6
|
-
import { Spacer as
|
|
7
|
-
import { Button as
|
|
8
|
-
import { CrossIcon as
|
|
9
|
-
import
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
1
|
+
import { jsx as e, jsxs as l } from "react/jsx-runtime";
|
|
2
|
+
import { createContext as f, useState as b } from "react";
|
|
3
|
+
import { TableFilterPanelPresenter as m } from "./table_filter_panel_presenter.js";
|
|
4
|
+
import { Aside as p } from "@tcn/ui/surfaces";
|
|
5
|
+
import { Header as d, Body as y, Scaffold as h, Section as u } from "@tcn/ui/layouts";
|
|
6
|
+
import { Spacer as P } from "@tcn/ui/stacks";
|
|
7
|
+
import { Button as F } from "@tcn/ui/actions";
|
|
8
|
+
import { CrossIcon as x } from "@tcn/icons/cross_icon.js";
|
|
9
|
+
import { Title as S } from "@tcn/ui/typography";
|
|
10
|
+
import '../../table_filter_panel.css';const T = "_table-filter-panel-body_c016eb0", _ = "_table-filter-panel-section_cfd2eb9", r = { "table-filter-panel-body": T, "table-filter-panel-section": _ };
|
|
11
|
+
function I({
|
|
12
|
+
children: n,
|
|
13
|
+
dataSource: i,
|
|
14
|
+
className: a,
|
|
15
|
+
onClose: t,
|
|
16
|
+
title: o = "Table Filters",
|
|
17
|
+
...c
|
|
16
18
|
}) {
|
|
17
|
-
const [
|
|
18
|
-
return /* @__PURE__ */ e(
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
d,
|
|
19
|
+
const [s] = b(() => new m(i));
|
|
20
|
+
return /* @__PURE__ */ e(B.Provider, { value: s, children: /* @__PURE__ */ l(p, { className: `tcn-table-filter-panel ${a}`, ...c, children: [
|
|
21
|
+
/* @__PURE__ */ l(d, { children: [
|
|
22
|
+
/* @__PURE__ */ e(S, { children: o }),
|
|
23
|
+
/* @__PURE__ */ e(P, {}),
|
|
24
|
+
t && /* @__PURE__ */ e(F, { utility: !0, hierarchy: "tertiary", onClick: t, children: /* @__PURE__ */ e(x, {}) })
|
|
25
|
+
] }),
|
|
26
|
+
/* @__PURE__ */ e(
|
|
27
|
+
y,
|
|
28
|
+
{
|
|
29
|
+
className: `${r["table-filter-panel-body"]} tcn-table-filter-panel-body`,
|
|
30
|
+
children: /* @__PURE__ */ e(h, { children: /* @__PURE__ */ e(
|
|
31
|
+
u,
|
|
31
32
|
{
|
|
32
|
-
className: `${
|
|
33
|
-
children:
|
|
34
|
-
y,
|
|
35
|
-
{
|
|
36
|
-
className: `${t["table-filter-panel-section"]} tcn-table-filter-panel-section`,
|
|
37
|
-
children: a
|
|
38
|
-
}
|
|
39
|
-
)
|
|
33
|
+
className: `${r["table-filter-panel-section"]} tcn-table-filter-panel-section`,
|
|
34
|
+
children: n
|
|
40
35
|
}
|
|
41
|
-
)
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
) });
|
|
36
|
+
) })
|
|
37
|
+
}
|
|
38
|
+
)
|
|
39
|
+
] }) });
|
|
45
40
|
}
|
|
46
|
-
const
|
|
41
|
+
const B = f(
|
|
47
42
|
null
|
|
48
43
|
);
|
|
49
44
|
export {
|
|
50
|
-
|
|
51
|
-
|
|
45
|
+
I as TableFilterPanel,
|
|
46
|
+
B as TableFilterPanelContext
|
|
52
47
|
};
|
|
53
48
|
//# sourceMappingURL=table_filter_panel.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"table_filter_panel.js","sources":["../../../src/components/table_filter_panel/table_filter_panel.tsx"],"sourcesContent":["import { DataSource } from '@tcn/resource-store';\nimport { ReactElement, useState, createContext } from 'react';\nimport { FieldFilterProps } from './field_filters/field_filter_props.js';\nimport { TableFilterPanelPresenter } from './table_filter_panel_presenter.js';\nimport {
|
|
1
|
+
{"version":3,"file":"table_filter_panel.js","sources":["../../../src/components/table_filter_panel/table_filter_panel.tsx"],"sourcesContent":["import { DataSource } from '@tcn/resource-store';\nimport { ReactElement, useState, createContext } from 'react';\nimport { FieldFilterProps } from './field_filters/field_filter_props.js';\nimport { TableFilterPanelPresenter } from './table_filter_panel_presenter.js';\nimport { Aside, type PanelProps } from '@tcn/ui/surfaces';\nimport { Body, Header, Scaffold, Section } from '@tcn/ui/layouts';\nimport styles from './table_filter_panel.module.css';\nimport { Spacer } from '@tcn/ui/stacks';\nimport { Button } from '@tcn/ui/actions';\nimport { CrossIcon } from '@tcn/icons/cross_icon.js';\nimport { Title } from '@tcn/ui/typography';\n\nexport interface TableFilterPanelProps extends Omit<PanelProps, 'children'> {\n children: ReactElement<FieldFilterProps>[] | ReactElement<FieldFilterProps>;\n dataSource: DataSource<any>;\n onClose?: () => void;\n title?: string;\n}\n\nexport function TableFilterPanel({\n children,\n dataSource,\n className,\n onClose,\n title = 'Table Filters',\n ...props\n}: TableFilterPanelProps) {\n const [presenter] = useState(() => {\n return new TableFilterPanelPresenter(dataSource);\n });\n\n return (\n <TableFilterPanelContext.Provider value={presenter}>\n <Aside className={`tcn-table-filter-panel ${className}`} {...props}>\n <Header>\n <Title>{title}</Title>\n <Spacer />\n {onClose && (\n <Button utility hierarchy=\"tertiary\" onClick={onClose}>\n <CrossIcon />\n </Button>\n )}\n </Header>\n <Body\n className={`${styles['table-filter-panel-body']} tcn-table-filter-panel-body`}\n >\n <Scaffold>\n <Section\n className={`${styles['table-filter-panel-section']} tcn-table-filter-panel-section`}\n >\n {children}\n </Section>\n </Scaffold>\n </Body>\n </Aside>\n </TableFilterPanelContext.Provider>\n );\n}\n\nexport const TableFilterPanelContext = createContext<TableFilterPanelPresenter | null>(\n null\n);\n"],"names":["TableFilterPanel","children","dataSource","className","onClose","title","props","presenter","useState","TableFilterPanelPresenter","jsx","TableFilterPanelContext","jsxs","Aside","Header","Title","Spacer","Button","CrossIcon","Body","styles","Scaffold","Section","createContext"],"mappings":";;;;;;;;;;AAmBO,SAASA,EAAiB;AAAA,EAC/B,UAAAC;AAAA,EACA,YAAAC;AAAA,EACA,WAAAC;AAAA,EACA,SAAAC;AAAA,EACA,OAAAC,IAAQ;AAAA,EACR,GAAGC;AACL,GAA0B;AACxB,QAAM,CAACC,CAAS,IAAIC,EAAS,MACpB,IAAIC,EAA0BP,CAAU,CAChD;AAED,SACE,gBAAAQ,EAACC,EAAwB,UAAxB,EAAiC,OAAOJ,GACvC,UAAA,gBAAAK,EAACC,GAAA,EAAM,WAAW,0BAA0BV,CAAS,IAAK,GAAGG,GAC3D,UAAA;AAAA,IAAA,gBAAAM,EAACE,GAAA,EACC,UAAA;AAAA,MAAA,gBAAAJ,EAACK,KAAO,UAAAV,EAAA,CAAM;AAAA,wBACbW,GAAA,EAAO;AAAA,MACPZ,KACC,gBAAAM,EAACO,GAAA,EAAO,SAAO,IAAC,WAAU,YAAW,SAASb,GAC5C,UAAA,gBAAAM,EAACQ,GAAA,CAAA,CAAU,EAAA,CACb;AAAA,IAAA,GAEJ;AAAA,IACA,gBAAAR;AAAA,MAACS;AAAA,MAAA;AAAA,QACC,WAAW,GAAGC,EAAO,yBAAyB,CAAC;AAAA,QAE/C,4BAACC,GAAA,EACC,UAAA,gBAAAX;AAAA,UAACY;AAAA,UAAA;AAAA,YACC,WAAW,GAAGF,EAAO,4BAA4B,CAAC;AAAA,YAEjD,UAAAnB;AAAA,UAAA;AAAA,QAAA,EACH,CACF;AAAA,MAAA;AAAA,IAAA;AAAA,EACF,EAAA,CACF,EAAA,CACF;AAEJ;AAEO,MAAMU,IAA0BY;AAAA,EACrC;AACF;"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
._table-filter-
|
|
1
|
+
._table-filter-panel-body_c016eb0{padding-block:8px}._table-filter-panel-body_c016eb0 ._table-filter-panel-section_cfd2eb9{gap:8px}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@tcn/ui-table",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.4.0",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "React table component library",
|
|
6
6
|
"author": "TCN",
|
|
@@ -41,9 +41,9 @@
|
|
|
41
41
|
"clarity-pattern-parser": "^11.5.4",
|
|
42
42
|
"@tcn/aip-160": "1.2.5",
|
|
43
43
|
"@tcn/icons": "2.3.0",
|
|
44
|
-
"@tcn/resource-store": "2.5.
|
|
45
|
-
"@tcn/
|
|
46
|
-
"@tcn/
|
|
44
|
+
"@tcn/resource-store": "2.5.6",
|
|
45
|
+
"@tcn/state": "1.3.2",
|
|
46
|
+
"@tcn/ui": "0.13.0"
|
|
47
47
|
},
|
|
48
48
|
"peerDependencies": {
|
|
49
49
|
"react": "^18.2.0",
|
|
@@ -10,7 +10,7 @@ import {
|
|
|
10
10
|
} from '@tcn/resource-store';
|
|
11
11
|
import { useSignalValue } from '@tcn/state';
|
|
12
12
|
import { Button } from '@tcn/ui/actions';
|
|
13
|
-
import { Footer, Header,
|
|
13
|
+
import { Footer, Header, Rail, Side, Body } from '@tcn/ui/layouts';
|
|
14
14
|
import { Box, HStack, Spacer, VStack, ZStack } from '@tcn/ui/stacks';
|
|
15
15
|
import { Panel } from '@tcn/ui/surfaces';
|
|
16
16
|
import { Title } from '@tcn/ui/typography';
|
|
@@ -308,7 +308,7 @@ export function WithTableHeaderAndTableFooter() {
|
|
|
308
308
|
<Spacer />
|
|
309
309
|
<GlobalSearch dataSource={source} />
|
|
310
310
|
</Header>
|
|
311
|
-
<
|
|
311
|
+
<Body height="flex">
|
|
312
312
|
<Table
|
|
313
313
|
dataSource={source}
|
|
314
314
|
onRowClick={item => {
|
|
@@ -323,7 +323,7 @@ export function WithTableHeaderAndTableFooter() {
|
|
|
323
323
|
<TableColumn heading="Occupation" fieldName="occupation" />
|
|
324
324
|
<TableColumn heading="Active" fieldName="isActive" />
|
|
325
325
|
</Table>
|
|
326
|
-
</
|
|
326
|
+
</Body>
|
|
327
327
|
<Footer>
|
|
328
328
|
<TablePager dataSource={source} />
|
|
329
329
|
</Footer>
|
|
@@ -411,21 +411,14 @@ export function WithFilterPanel() {
|
|
|
411
411
|
<StoryWrapper>
|
|
412
412
|
<Panel height="100%">
|
|
413
413
|
<Header>The Table</Header>
|
|
414
|
-
<
|
|
414
|
+
<Body>
|
|
415
415
|
<Rail>
|
|
416
|
+
{/* TODO: Refactor to remove duplicate column logic (outer Side and inner Aside - in TableFilterPanel ) */}
|
|
416
417
|
<Side padding="0px">
|
|
417
|
-
<Box
|
|
418
|
-
minWidth="300px"
|
|
419
|
-
enableResizeOnEnd
|
|
420
|
-
overflowY="auto"
|
|
421
|
-
height="100%"
|
|
422
|
-
style={{
|
|
423
|
-
scrollbarGutter: 'stable', // Not sure if there is a better way to prevent the scrollbar appearing causing a horizontal scroll - to to resizing, we fix the width of the content, so adding a vertical scrollbar causing a horizontal overflow.
|
|
424
|
-
}}
|
|
425
|
-
>
|
|
418
|
+
<Box minWidth="300px" enableResizeOnEnd height="100%" maxHeight="100%">
|
|
426
419
|
<TableFilterPanel
|
|
427
420
|
dataSource={source}
|
|
428
|
-
onClose={() => window.alert('
|
|
421
|
+
onClose={() => window.alert('onClose callback called.')}
|
|
429
422
|
>
|
|
430
423
|
<StringFieldFilter fieldName="name" label="Name (string)" />
|
|
431
424
|
<NumberFieldFilter fieldName="age" label="Age (number)" />
|
|
@@ -434,8 +427,8 @@ export function WithFilterPanel() {
|
|
|
434
427
|
</TableFilterPanel>
|
|
435
428
|
</Box>
|
|
436
429
|
</Side>
|
|
437
|
-
<
|
|
438
|
-
<Table dataSource={source} height="100%"
|
|
430
|
+
<Body>
|
|
431
|
+
<Table dataSource={source} height="100%">
|
|
439
432
|
<TableColumn heading="Name" fieldName="name" sticky="start" />
|
|
440
433
|
<TableColumn heading="Age" fieldName="age" width={150} canSort />
|
|
441
434
|
<TableColumn heading="Email" fieldName="email" width={300} />
|
|
@@ -449,9 +442,9 @@ export function WithFilterPanel() {
|
|
|
449
442
|
<TableColumn heading="Occupation" fieldName="occupation" width={200} />
|
|
450
443
|
<TableColumn heading="Active" fieldName="isActive" />
|
|
451
444
|
</Table>
|
|
452
|
-
</
|
|
445
|
+
</Body>
|
|
453
446
|
</Rail>
|
|
454
|
-
</
|
|
447
|
+
</Body>
|
|
455
448
|
<Footer>
|
|
456
449
|
<TablePager dataSource={source} />
|
|
457
450
|
</Footer>
|
|
@@ -42,9 +42,10 @@ export function HeaderCell({
|
|
|
42
42
|
padding="0px 8px" // FIXME: should be on theme ideally.
|
|
43
43
|
overflow="hidden"
|
|
44
44
|
minWidth="24px"
|
|
45
|
+
maxWidth="unset"
|
|
46
|
+
width={width}
|
|
45
47
|
enableResizeOnEnd
|
|
46
48
|
onWidthResize={handleResize}
|
|
47
|
-
style={{ width: `${width}px`, minWidth: '20px' }}
|
|
48
49
|
onClick={e => e.stopPropagation()}
|
|
49
50
|
>
|
|
50
51
|
<HStack>
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { useSignalValue } from '@tcn/state';
|
|
2
|
-
import { Input, Option, Select,
|
|
2
|
+
import { Input, Option, Select, ControlSet } from '@tcn/ui/inputs';
|
|
3
3
|
import { FieldFilterProps } from './field_filter_props.js';
|
|
4
4
|
import { NumberFieldFilterPresenter } from './number_field_filter_presenter.js';
|
|
5
5
|
import { useFieldFilterStrategy } from './use_field_filter_strategy.js';
|
|
@@ -20,7 +20,7 @@ export function NumberFieldFilter({ fieldName, label }: FieldFilterProps) {
|
|
|
20
20
|
onClear={() => presenter.setValue(null)}
|
|
21
21
|
isClearable={value == null}
|
|
22
22
|
>
|
|
23
|
-
<
|
|
23
|
+
<ControlSet>
|
|
24
24
|
<Select
|
|
25
25
|
value={operator}
|
|
26
26
|
onChange={value => presenter.setOperator(value as ComparisonOperator)}
|
|
@@ -37,7 +37,7 @@ export function NumberFieldFilter({ fieldName, label }: FieldFilterProps) {
|
|
|
37
37
|
value={String(value ?? '')}
|
|
38
38
|
onChange={value => presenter.setValue(Number(value))}
|
|
39
39
|
/>
|
|
40
|
-
</
|
|
40
|
+
</ControlSet>
|
|
41
41
|
</ClearableField>
|
|
42
42
|
);
|
|
43
43
|
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { useSignalValue } from '@tcn/state';
|
|
2
|
-
import { Input, Option, Select,
|
|
2
|
+
import { Input, Option, Select, ControlSet } from '@tcn/ui/inputs';
|
|
3
3
|
import { FieldFilterProps } from './field_filter_props.js';
|
|
4
4
|
import { StringFieldFilterPresenter } from './string_field_filter_presenter.js';
|
|
5
5
|
import { ComparisonOperator } from '../types.js';
|
|
@@ -33,7 +33,7 @@ export function StringFieldFilter({ fieldName, label, operators }: FieldFilterPr
|
|
|
33
33
|
onClear={() => presenter.setValue(null)}
|
|
34
34
|
isClearable={value == null}
|
|
35
35
|
>
|
|
36
|
-
<
|
|
36
|
+
<ControlSet>
|
|
37
37
|
<Select
|
|
38
38
|
value={operator}
|
|
39
39
|
onChange={value => presenter.setOperator(value as ComparisonOperator)}
|
|
@@ -54,7 +54,7 @@ export function StringFieldFilter({ fieldName, label, operators }: FieldFilterPr
|
|
|
54
54
|
value={value ?? ''}
|
|
55
55
|
onChange={value => presenter.setValue(value)}
|
|
56
56
|
/>
|
|
57
|
-
</
|
|
57
|
+
</ControlSet>
|
|
58
58
|
</ClearableField>
|
|
59
59
|
);
|
|
60
60
|
}
|
|
@@ -3,10 +3,11 @@ import {
|
|
|
3
3
|
StaticNumberField,
|
|
4
4
|
StaticStringField,
|
|
5
5
|
} from '@tcn/resource-store';
|
|
6
|
-
import
|
|
6
|
+
import { useState } from 'react';
|
|
7
7
|
import { items } from '../../__stories__/sample_data.js';
|
|
8
8
|
import { NumberFieldFilter } from './field_filters/number_field_filter.js';
|
|
9
9
|
import { TableFilterPanel } from './table_filter_panel.js';
|
|
10
|
+
import { VStack } from '@tcn/ui/stacks';
|
|
10
11
|
|
|
11
12
|
type DataItem = {
|
|
12
13
|
id: string;
|
|
@@ -37,10 +38,10 @@ export const Demo = () => {
|
|
|
37
38
|
});
|
|
38
39
|
|
|
39
40
|
return (
|
|
40
|
-
<
|
|
41
|
+
<VStack width="300px" height="100%">
|
|
41
42
|
<TableFilterPanel dataSource={source}>
|
|
42
43
|
<NumberFieldFilter fieldName="age" label="Age" />
|
|
43
44
|
</TableFilterPanel>
|
|
44
|
-
</
|
|
45
|
+
</VStack>
|
|
45
46
|
);
|
|
46
47
|
};
|
|
@@ -2,17 +2,19 @@ import { DataSource } from '@tcn/resource-store';
|
|
|
2
2
|
import { ReactElement, useState, createContext } from 'react';
|
|
3
3
|
import { FieldFilterProps } from './field_filters/field_filter_props.js';
|
|
4
4
|
import { TableFilterPanelPresenter } from './table_filter_panel_presenter.js';
|
|
5
|
-
import {
|
|
6
|
-
import { Header,
|
|
5
|
+
import { Aside, type PanelProps } from '@tcn/ui/surfaces';
|
|
6
|
+
import { Body, Header, Scaffold, Section } from '@tcn/ui/layouts';
|
|
7
7
|
import styles from './table_filter_panel.module.css';
|
|
8
8
|
import { Spacer } from '@tcn/ui/stacks';
|
|
9
9
|
import { Button } from '@tcn/ui/actions';
|
|
10
10
|
import { CrossIcon } from '@tcn/icons/cross_icon.js';
|
|
11
|
+
import { Title } from '@tcn/ui/typography';
|
|
11
12
|
|
|
12
13
|
export interface TableFilterPanelProps extends Omit<PanelProps, 'children'> {
|
|
13
14
|
children: ReactElement<FieldFilterProps>[] | ReactElement<FieldFilterProps>;
|
|
14
15
|
dataSource: DataSource<any>;
|
|
15
16
|
onClose?: () => void;
|
|
17
|
+
title?: string;
|
|
16
18
|
}
|
|
17
19
|
|
|
18
20
|
export function TableFilterPanel({
|
|
@@ -20,6 +22,7 @@ export function TableFilterPanel({
|
|
|
20
22
|
dataSource,
|
|
21
23
|
className,
|
|
22
24
|
onClose,
|
|
25
|
+
title = 'Table Filters',
|
|
23
26
|
...props
|
|
24
27
|
}: TableFilterPanelProps) {
|
|
25
28
|
const [presenter] = useState(() => {
|
|
@@ -28,12 +31,9 @@ export function TableFilterPanel({
|
|
|
28
31
|
|
|
29
32
|
return (
|
|
30
33
|
<TableFilterPanelContext.Provider value={presenter}>
|
|
31
|
-
<
|
|
32
|
-
className={`${styles['table-filter-panel']} tcn-table-filter-panel ${className}`}
|
|
33
|
-
{...props}
|
|
34
|
-
>
|
|
34
|
+
<Aside className={`tcn-table-filter-panel ${className}`} {...props}>
|
|
35
35
|
<Header>
|
|
36
|
-
|
|
36
|
+
<Title>{title}</Title>
|
|
37
37
|
<Spacer />
|
|
38
38
|
{onClose && (
|
|
39
39
|
<Button utility hierarchy="tertiary" onClick={onClose}>
|
|
@@ -41,16 +41,18 @@ export function TableFilterPanel({
|
|
|
41
41
|
</Button>
|
|
42
42
|
)}
|
|
43
43
|
</Header>
|
|
44
|
-
<
|
|
44
|
+
<Body
|
|
45
45
|
className={`${styles['table-filter-panel-body']} tcn-table-filter-panel-body`}
|
|
46
46
|
>
|
|
47
|
-
<
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
47
|
+
<Scaffold>
|
|
48
|
+
<Section
|
|
49
|
+
className={`${styles['table-filter-panel-section']} tcn-table-filter-panel-section`}
|
|
50
|
+
>
|
|
51
|
+
{children}
|
|
52
|
+
</Section>
|
|
53
|
+
</Scaffold>
|
|
54
|
+
</Body>
|
|
55
|
+
</Aside>
|
|
54
56
|
</TableFilterPanelContext.Provider>
|
|
55
57
|
);
|
|
56
58
|
}
|