playbook_ui 14.14.0.pre.alpha.play1852reacthookformsupportradio6318 → 14.14.0.pre.alpha.play1853typeaheadreacthookform6373

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 (31) hide show
  1. checksums.yaml +4 -4
  2. data/app/pb_kits/playbook/pb_currency/_currency.tsx +46 -31
  3. data/app/pb_kits/playbook/pb_currency/currency.html.erb +15 -8
  4. data/app/pb_kits/playbook/pb_currency/currency.rb +17 -2
  5. data/app/pb_kits/playbook/pb_currency/docs/_currency_null_display.html.erb +22 -0
  6. data/app/pb_kits/playbook/pb_currency/docs/_currency_null_display.jsx +34 -0
  7. data/app/pb_kits/playbook/pb_currency/docs/_currency_null_display_rails.md +1 -0
  8. data/app/pb_kits/playbook/pb_currency/docs/_currency_null_display_react.md +1 -0
  9. data/app/pb_kits/playbook/pb_currency/docs/example.yml +2 -0
  10. data/app/pb_kits/playbook/pb_currency/docs/index.js +2 -1
  11. data/app/pb_kits/playbook/pb_radio/_radio.tsx +74 -85
  12. data/app/pb_kits/playbook/pb_radio/docs/example.yml +1 -2
  13. data/app/pb_kits/playbook/pb_radio/docs/index.js +0 -1
  14. data/app/pb_kits/playbook/pb_radio/radio.test.js +0 -16
  15. data/app/pb_kits/playbook/pb_typeahead/_typeahead.tsx +9 -4
  16. data/app/pb_kits/playbook/pb_typeahead/docs/_typeahead_react_hook.jsx +66 -0
  17. data/app/pb_kits/playbook/pb_typeahead/docs/_typeahead_react_hook.md +1 -0
  18. data/app/pb_kits/playbook/pb_typeahead/docs/example.yml +1 -0
  19. data/app/pb_kits/playbook/pb_typeahead/docs/index.js +1 -0
  20. data/dist/chunks/_typeahead-B0mEqUUF.js +36 -0
  21. data/dist/chunks/_weekday_stacked-77oCRlb0.js +45 -0
  22. data/dist/chunks/vendor.js +1 -1
  23. data/dist/playbook-doc.js +1 -1
  24. data/dist/playbook-rails-react-bindings.js +1 -1
  25. data/dist/playbook-rails.js +1 -1
  26. data/lib/playbook/version.rb +1 -1
  27. metadata +10 -6
  28. data/app/pb_kits/playbook/pb_radio/docs/_radio_react_hook.jsx +0 -60
  29. data/app/pb_kits/playbook/pb_radio/docs/_radio_react_hook.md +0 -1
  30. data/dist/chunks/_typeahead-8okiJBmN.js +0 -36
  31. data/dist/chunks/_weekday_stacked-DrKLZrfR.js +0 -45
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: '08169588154946fcdb034524b646de6a050c504884a381f360f3a5470ea4917d'
4
- data.tar.gz: d2794398a68601eeac259328439846e39816d671489e70cf35c9e9cc3669b76e
3
+ metadata.gz: 22e1a85a49aae5e5698d7b36ac25dbc9ea32083afb4127898317d258a7423803
4
+ data.tar.gz: ebaf8cf1ec646ec276f040bf37e873b7650f40fe1e1d0726d365b0bb3ef55c0e
5
5
  SHA512:
