playbook_ui 14.5.0.pre.alpha.javascriptassets3939 → 14.5.0.pre.alpha.20241007playbookwebsiteaddrdbms4036
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/app/pb_kits/playbook/pb_enhanced_element/{element_observer.js → element_observer.ts} +27 -19
- data/app/pb_kits/playbook/pb_enhanced_element/{index.js → index.ts} +22 -15
- data/app/pb_kits/playbook/pb_form_pill/_form_pill.tsx +9 -1
- data/app/pb_kits/playbook/pb_form_pill/docs/_form_pill_truncated_text.html.erb +19 -0
- data/app/pb_kits/playbook/pb_form_pill/docs/_form_pill_truncated_text.jsx +27 -0
- data/app/pb_kits/playbook/pb_form_pill/docs/_form_pill_truncated_text.md +1 -0
- data/app/pb_kits/playbook/pb_form_pill/docs/example.yml +2 -0
- data/app/pb_kits/playbook/pb_form_pill/docs/index.js +1 -0
- data/app/pb_kits/playbook/pb_multi_level_select/_multi_level_select.tsx +195 -228
- data/app/pb_kits/playbook/pb_multi_level_select/context/index.tsx +5 -0
- data/app/pb_kits/playbook/pb_multi_level_select/docs/_multi_level_select_default.jsx +1 -1
- data/app/pb_kits/playbook/pb_multi_level_select/docs/_multi_level_select_with_children.jsx +105 -0
- data/app/pb_kits/playbook/pb_multi_level_select/docs/_multi_level_select_with_children.md +1 -0
- data/app/pb_kits/playbook/pb_multi_level_select/docs/_multi_level_select_with_children_with_radios.jsx +106 -0
- data/app/pb_kits/playbook/pb_multi_level_select/docs/_multi_level_select_with_children_with_radios.md +1 -0
- data/app/pb_kits/playbook/pb_multi_level_select/docs/example.yml +3 -0
- data/app/pb_kits/playbook/pb_multi_level_select/docs/index.js +2 -0
- data/app/pb_kits/playbook/pb_multi_level_select/multi_level_select_options.tsx +149 -0
- data/app/pb_kits/playbook/pb_typeahead/_typeahead.tsx +4 -1
- data/app/pb_kits/playbook/pb_typeahead/components/MultiValue.tsx +3 -1
- data/app/pb_kits/playbook/pb_typeahead/typeahead.rb +3 -1
- data/dist/chunks/_typeahead-CT2ByCBK.js +22 -0
- data/dist/chunks/_weekday_stacked-Bwdy1TtH.js +45 -0
- data/dist/chunks/lib-CEpcaI8y.js +29 -0
- data/dist/chunks/{pb_form_validation-8H8TD40J.js → pb_form_validation-D9zkwt2b.js} +1 -1
- data/dist/chunks/vendor.js +1 -45
- data/dist/playbook-doc.js +1 -1
- data/dist/playbook-rails-react-bindings.js +1 -1
- data/dist/playbook-rails.js +1 -1
- data/lib/playbook/pb_doc_helper.rb +5 -5
- data/lib/playbook/version.rb +1 -1
- metadata +17 -11
- data/dist/chunks/_typeahead-DPGG9h5l.js +0 -65
- data/dist/chunks/index-CaXZ6mCT.js +0 -1
- data/dist/chunks/index-DfoYI7sS.js +0 -1
- data/dist/chunks/lib-ByFv-sq8.js +0 -45
- data/dist/mark.js +0 -1
- data/dist/playbook-rails-friendly.js +0 -1
@@ -0,0 +1,105 @@
|
|
1
|
+
import React from "react";
|
2
|
+
import MultiLevelSelect from "../_multi_level_select";
|
3
|
+
import Badge from "../../pb_badge/_badge";
|
4
|
+
|
5
|
+
const treeData = [
|
6
|
+
{
|
7
|
+
label: "Power Home Remodeling",
|
8
|
+
value: "Power Home Remodeling",
|
9
|
+
id: "powerhome1",
|
10
|
+
expanded: true,
|
11
|
+
children: [
|
12
|
+
{
|
13
|
+
label: "People",
|
14
|
+
value: "People",
|
15
|
+
id: "people1",
|
16
|
+
expanded: true,
|
17
|
+
status: "active",
|
18
|
+
children: [
|
19
|
+
{
|
20
|
+
label: "Talent Acquisition",
|
21
|
+
value: "Talent Acquisition",
|
22
|
+
id: "talent1",
|
23
|
+
},
|
24
|
+
{
|
25
|
+
label: "Business Affairs",
|
26
|
+
value: "Business Affairs",
|
27
|
+
id: "business1",
|
28
|
+
status: "active",
|
29
|
+
variant: "primary",
|
30
|
+
|
31
|
+
children: [
|
32
|
+
{
|
33
|
+
label: "Initiatives",
|
34
|
+
value: "Initiatives",
|
35
|
+
id: "initiative1",
|
36
|
+
},
|
37
|
+
{
|
38
|
+
label: "Learning & Development",
|
39
|
+
value: "Learning & Development",
|
40
|
+
id: "development1",
|
41
|
+
status: "Inactive",
|
42
|
+
},
|
43
|
+
],
|
44
|
+
},
|
45
|
+
{
|
46
|
+
label: "People Experience",
|
47
|
+
value: "People Experience",
|
48
|
+
id: "experience1",
|
49
|
+
},
|
50
|
+
],
|
51
|
+
},
|
52
|
+
{
|
53
|
+
label: "Contact Center",
|
54
|
+
value: "Contact Center",
|
55
|
+
id: "contact1",
|
56
|
+
status: "Inactive",
|
57
|
+
variant: "error",
|
58
|
+
children: [
|
59
|
+
{
|
60
|
+
label: "Appointment Management",
|
61
|
+
value: "Appointment Management",
|
62
|
+
id: "appointment1",
|
63
|
+
},
|
64
|
+
{
|
65
|
+
label: "Customer Service",
|
66
|
+
value: "Customer Service",
|
67
|
+
id: "customer1",
|
68
|
+
},
|
69
|
+
{
|
70
|
+
label: "Energy",
|
71
|
+
value: "Energy",
|
72
|
+
id: "energy1",
|
73
|
+
},
|
74
|
+
],
|
75
|
+
},
|
76
|
+
],
|
77
|
+
},
|
78
|
+
];
|
79
|
+
|
80
|
+
const MultiLevelSelectWithChildren = (props) => {
|
81
|
+
return (
|
82
|
+
<div>
|
83
|
+
<MultiLevelSelect
|
84
|
+
id="multiselect-with-children"
|
85
|
+
onSelect={(selectedNodes) =>
|
86
|
+
console.log("Selected Items", selectedNodes)
|
87
|
+
}
|
88
|
+
treeData={treeData}
|
89
|
+
{...props}
|
90
|
+
>
|
91
|
+
<MultiLevelSelect.Options>
|
92
|
+
{(item) => (
|
93
|
+
<Badge
|
94
|
+
marginLeft="sm"
|
95
|
+
text={item.status}
|
96
|
+
variant={item.status === "active" ? "success" : "warning"}
|
97
|
+
/>
|
98
|
+
)}
|
99
|
+
</MultiLevelSelect.Options>
|
100
|
+
</MultiLevelSelect>
|
101
|
+
</div>
|
102
|
+
);
|
103
|
+
};
|
104
|
+
|
105
|
+
export default MultiLevelSelectWithChildren;
|
@@ -0,0 +1 @@
|
|
1
|
+
The MultiLevelSelect also provides a subcomponent structure which can be used to render children to the right of the Checkboxes and their labels. As seen in the code snippet below, these children have access to the current item being iterated over which can be used for conditional rendering.
|
@@ -0,0 +1,106 @@
|
|
1
|
+
import React from "react";
|
2
|
+
import MultiLevelSelect from "../_multi_level_select";
|
3
|
+
import Badge from "../../pb_badge/_badge";
|
4
|
+
|
5
|
+
const treeData = [
|
6
|
+
{
|
7
|
+
label: "Power Home Remodeling",
|
8
|
+
value: "Power Home Remodeling",
|
9
|
+
id: "powerhome1",
|
10
|
+
expanded: true,
|
11
|
+
children: [
|
12
|
+
{
|
13
|
+
label: "People",
|
14
|
+
value: "People",
|
15
|
+
id: "people1",
|
16
|
+
expanded: true,
|
17
|
+
status: "active",
|
18
|
+
children: [
|
19
|
+
{
|
20
|
+
label: "Talent Acquisition",
|
21
|
+
value: "Talent Acquisition",
|
22
|
+
id: "talent1",
|
23
|
+
},
|
24
|
+
{
|
25
|
+
label: "Business Affairs",
|
26
|
+
value: "Business Affairs",
|
27
|
+
id: "business1",
|
28
|
+
status: "active",
|
29
|
+
variant: "primary",
|
30
|
+
|
31
|
+
children: [
|
32
|
+
{
|
33
|
+
label: "Initiatives",
|
34
|
+
value: "Initiatives",
|
35
|
+
id: "initiative1",
|
36
|
+
},
|
37
|
+
{
|
38
|
+
label: "Learning & Development",
|
39
|
+
value: "Learning & Development",
|
40
|
+
id: "development1",
|
41
|
+
status: "Inactive",
|
42
|
+
},
|
43
|
+
],
|
44
|
+
},
|
45
|
+
{
|
46
|
+
label: "People Experience",
|
47
|
+
value: "People Experience",
|
48
|
+
id: "experience1",
|
49
|
+
},
|
50
|
+
],
|
51
|
+
},
|
52
|
+
{
|
53
|
+
label: "Contact Center",
|
54
|
+
value: "Contact Center",
|
55
|
+
id: "contact1",
|
56
|
+
status: "Inactive",
|
57
|
+
variant: "error",
|
58
|
+
children: [
|
59
|
+
{
|
60
|
+
label: "Appointment Management",
|
61
|
+
value: "Appointment Management",
|
62
|
+
id: "appointment1",
|
63
|
+
},
|
64
|
+
{
|
65
|
+
label: "Customer Service",
|
66
|
+
value: "Customer Service",
|
67
|
+
id: "customer1",
|
68
|
+
},
|
69
|
+
{
|
70
|
+
label: "Energy",
|
71
|
+
value: "Energy",
|
72
|
+
id: "energy1",
|
73
|
+
},
|
74
|
+
],
|
75
|
+
},
|
76
|
+
],
|
77
|
+
},
|
78
|
+
];
|
79
|
+
|
80
|
+
const MultiLevelSelectWithChildrenWithRadios = (props) => {
|
81
|
+
return (
|
82
|
+
<div>
|
83
|
+
<MultiLevelSelect
|
84
|
+
id="multiselect-with-children"
|
85
|
+
onSelect={(selectedNodes) =>
|
86
|
+
console.log("Selected Items", selectedNodes)
|
87
|
+
}
|
88
|
+
treeData={treeData}
|
89
|
+
variant="single"
|
90
|
+
{...props}
|
91
|
+
>
|
92
|
+
<MultiLevelSelect.Options>
|
93
|
+
{(item) => (
|
94
|
+
<Badge
|
95
|
+
marginLeft="sm"
|
96
|
+
text={item.status}
|
97
|
+
variant={item.status === "active" ? "success" : "warning"}
|
98
|
+
/>
|
99
|
+
)}
|
100
|
+
</MultiLevelSelect.Options>
|
101
|
+
</MultiLevelSelect>
|
102
|
+
</div>
|
103
|
+
);
|
104
|
+
};
|
105
|
+
|
106
|
+
export default MultiLevelSelectWithChildrenWithRadios;
|
@@ -0,0 +1 @@
|
|
1
|
+
The MultiLevelSelect subcomponent structure is also available in the 'Single Select' variant. In this variant, the children will be rendered to the right of the Radios and their labels.
|
@@ -15,3 +15,6 @@ examples:
|
|
15
15
|
- multi_level_select_return_all_selected: Return All Selected
|
16
16
|
- multi_level_select_selected_ids_react: Selected Ids
|
17
17
|
- multi_level_select_color: With Pills (Custom Color)
|
18
|
+
- multi_level_select_with_children: Checkboxes With Children
|
19
|
+
- multi_level_select_with_children_with_radios: Single Select With Children
|
20
|
+
|
@@ -4,3 +4,5 @@ export { default as MultiLevelSelectSingleChildrenOnly } from './_multi_level_se
|
|
4
4
|
export { default as MultiLevelSelectReturnAllSelected } from './_multi_level_select_return_all_selected.jsx'
|
5
5
|
export { default as MultiLevelSelectSelectedIdsReact } from "./_multi_level_select_selected_ids_react.jsx"
|
6
6
|
export { default as MultiLevelSelectColor } from './_multi_level_select_color.jsx'
|
7
|
+
export { default as MultiLevelSelectWithChildren } from './_multi_level_select_with_children.jsx'
|
8
|
+
export { default as MultiLevelSelectWithChildrenWithRadios } from './_multi_level_select_with_children_with_radios.jsx'
|
@@ -0,0 +1,149 @@
|
|
1
|
+
import React, {useContext} from "react";
|
2
|
+
import classnames from "classnames";
|
3
|
+
import MultiLevelSelectContext from "./context";
|
4
|
+
import { globalProps, GlobalProps } from "../utilities/globalProps";
|
5
|
+
import {
|
6
|
+
buildAriaProps,
|
7
|
+
buildCss,
|
8
|
+
buildDataProps,
|
9
|
+
buildHtmlProps,
|
10
|
+
} from "../utilities/props";
|
11
|
+
import Checkbox from "../pb_checkbox/_checkbox";
|
12
|
+
import Radio from "../pb_radio/_radio";
|
13
|
+
import CircleIconButton from "../pb_circle_icon_button/_circle_icon_button";
|
14
|
+
import Body from "../pb_body/_body";
|
15
|
+
|
16
|
+
type MultiLevelSelectOptionsProps = {
|
17
|
+
aria?: { [key: string]: string },
|
18
|
+
children?: React.ReactNode | ((item: any) => React.ReactNode),
|
19
|
+
className?: string,
|
20
|
+
dark?: boolean,
|
21
|
+
data?: { [key: string]: string },
|
22
|
+
htmlOptions?: {[key: string]: string | number | boolean | (() => void)},
|
23
|
+
} & GlobalProps;
|
24
|
+
|
25
|
+
const MultiLevelSelectOptions = ({
|
26
|
+
children,
|
27
|
+
items,
|
28
|
+
...props
|
29
|
+
}: MultiLevelSelectOptionsProps) => {
|
30
|
+
const {
|
31
|
+
variant,
|
32
|
+
inputName,
|
33
|
+
renderNestedOptions,
|
34
|
+
isTreeRowExpanded,
|
35
|
+
handleToggleClick,
|
36
|
+
handleRadioButtonClick,
|
37
|
+
handledropdownItemClick,
|
38
|
+
filterItem,
|
39
|
+
} = useContext(MultiLevelSelectContext)
|
40
|
+
|
41
|
+
const {
|
42
|
+
aria = {},
|
43
|
+
className,
|
44
|
+
data = {},
|
45
|
+
htmlOptions = {},
|
46
|
+
} = props;
|
47
|
+
|
48
|
+
const ariaProps = buildAriaProps(aria);
|
49
|
+
const dataProps = buildDataProps(data);
|
50
|
+
const htmlProps = buildHtmlProps(htmlOptions);
|
51
|
+
const classes = classnames(
|
52
|
+
buildCss("pb_multi_level_select_options"),
|
53
|
+
globalProps(props),
|
54
|
+
className
|
55
|
+
);
|
56
|
+
|
57
|
+
return (
|
58
|
+
<ul
|
59
|
+
{...ariaProps}
|
60
|
+
{...dataProps}
|
61
|
+
{...htmlProps}
|
62
|
+
className={classes}
|
63
|
+
>
|
64
|
+
{Array.isArray(items) &&
|
65
|
+
items.map((item: { [key: string]: any }) => {
|
66
|
+
return (
|
67
|
+
<div key={item.id}>
|
68
|
+
<li className={"dropdown_item"}
|
69
|
+
data-name={item.id}
|
70
|
+
>
|
71
|
+
<div className="dropdown_item_checkbox_row">
|
72
|
+
{!item.parent_id && !item.children ? null : (
|
73
|
+
<div
|
74
|
+
key={
|
75
|
+
isTreeRowExpanded(item)
|
76
|
+
? "chevron-down"
|
77
|
+
: "chevron-right"
|
78
|
+
}
|
79
|
+
>
|
80
|
+
<CircleIconButton
|
81
|
+
className={
|
82
|
+
item.children && item.children.length > 0
|
83
|
+
? ""
|
84
|
+
: "toggle_icon"
|
85
|
+
}
|
86
|
+
icon={
|
87
|
+
isTreeRowExpanded(item)
|
88
|
+
? "chevron-down"
|
89
|
+
: "chevron-right"
|
90
|
+
}
|
91
|
+
onClick={(event: React.MouseEvent) =>
|
92
|
+
handleToggleClick(item.id, event)
|
93
|
+
}
|
94
|
+
variant="link"
|
95
|
+
/>
|
96
|
+
</div>
|
97
|
+
)}
|
98
|
+
{variant === "single" ? (
|
99
|
+
item.hideRadio ? (
|
100
|
+
<Body>{item.label}</Body>
|
101
|
+
) : (
|
102
|
+
<Radio
|
103
|
+
checked={item.checked}
|
104
|
+
id={`${item.id}-${item.label}`}
|
105
|
+
label={item.label}
|
106
|
+
name={inputName}
|
107
|
+
onChange={(e: React.ChangeEvent<HTMLInputElement>) =>
|
108
|
+
handleRadioButtonClick(e)
|
109
|
+
}
|
110
|
+
padding={item.children ? "none" : "xs"}
|
111
|
+
type="radio"
|
112
|
+
value={item.label}
|
113
|
+
/>
|
114
|
+
)
|
115
|
+
) : (
|
116
|
+
<Checkbox id={item.id}
|
117
|
+
text={item.label}
|
118
|
+
>
|
119
|
+
<input
|
120
|
+
checked={item.checked}
|
121
|
+
name={item.label}
|
122
|
+
onChange={(e) => {
|
123
|
+
handledropdownItemClick(e, !item.checked);
|
124
|
+
}}
|
125
|
+
type="checkbox"
|
126
|
+
value={item.label}
|
127
|
+
/>
|
128
|
+
</Checkbox>
|
129
|
+
)}
|
130
|
+
{/* Render children next to the checkbox */}
|
131
|
+
{children && (
|
132
|
+
typeof children === "function" ? children(item) : children
|
133
|
+
)}
|
134
|
+
</div>
|
135
|
+
{isTreeRowExpanded(item) &&
|
136
|
+
item.children &&
|
137
|
+
item.children.length > 0 &&
|
138
|
+
(variant === "single" || !filterItem) && (
|
139
|
+
<div>{renderNestedOptions(item.children)}</div>
|
140
|
+
)}
|
141
|
+
</li>
|
142
|
+
</div>
|
143
|
+
);
|
144
|
+
})}
|
145
|
+
</ul>
|
146
|
+
);
|
147
|
+
};
|
148
|
+
|
149
|
+
export default MultiLevelSelectOptions;
|
@@ -136,12 +136,15 @@ const Typeahead = ({
|
|
136
136
|
}
|
137
137
|
}
|
138
138
|
|
139
|
+
const filteredProps: TypeaheadProps = {...props}
|
140
|
+
delete filteredProps.truncate
|
141
|
+
|
139
142
|
const dataProps = buildDataProps(data)
|
140
143
|
const htmlProps = buildHtmlProps(htmlOptions)
|
141
144
|
const classes = classnames(
|
142
145
|
'pb_typeahead_kit react-select',
|
143
146
|
`mb_${marginBottom}`,
|
144
|
-
globalProps(
|
147
|
+
globalProps(filteredProps),
|
145
148
|
className
|
146
149
|
)
|
147
150
|
|
@@ -16,7 +16,7 @@ type Props = {
|
|
16
16
|
const MultiValue = (props: Props) => {
|
17
17
|
const { removeProps } = props
|
18
18
|
const { imageUrl, label } = props.data
|
19
|
-
const { dark, multiKit, pillColor } = props.selectProps
|
19
|
+
const { dark, multiKit, pillColor, truncate } = props.selectProps
|
20
20
|
|
21
21
|
const formPillProps = {
|
22
22
|
marginRight: 'xs',
|
@@ -51,6 +51,7 @@ const MultiValue = (props: Props) => {
|
|
51
51
|
name={label}
|
52
52
|
size={multiKit === 'smallPill' ? 'small' : ''}
|
53
53
|
text=''
|
54
|
+
truncate={truncate}
|
54
55
|
{...props}
|
55
56
|
/>
|
56
57
|
}
|
@@ -64,6 +65,7 @@ const MultiValue = (props: Props) => {
|
|
64
65
|
name=''
|
65
66
|
size={multiKit === 'smallPill' ? 'small' : ''}
|
66
67
|
text={label}
|
68
|
+
truncate={truncate}
|
67
69
|
{...props}
|
68
70
|
/>
|
69
71
|
}
|
@@ -65,10 +65,10 @@ module Playbook
|
|
65
65
|
def typeahead_react_options
|
66
66
|
base_options = {
|
67
67
|
className: classname,
|
68
|
-
pillColor: pill_color,
|
69
68
|
dark: dark,
|
70
69
|
defaultValue: default_options,
|
71
70
|
error: error,
|
71
|
+
htmlOptions: html_options,
|
72
72
|
id: id,
|
73
73
|
inline: inline,
|
74
74
|
isMulti: is_multi,
|
@@ -77,8 +77,10 @@ module Playbook
|
|
77
77
|
multiKit: multi_kit,
|
78
78
|
name: name,
|
79
79
|
options: options,
|
80
|
+
pillColor: pill_color,
|
80
81
|
placeholder: placeholder,
|
81
82
|
plusIcon: plus_icon,
|
83
|
+
truncate: truncate,
|
82
84
|
}
|
83
85
|
|
84
86
|
base_options[:getOptionLabel] = get_option_label if get_option_label.present?
|