6
- metadata.gz: ca7b5000b148f3a0e8beac0926d11b05e36b9cc32cef3ccd72b8c53e04a4bdb6822e957ac82c85d50910dd4240d165c912e2b4eeb09566c8dbae3b70b28320de
7
- data.tar.gz: fa1e9d28c2a166f674ac45c0c662262fb86fb69815409769be724bdba9a36b31bf24fe484053f17f97c691f9083759827b054f5a2a6652c7aab72bd8dc1c06f3
6
+ metadata.gz: 24a940d00c38dae7e50874252433c6571bcb6cc6d9b96f6258251180544834f59c499fecf2cfd63327e6d8442e31c4a9b606ba70bcc5187c1eb4afdeb630de84
7
+ data.tar.gz: a4b67e9a19b2941265e0921efa1ea9b43870296f43221ebce1259f33f42c31daec950cd01ba26bc7b698599f08a50176eba0a483b61e89bbaafa71ed51eaeac3
@@ -21,6 +21,7 @@ type CurrencyProps = {
21
21
  htmlOptions?: {[key: string]: string | number | boolean | (() => void)},
22
22
  id?: string,
23
23
  label?: string,
24
+ nullDisplay?: string,
24
25
  size?: 'sm' | 'md' | 'lg',
25
26
  symbol?: string,
26
27
  variant?: 'default' | 'light' | 'bold',
@@ -49,6 +50,7 @@ const Currency = (props: CurrencyProps): React.ReactElement => {
49
50
  unit,
50
51
  className,
51
52
  label = '',
53
+ nullDisplay = '',
52
54
  size = 'sm',
53
55
  symbol = '$',
54
56
  variant = 'default',
@@ -118,44 +120,57 @@ const Currency = (props: CurrencyProps): React.ReactElement => {
118
120
  id={id}
119
121
  >
120
122
  <Caption dark={dark}>{label}</Caption>
121
-
122
123
  <div className={`pb_currency_wrapper${variantClass || emphasizedClass}`}>
123
124
  {unstyled ? (
124
- <>
125
- <div>{handleNegative}{symbol}</div>
126
- <div>{getAmount}</div>
127
- <div>
128
- {getAbbreviation}
129
- {unit ? unit : getDecimalValue}
130
- </div>
131
- </>
125
+ nullDisplay && !amount ? (
126
+ <div>{nullDisplay}</div>
127
+ ) : (
128
+ <>
129
+ <div>{handleNegative}{symbol}</div>
130
+ <div>{getAmount}</div>
131
+ <div>
132
+ {getAbbreviation}
133
+ {unit ? unit : getDecimalValue}
134
+ </div>
135
+ </>
136
+ )
132
137
  ) : (
133
- <>
134
- <Body
135
- className="dollar_sign"
136
- color="light"
137
- dark={dark}
138
- >
139
- {handleNegative}{symbol}
140
- </Body>
141
-
138
+ nullDisplay && !amount ? (
142
139
  <Title
143
140
  className="pb_currency_value"
144
141
  dark={dark}
145
142
  size={sizes[size]}
146
- >
147
- {getAmount}
148
- </Title>
149
-
150
- <Body
151
- className="unit"
152
- color="light"
153
- dark={dark}
154
- >
155
- {getAbbreviation}
156
- {unit ? unit : getDecimalValue}
157
- </Body>
158
- </>
143
+ >
144
+ {nullDisplay}
145
+ </Title>
146
+ ) : (
147
+ <>
148
+ <Body
149
+ className="dollar_sign"
150
+ color="light"
151
+ dark={dark}
152
+ >
153
+ {handleNegative}{symbol}
154
+ </Body>
155
+
156
+ <Title
157
+ className="pb_currency_value"
158
+ dark={dark}
159
+ size={sizes[size]}
160
+ >
161
+ {getAmount}
162
+ </Title>
163
+
164
+ <Body
165
+ className="unit"
166
+ color="light"
167
+ dark={dark}
168
+ >
169
+ {getAbbreviation}
170
+ {unit ? unit : getDecimalValue}
171
+ </Body>
172
+ </>
173
+ )
159
174
  )}
160
175
  </div>
161
176
  </div>
@@ -1,17 +1,24 @@
1
1
  <%= pb_content_tag do %>
2
2
  <%= pb_rails("caption", props: object.caption_props) %>
3
-
4
3
  <div class=<%= "pb_currency_wrapper#{object.variant_class || object.emphasized_class}" %>>
5
4
  <% if object.unstyled %>
6
- <div><%= object.negative_sign %><%= object.symbol %></div>
7
- <div><%= object.title_props[:text] %></div>
8
- <div><%= object.body_props[:text] %></div>
5
+ <% if object.null_display && object.amount.blank? %>
6
+ <div><%= object.null_display %></div>
7
+ <% else %>
8
+ <div><%= object.negative_sign %><%= object.symbol %></div>
9
+ <div><%= object.title_props[:text] %></div>
10
+ <div><%= object.body_props[:text] %></div>
11
+ <% end %>
9
12
  <% else %>
10
- <%= pb_rails("body", props: object.currency_wrapper_props) do %>
11
- <%= object.negative_sign %><%= object.symbol %>
13
+ <% if object.null_display && object.amount.blank? %>
14
+ <%= pb_rails("title", props: object.title_props) %>
15
+ <% else %>
16
+ <%= pb_rails("body", props: object.currency_wrapper_props) do %>
17
+ <%= object.negative_sign %><%= object.symbol %>
18
+ <% end %>
19
+ <%= pb_rails("title", props: object.title_props) %>
20
+ <%= pb_rails("body", props: object.body_props) %>
12
21
  <% end %>
13
- <%= pb_rails("title", props: object.title_props) %>
14
- <%= pb_rails("body", props: object.body_props) %>
15
22
  <% end %>
16
23
  </div>
17
24
  <% end %>
@@ -46,6 +46,9 @@ module Playbook
46
46
  prop :comma_separator, type: Playbook::Props::Boolean,
47
47
  default: false
48
48
 
49
+ prop :null_display, type: Playbook::Props::String,
50
+ required: false
51
+
49
52
  def classname
50
53
  generate_classname("pb_currency_kit", align, size, dark_class)
51
54
  end
@@ -65,10 +68,20 @@ module Playbook
65
68
  }
66
69
  end
67
70
 
71
+ def title_text
72
+ if null_display
73
+ null_display
74
+ elsif swap_negative
75
+ absolute_amount(abbr_or_format_amount)
76
+ else
77
+ abbr_or_format_amount
78
+ end
79
+ end
80
+
68
81
  def title_props
69
82
  {
70
83
  size: size_value,
71
- text: swap_negative ? absolute_amount(abbr_or_format_amount) : abbr_or_format_amount,
84
+ text: title_text,
72
85
  classname: "pb_currency_value",
73
86
  dark: dark,
74
87
  }
@@ -145,8 +158,10 @@ module Playbook
145
158
  1
146
159
  when "md"
147
160
  3
148
- else
161
+ when "sm"
149
162
  4
163
+ else
164
+ 3
150
165
  end
151
166
  end
152
167
 
@@ -0,0 +1,22 @@
1
+ <%= pb_rails("currency", props: {
2
+ amount: "",
3
+ label: "Nil",
4
+ margin_bottom: "md",
5
+ null_display: "--",
6
+ size: "sm"
7
+ }) %>
8
+
9
+ <%= pb_rails("currency", props: {
10
+ amount: "",
11
+ label: "Nil",
12
+ margin_bottom: "md",
13
+ null_display: "$0.00",
14
+ size: "sm"
15
+ }) %>
16
+
17
+ <%= pb_rails("currency", props: {
18
+ amount: "",
19
+ label: "Nil",
20
+ null_display: " ",
21
+ size: "sm"
22
+ }) %>
@@ -0,0 +1,34 @@
1
+ import React from 'react'
2
+ import { Currency } from 'playbook-ui'
3
+
4
+ const CurrencyNullDisplay = (props) => {
5
+ return (
6
+ <>
7
+ <Currency
8
+ amount=""
9
+ label="Null"
10
+ marginBottom="md"
11
+ nullDisplay="--"
12
+ {...props}
13
+ />
14
+
15
+ <Currency
16
+ amount=""
17
+ label="Null"
18
+ marginBottom="md"
19
+ nullDisplay="$0.00"
20
+ {...props}
21
+ />
22
+
23
+ <Currency
24
+ amount=""
25
+ label="Null"
26
+ marginBottom="md"
27
+ nullDisplay=" "
28
+ {...props}
29
+ />
30
+ </>
31
+ )
32
+ }
33
+
34
+ export default CurrencyNullDisplay
@@ -0,0 +1 @@
1
+ To customize how the `amount` field appears when it is empty, use the `null_display` prop and set it to the desired value you want to display.
@@ -0,0 +1 @@
1
+ To customize how the `amount` field appears when it is empty, use the `nullDisplay` prop and set it to the desired value you want to display.
@@ -10,6 +10,7 @@ examples:
10
10
  - currency_unstyled: Unstyled
11
11
  - currency_comma_separator: Comma Separator
12
12
  - currency_negative: Negative
13
+ - currency_null_display: Null Display
13
14
 
14
15
  react:
15
16
  - currency_variants: Variants
@@ -21,6 +22,7 @@ examples:
21
22
  - currency_unstyled: Unstyled
22
23
  - currency_comma_separator: Comma Separator
23
24
  - currency_negative: Negative
25
+ - currency_null_display: Null Display
24
26
 
25
27
  swift:
26
28
  - currency_size_swift: Size
@@ -6,4 +6,5 @@ export { default as CurrencyAbbreviated } from './_currency_abbreviated.jsx'
6
6
  export { default as CurrencyMatchingDecimals } from './_currency_matching_decimals.jsx'
7
7
  export { default as CurrencyUnstyled } from './_currency_unstyled.jsx'
8
8
  export { default as CurrencyCommaSeparator } from './_currency_comma_separator.jsx'
9
- export { default as CurrencyNegative } from './_currency_negative.jsx'
9
+ export { default as CurrencyNegative } from './_currency_negative.jsx'
10
+ export { default as CurrencyNullDisplay } from './_currency_null_display.jsx'
@@ -1,4 +1,6 @@
1
- import React, { useRef, forwardRef } from 'react'
1
+ /*eslint-disable react/no-multi-comp */
2
+
3
+ import React, { forwardRef, useRef } from 'react'
2
4
  import Body from '../pb_body/_body'
3
5
  import Flex from '../pb_flex/_flex'
4
6
  import classnames from 'classnames'
@@ -8,7 +10,7 @@ import { globalProps, GlobalProps } from '../utilities/globalProps'
8
10
  type RadioProps = {
9
11
  aria?: { [key: string]: string },
10
12
  alignment?: string,
11
- checked?: boolean, // removed default assignment here
13
+ checked?: boolean,
12
14
  children?: React.ReactChild[] | React.ReactChild,
13
15
  customChildren?: boolean,
14
16
  className?: string,
@@ -22,10 +24,10 @@ type RadioProps = {
22
24
  name?: string,
23
25
  value?: string,
24
26
  text?: string,
25
- onChange?: (event: React.FormEvent<HTMLInputElement> | null) => void,
27
+ onChange: (event: React.FormEvent<HTMLInputElement> | null) => void,
26
28
  } & GlobalProps
27
29
 
28
- const Radio = forwardRef<HTMLInputElement, RadioProps>(({
30
+ const Radio = ({
29
31
  aria = {},
30
32
  alignment,
31
33
  children,
@@ -41,123 +43,110 @@ const Radio = forwardRef<HTMLInputElement, RadioProps>(({
41
43
  name = 'radio_name',
42
44
  text = 'Radio Text',
43
45
  value = 'radio_text',
44
- checked,
45
46
  onChange = () => { void 0 },
46
47
  ...props
47
- }, ref) => {
48
- const internalRef = useRef<HTMLInputElement>(null)
49
- const setRefs = (el: HTMLInputElement) => {
50
- internalRef.current = el
51
- if (typeof ref === 'function') {
52
- ref(el)
53
- } else if (ref) {
54
- (ref as React.MutableRefObject<HTMLInputElement | null>).current = el
55
- }
56
- }
57
-
58
- const ariaProps = buildAriaProps(aria)
59
- const dataProps = buildDataProps(data)
60
- const htmlProps = buildHtmlProps(htmlOptions)
48
+ }: RadioProps, ref: any) => {
49
+ const radioRef = useRef(null);
61
50
 
51
+ const ariaProps = buildAriaProps(aria);
52
+ const dataProps = buildDataProps(data);
53
+ const htmlProps = buildHtmlProps(htmlOptions);
62
54
  const classes = classnames(
63
55
  buildCss('pb_radio_kit', alignment),
64
56
  dark ? 'dark' : null,
65
57
  error ? 'error' : null,
66
58
  globalProps(props),
67
59
  className
68
- )
60
+ );
69
61
 
70
62
  const classesCustom = classnames(
71
63
  dark ? 'dark' : null,
72
64
  error ? 'error' : null,
73
65
  globalProps(props),
74
66
  className
75
- )
76
-
77
- const checkedProps = checked !== undefined ? { checked } : {}
67
+ );
78
68
 
79
- const displayRadio = (inputProps: any) => {
80
- if (children && customChildren === false)
81
- return children
69
+ const displayRadio = (props: RadioProps & any) => {
70
+ if (children && customChildren == false)
71
+ return (children)
82
72
  else
83
- return (
84
- <input
85
- {...checkedProps}
86
- disabled={disabled}
87
- id={id}
88
- name={name}
89
- onChange={onChange}
90
- ref={setRefs}
91
- type="radio"
92
- value={value}
93
- {...inputProps}
94
- />
95
- )
96
- }
73
+ return (
74
+ <input
75
+ disabled={disabled}
76
+ id={id}
77
+ name={name}
78
+ onChange={onChange}
79
+ ref={ref}
80
+ text={text}
81
+ type="radio"
82
+ value={value}
83
+ {...props}
84
+ />
85
+ )}
97
86
 
98
87
  const handleContainerClick = (event: React.MouseEvent<HTMLDivElement, MouseEvent> | undefined) => {
99
88
  if (event) {
100
- const target = event.target as HTMLElement
89
+ const target = event.target as HTMLElement;
101
90
  if (
102
91
  target.id === 'pb-radio-children-wrapper' ||
103
92
  target.closest('#pb-radio-children-wrapper')
104
93
  ) {
105
- internalRef.current?.click()
94
+ radioRef.current?.click();
106
95
  }
107
96
  }
108
- }
97
+ };
109
98
 
110
- return customChildren ? (
111
- <Flex
112
- {...ariaProps}
113
- {...dataProps}
114
- {...htmlProps}
115
- align="center"
116
- className={classesCustom}
117
- cursor="pointer"
118
- htmlFor={id}
119
- htmlOptions={{
120
- onClick: ((event: React.MouseEvent<HTMLDivElement, MouseEvent>) => {
121
- handleContainerClick(event)
122
- }) as unknown as () => void
123
- }}
124
- id="radio-container"
125
- >
126
- <label className={buildCss('pb_radio_kit', alignment)}>
99
+ return (
100
+ customChildren ? (
101
+ <Flex
102
+ {...ariaProps}
103
+ {...dataProps}
104
+ {...htmlProps}
105
+ align='center'
106
+ className={classesCustom}
107
+ cursor='pointer'
108
+ htmlFor={id}
109
+ htmlOptions={{
110
+ onClick: ((event: React.MouseEvent<HTMLDivElement, MouseEvent>) => {
111
+ handleContainerClick(event);
112
+ }) as unknown as () => void
113
+ }}
114
+ id="radio-container"
115
+ >
116
+ <label className={buildCss('pb_radio_kit', alignment)}>
127
117
  <input
128
- {...checkedProps}
129
118
  disabled={disabled}
130
119
  id={id}
131
120
  name={name}
132
121
  onChange={onChange}
133
- ref={setRefs}
122
+ ref={radioRef}
134
123
  type="radio"
135
124
  value={value}
136
125
  {...props}
137
126
  />
127
+ <span className="pb_radio_button" />
128
+ </label>
129
+ <div id="pb-radio-children-wrapper"> {children} </div>
130
+ </Flex>
131
+ ) : (
132
+ <label
133
+ {...ariaProps}
134
+ {...dataProps}
135
+ {...htmlProps}
136
+ className={classes}
137
+ htmlFor={id}
138
+ >
139
+ <>{displayRadio(props)}</>
138
140
  <span className="pb_radio_button" />
141
+ <Body
142
+ dark={dark}
143
+ status={error ? 'negative' : null}
144
+ text={label}
145
+ variant={null}
146
+ />
139
147
  </label>
140
- <div id="pb-radio-children-wrapper"> {children} </div>
141
- </Flex>
142
- ) : (
143
- <label
144
- {...ariaProps}
145
- {...dataProps}
146
- {...htmlProps}
147
- className={classes}
148
- htmlFor={id}
149
- >
150
- {displayRadio(props)}
151
- <span className="pb_radio_button" />
152
- <Body
153
- dark={dark}
154
- status={error ? 'negative' : null}
155
- text={label}
156
- variant={null}
157
- />
158
- </label>
159
- )
160
- })
148
+ )
149
+ );
150
+ };
161
151
 
162
- Radio.displayName = "Radio"
163
- export default Radio
152
+ export default forwardRef(Radio);
@@ -16,7 +16,6 @@ examples:
16
16
  - radio_alignment: Alignment
17
17
  - radio_disabled: Disabled
18
18
  - radio_custom_children: Custom Children
19
- - radio_react_hook: React Hook Form
20
19
 
21
20
  swift:
22
21
  - radio_default_swift: Default
@@ -27,4 +26,4 @@ examples:
27
26
  - radio_spacing_swift: Spacing
28
27
  - radio_padding_swift: Padding
29
28
  - radio_subtitle_swift: Subtitle
30
- - radio_props_swift: ""
29
+ - radio_props_swift: ""
@@ -4,4 +4,3 @@ export { default as RadioError } from './_radio_error.jsx'
4
4
  export { default as RadioAlignment } from './_radio_alignment.jsx'
5
5
  export { default as RadioDisabled } from './_radio_disabled.jsx'
6
6
  export { default as RadioCustomChildren } from './_radio_custom_children.jsx'
7
- export { default as RadioReactHook } from './_radio_react_hook.jsx'
@@ -86,19 +86,3 @@ test('has disabled attribute', () => {
86
86
  expect(input).toHaveAttribute('disabled')
87
87
  })
88
88
 
89
-
90
- test('has ref in the input element', () => {
91
- const ref = React.createRef()
92
- render(
93
- <Radio
94
- data={{ testid: testId }}
95
- name="Radio-name"
96
- ref={ref}
97
- text="Radio"
98
- value="radio value"
99
- />
100
- )
101
-
102
- expect(ref.current).not.toBeNull()
103
- expect(ref.current?.tagName).toBe('INPUT')
104
- })
@@ -1,4 +1,4 @@
1
- import React from 'react'
1
+ import React, { forwardRef } from 'react'
2
2
  import Select from 'react-select'
3
3
  import AsyncSelect from 'react-select/async'
4
4
  import CreateableSelect from 'react-select/creatable'
@@ -47,6 +47,7 @@ type TypeaheadProps = {
47
47
  name?: string,
48
48
  marginBottom?: "none" | "xxs" | "xs" | "sm" | "md" | "lg" | "xl",
49
49
  pillColor?: "primary" | "neutral" | "success" | "warning" | "error" | "info" | "data_1" | "data_2" | "data_3" | "data_4" | "data_5" | "data_6" | "data_7" | "data_8" | "windows" | "siding" | "roofing" | "doors" | "gutters" | "solar" | "insulation" | "accessories",
50
+ onChange?: (event: React.FormEvent<HTMLInputElement> | null) => void,
50
51
  } & GlobalProps
51
52
 
52
53
  export type SelectValueType = {
@@ -66,8 +67,7 @@ type TagOnChangeValues = {
66
67
  * @constant {React.ReactComponent} Typeahead
67
68
  * @param {TypeaheadProps} props - props as described at https://react-select.com/props
68
69
  */
69
-
70
- const Typeahead = ({
70
+ const Typeahead = forwardRef<HTMLInputElement, TypeaheadProps>(({
71
71
  async,
72
72
  className,
73
73
  components = {},
@@ -78,9 +78,11 @@ const Typeahead = ({
78
78
  getOptionValue,
79
79
  htmlOptions = {},
80
80
  id,
81
+ name,
81
82
  loadOptions = noop,
82
83
  marginBottom = "sm",
83
84
  pillColor,
85
+ onChange = () => { void 0 },
84
86
  ...props
85
87
  }: TypeaheadProps) => {
86
88
  const selectProps = {
@@ -122,6 +124,8 @@ const Typeahead = ({
122
124
  )
123
125
 
124
126
  const handleOnChange = (_data: SelectValueType, { action, option, removedValue }: TagOnChangeValues) => {
127
+ onChange({ target: { name: name, value: _data } } as unknown as React.ChangeEvent<HTMLInputElement>)
128
+
125
129
  if (action === 'select-option') {
126
130
  if (selectProps.onMultiValueClick) selectProps.onMultiValueClick(option)
127
131
  const multiValueClearEvent = new CustomEvent(`pb-typeahead-kit-${selectProps.id}-result-option-select`, { detail: option ? option : _data })
@@ -165,10 +169,11 @@ const Typeahead = ({
165
169
  />
166
170
  </div>
167
171
  )
168
- }
172
+ })
169
173
 
170
174
  Object.keys(kitComponents).forEach((k) => {
171
175
  (Typeahead as GenericObject)[k] = (kitComponents as {[key: string]: unknown})[k]
172
176
  })
173
177
 
178
+ Typeahead.displayName = 'Typeahead'
174
179
  export default Typeahead
@@ -0,0 +1,66 @@
1
+ import React from 'react'
2
+
3
+ import { Typeahead, Title } from 'playbook-ui'
4
+ import { useForm } from 'react-hook-form'
5
+
6
+ const languages = [
7
+ { label: 'JavaScript', value: '1995', category: 'Web Development' },
8
+ { label: 'Python', value: '1991', category: 'General Purpose' },
9
+ { label: 'Java', value: '1995', category: 'Enterprise' },
10
+ { label: 'C++', value: '1985', category: 'Systems Programming' },
11
+ { label: 'Go', value: '2009', category: 'Systems Programming' },
12
+ { label: 'Rust', value: '2010', category: 'Systems Programming' },
13
+ { label: 'Swift', value: '2014', category: 'Mobile Development' },
14
+ { label: 'Kotlin', value: '2011', category: 'Mobile Development' },
15
+ { label: 'Ruby', value: '1995', category: 'Web Development' },
16
+ { label: 'PHP', value: '1995', category: 'Web Development' },
17
+ ]
18
+
19
+ const colors = [
20
+ { label: 'Orange', value: '#FFA500' },
21
+ { label: 'Red', value: '#FF0000' },
22
+ { label: 'Green', value: '#00FF00' },
23
+ { label: 'Blue', value: '#0000FF' },
24
+ ]
25
+
26
+ const TypeaheadReactHook = (props) => {
27
+ const { register, watch } = useForm()
28
+
29
+ const selectedLanguages = watch('languages')
30
+ const selectedColor = watch('color')
31
+
32
+ return (
33
+ <>
34
+ <Typeahead
35
+ isMulti
36
+ label="Multi Select Languages"
37
+ multiKit="language"
38
+ options={languages}
39
+ {...props}
40
+ {...register('languages')}
41
+ />
42
+ <Title
43
+ size={4}
44
+ text='Selected Languages'
45
+ />
46
+ {selectedLanguages && selectedLanguages.map(language => (
47
+ <p key={language.label}>{`${language.label} - ${language.value} - ${language.category}`}</p>
48
+ ))}
49
+
50
+ <Typeahead
51
+ label="Colors"
52
+ marginTop="lg"
53
+ options={colors}
54
+ {...props}
55
+ {...register('color')}
56
+ />
57
+ <Title
58
+ size={4}
59
+ text='Selected Color'
60
+ />
61
+ <p>{ selectedColor && `${selectedColor.label} - ${selectedColor.value}`}</p>
62
+ </>
63
+ )
64
+ }
65
+
66
+ export default TypeaheadReactHook
@@ -0,0 +1 @@
1
+ You can pass `react-hook-form` props to the Typeahead kit.