playbook_ui 12.38.0 → 12.39.0.pre.alpha.salesbookmismatchingdate1114

Sign up to get free protection for your applications and to get access to all the features.
Files changed (47) hide show
  1. checksums.yaml +4 -4
  2. data/app/pb_kits/playbook/pb_collapsible/_collapsible.scss +6 -0
  3. data/app/pb_kits/playbook/pb_collapsible/_collapsible.tsx +3 -3
  4. data/app/pb_kits/playbook/pb_collapsible/child_kits/CollapsibleMain.tsx +10 -9
  5. data/app/pb_kits/playbook/pb_collapsible/docs/_collapsible_color.jsx +2 -2
  6. data/app/pb_kits/playbook/pb_collapsible/docs/_collapsible_default.jsx +2 -2
  7. data/app/pb_kits/playbook/pb_collapsible/docs/_collapsible_icons.jsx +4 -8
  8. data/app/pb_kits/playbook/pb_collapsible/docs/_collapsible_icons.md +1 -1
  9. data/app/pb_kits/playbook/pb_collapsible/docs/_collapsible_size.jsx +5 -5
  10. data/app/pb_kits/playbook/pb_collapsible/docs/_collapsible_state.jsx +75 -0
  11. data/app/pb_kits/playbook/pb_collapsible/docs/_collapsible_state.md +3 -0
  12. data/app/pb_kits/playbook/pb_collapsible/docs/example.yml +7 -6
  13. data/app/pb_kits/playbook/pb_collapsible/docs/index.js +2 -1
  14. data/app/pb_kits/playbook/pb_kit/dateTime.ts +41 -36
  15. data/app/pb_kits/playbook/pb_nav/_collapsible_nav.scss +280 -17
  16. data/app/pb_kits/playbook/pb_nav/_horizontal_nav.scss +6 -0
  17. data/app/pb_kits/playbook/pb_nav/_item.tsx +35 -22
  18. data/app/pb_kits/playbook/pb_nav/_mixins.scss +5 -0
  19. data/app/pb_kits/playbook/pb_nav/_subtle_mixin.scss +6 -7
  20. data/app/pb_kits/playbook/pb_nav/_vertical_nav.scss +1 -1
  21. data/app/pb_kits/playbook/pb_nav/docs/_collapsible_nav.jsx +85 -58
  22. data/app/pb_kits/playbook/pb_nav/docs/_collapsible_nav.md +1 -0
  23. data/app/pb_kits/playbook/pb_nav/docs/_collapsible_nav_custom.jsx +58 -0
  24. data/app/pb_kits/playbook/pb_nav/docs/_collapsible_nav_custom.md +1 -0
  25. data/app/pb_kits/playbook/pb_nav/docs/_collapsible_nav_emphasize.html.erb +23 -0
  26. data/app/pb_kits/playbook/pb_nav/docs/{_collapsible_nav_custom_icons.jsx → _collapsible_nav_emphasize.jsx} +14 -5
  27. data/app/pb_kits/playbook/pb_nav/docs/_collapsible_nav_emphasize.md +1 -0
  28. data/app/pb_kits/playbook/pb_nav/docs/example.yml +5 -3
  29. data/app/pb_kits/playbook/pb_nav/docs/index.js +2 -1
  30. data/app/pb_kits/playbook/pb_nav/item.html.erb +5 -4
  31. data/app/pb_kits/playbook/pb_nav/item.rb +29 -3
  32. data/app/pb_kits/playbook/pb_select/_select.scss +76 -0
  33. data/app/pb_kits/playbook/pb_select/_select.tsx +9 -5
  34. data/app/pb_kits/playbook/pb_select/docs/_select_attributes.html.erb +26 -0
  35. data/app/pb_kits/playbook/pb_select/docs/_select_attributes.md +1 -0
  36. data/app/pb_kits/playbook/pb_select/docs/_select_multiple.html.erb +36 -0
  37. data/app/pb_kits/playbook/pb_select/docs/_select_multiple.jsx +50 -0
  38. data/app/pb_kits/playbook/pb_select/docs/_select_multiple.md +1 -0
  39. data/app/pb_kits/playbook/pb_select/docs/example.yml +3 -0
  40. data/app/pb_kits/playbook/pb_select/docs/index.js +1 -0
  41. data/app/pb_kits/playbook/pb_select/select.html.erb +5 -9
  42. data/app/pb_kits/playbook/pb_select/select.rb +14 -0
  43. data/app/pb_kits/playbook/pb_select/select.test.js +17 -0
  44. data/app/pb_kits/playbook/pb_time/_time.tsx +1 -1
  45. data/dist/playbook-rails.js +2 -2
  46. data/lib/playbook/version.rb +2 -2
  47. metadata +21 -8
@@ -0,0 +1,58 @@
1
+ import React from "react"
2
+ import { Nav, NavItem, useCollapsible } from "../.."
3
+
4
+ const CollapsibleNavCustom = (props) => {
5
+ const navItems = ["Overview", "Albums", "Similar Artists"]
6
+ // eslint-disable-next-line react-hooks/rules-of-hooks
7
+ const collapsibles = navItems.map(() => useCollapsible(true))
8
+
9
+ const handleMainClick = (index) => {
10
+ collapsibles.forEach(([, , setCollapsed], idx) => {
11
+ if (idx === index) {
12
+ setCollapsed(false)
13
+ } else {
14
+ setCollapsed(true)
15
+ }
16
+ })
17
+ }
18
+
19
+ return (
20
+ <>
21
+ <Nav variant='bold'>
22
+ {navItems.map((text, index) => {
23
+ const [collapsed] = collapsibles[index]
24
+ return (
25
+ <NavItem
26
+ collapsed={collapsed}
27
+ collapsible
28
+ collapsibleTrail
29
+ fontWeight="bolder"
30
+ iconLeft="chevron-down"
31
+ id={`collapsible-nav-item-${index + 1}`}
32
+ key={index}
33
+ link="#"
34
+ onClick={() => handleMainClick(index)}
35
+ text={text}
36
+ {...props}
37
+ >
38
+ <NavItem link="#"
39
+ text="City"
40
+ {...props}
41
+ />
42
+ <NavItem link="#"
43
+ text="People"
44
+ {...props}
45
+ />
46
+ <NavItem link="#"
47
+ text="Business"
48
+ {...props}
49
+ />
50
+ </NavItem>
51
+ );
52
+ })}
53
+ </Nav>
54
+ </>
55
+ )
56
+ }
57
+
58
+ export default CollapsibleNavCustom
@@ -0,0 +1 @@
1
+ The collapsible nav kit uses our Collapsible kit under the hood and as such the `useCollapsible` hook can be used to achieve custom toggling of the collapsible nav. To do this, you must import and declare the `useCollapsible` hook and pass it's state to the `collapsed` prop. See our code example below to see how this can be done.
@@ -0,0 +1,23 @@
1
+ <%= pb_rails("nav", props: { variant: "subtle" }) do %>
2
+ <%= pb_rails("nav/item", props: { text: "Overview", link: "#", font_weight:"bolder", font_size:"small", collapsible: true, icon_left:"city", collapsible_trail: true }) do %>
3
+ <%= pb_rails("nav", props: { variant: "subtle" }) do %>
4
+ <%= pb_rails("nav/item", props: { text: "City", link: "#" }) %>
5
+ <%= pb_rails("nav/item", props: { text: "People", link: "#" }) %>
6
+ <%= pb_rails("nav/item", props: { text: "Business", link: "#" }) %>
7
+ <% end %>
8
+ <% end %>
9
+ <%= pb_rails("nav/item", props: { text: "Albums", link: "#", font_weight:"bolder", font_size:"small", collapsible: true, icon_left: "theater-masks", collapsible_trail:true }) do %>
10
+ <%= pb_rails("nav", props: { variant: "subtle" }) do %>
11
+ <%= pb_rails("nav/item", props: { text: "Entertainment", link: "#" }) %>
12
+ <%= pb_rails("nav/item", props: { text: "Food", link: "#" }) %>
13
+ <%= pb_rails("nav/item", props: { text: "Style", link: "#" }) %>
14
+ <% end %>
15
+ <% end %>
16
+ <%= pb_rails("nav/item", props: { text: "Similar Artists", link: "#", font_weight:"bolder", font_size:"small", collapsible: true, icon_left: "city", collapsible_trail:true }) do %>
17
+ <%= pb_rails("nav", props: { variant: "subtle" }) do %>
18
+ <%= pb_rails("nav/item", props: { text: "City", link: "#" }) %>
19
+ <%= pb_rails("nav/item", props: { text: "People", link: "#" }) %>
20
+ <%= pb_rails("nav/item", props: { text: "Business", link: "#" }) %>
21
+ <% end %>
22
+ <% end %>
23
+ <% end %>
@@ -1,11 +1,15 @@
1
1
  import React from "react";
2
2
  import { Nav, NavItem } from '../..'
3
3
 
4
- const CollapsibleNavCustomIcons = (props) => {
4
+ const CollapsibleNavEmphasize = (props) => {
5
5
  return (
6
- <Nav variant="subtle">
6
+ <Nav variant="bold">
7
7
  <NavItem
8
- collapsible
8
+ active
9
+ collapsible
10
+ collapsibleTrail
11
+ fontSize="small"
12
+ fontWeight="bolder"
9
13
  iconLeft="city"
10
14
  iconRight={["plus", "minus"]}
11
15
  link="#"
@@ -29,8 +33,10 @@ const CollapsibleNavCustomIcons = (props) => {
29
33
  />
30
34
  </NavItem>
31
35
  <NavItem
32
- active
33
36
  collapsible
37
+ collapsibleTrail
38
+ fontSize="small"
39
+ fontWeight="bolder"
34
40
  iconLeft="theater-masks"
35
41
  iconRight={["plus", "minus"]}
36
42
  link="#"
@@ -55,6 +61,9 @@ const CollapsibleNavCustomIcons = (props) => {
55
61
  </NavItem>
56
62
  <NavItem
57
63
  collapsible
64
+ collapsibleTrail
65
+ fontSize="small"
66
+ fontWeight="bolder"
58
67
  iconLeft="city"
59
68
  iconRight={["plus", "minus"]}
60
69
  link="#"
@@ -81,4 +90,4 @@ const CollapsibleNavCustomIcons = (props) => {
81
90
  );
82
91
  };
83
92
 
84
- export default CollapsibleNavCustomIcons;
93
+ export default CollapsibleNavEmphasize;
@@ -0,0 +1 @@
1
+ The ` navBold` prop can be passed to NavItem
@@ -7,7 +7,8 @@ examples:
7
7
  - borderless_nav: No Borders
8
8
  - subtle_nav: Subtle Variant
9
9
  - subtle_with_icons_nav: Subtle With Icons
10
- # - collapsible_nav: Subtle With Collapsible
10
+ # - collapsible_nav: Collapsible Nav
11
+ # - collapsible_nav_emphasize: Collapsible Nav with Emphasize Styling
11
12
  - subtle_no_highlight_nav: Subtle No Highlight
12
13
  - bold_vertical_nav: Bold Variant
13
14
  - horizontal_nav: Horizontal Nav
@@ -25,8 +26,9 @@ examples:
25
26
  - borderless_nav: No Borders
26
27
  - subtle_nav: Subtle Variant
27
28
  - subtle_with_icons_nav: Subtle With Icons
28
- # - collapsible_nav: Subtle With Collapsible
29
- # - collapsible_nav_custom_icons: Subtle With Collapsible (No custom toggling)
29
+ # - collapsible_nav: Collapsible Nav
30
+ # - collapsible_nav_emphasize: Collapsible Nav with Emphasize Styling
31
+ # - collapsible_nav_custom: Collapsible Nav With Custom Toggling
30
32
  - subtle_no_highlight_nav: Subtle No Highlight
31
33
  - bold_vertical_nav: Bold Variant
32
34
  - horizontal_nav: Horizontal Nav
@@ -14,4 +14,5 @@ export { default as NewTab } from './_new_tab.jsx'
14
14
  export { default as BoldHorizontalNav } from './_bold_horizontal_nav.jsx'
15
15
  export { default as BoldVerticalNav } from './_bold_vertical_nav.jsx'
16
16
  export { default as CollapsibleNav } from './_collapsible_nav.jsx'
17
- export { default as CollapsibleNavCustomIcons } from './_collapsible_nav_custom_icons.jsx'
17
+ export { default as CollapsibleNavCustom } from './_collapsible_nav_custom.jsx'
18
+ export { default as CollapsibleNavEmphasize } from "./_collapsible_nav_emphasize.jsx"
@@ -2,19 +2,20 @@
2
2
  aria: object.aria,
3
3
  class: object.classname,
4
4
  data: object.data,
5
+ dark: object.dark,
5
6
  id: object.id) do %>
6
7
  <% if object.collapsible %>
7
8
  <%= pb_rails("collapsible", props: { name: "collapsible-nav-example" }) do %>
8
- <%= pb_rails("collapsible/collapsible_main", props: { name: "default-collapsible-nav", icon: object.collapsible_icons, size: "xs" }) do %>
9
+ <%= pb_rails("collapsible/collapsible_main", props: { name: "default-collapsible-nav", icon: object.collapsible_icons, size: "xs", dark: object.dark }) do %>
9
10
  <%= content_tag(object.tag,
10
11
  object.link ? object.link_options : object.options) do %>
11
12
  <% if object.image_url %>
12
- <%= pb_rails("image", props: { url: object.image_url, classname: "pb_nav_img_wrapper" }) %>
13
+ <%= pb_rails("image", props: { url: object.image_url, classname: "pb_nav_img_wrapper_collapsible" }) %>
13
14
  <% end %>
14
15
  <% if object.icon_left %>
15
- <%= pb_rails("icon", props: { icon: object.icon_left, classname: "pb_nav_list_item_icon_left", fixed_width: true}) %>
16
+ <%= pb_rails("icon", props: { icon: object.icon_left, classname: "pb_nav_list_item_icon_left_collapsible", fixed_width: true}) %>
16
17
  <% end %>
17
- <span class="pb_nav_list_item_text">
18
+ <span class="pb_nav_list_item_text_collapsible">
18
19
  <%= object.text %>
19
20
  </span>
20
21
  <% end %>
@@ -4,9 +4,16 @@ module Playbook
4
4
  module PbNav
5
5
  class Item < Playbook::KitBase
6
6
  prop :active, type: Playbook::Props::Boolean, default: false
7
+ prop :font_size, type: Playbook::Props::Enum,
8
+ values: %w[normal small],
9
+ default: "normal"
10
+ prop :font_weight, type: Playbook::Props::Enum,
11
+ values: %w[bold regular bolder],
12
+ default: "regular"
7
13
  prop :collapsible, type: Playbook::Props::Boolean, default: false
8
14
  prop :link
9
15
  prop :text
16
+ prop :collapsible_trail, type: Playbook::Props::Boolean, default: false
10
17
  prop :icon_left
11
18
  prop :icon_right
12
19
  prop :image_url
@@ -15,9 +22,9 @@ module Playbook
15
22
  default: "_self"
16
23
  def classname
17
24
  if collapsible
18
- "pb_collapsible_nav_item #{generate_classname('pb_nav_list_kit_item', active_class)}"
25
+ "#{generate_classname('pb_nav_list_kit_item', active_class)} #{generate_classname('pb_collapsible_nav_item', active_class, collapsible_trail_class)} #{font_size_class} #{font_weight_class}"
19
26
  else
20
- generate_classname("pb_nav_list_kit_item", active_class)
27
+ "#{generate_classname('pb_nav_list_kit_item', active_class)} #{font_size_class} #{font_weight_class}"
21
28
  end
22
29
  end
23
30
 
@@ -27,7 +34,7 @@ module Playbook
27
34
 
28
35
  def options
29
36
  {
30
- class: "pb_nav_list_item_link",
37
+ class: collapsible ? "pb_nav_list_item_link_collapsible" : "pb_nav_list_item_link",
31
38
  }.compact
32
39
  end
33
40
 
@@ -47,6 +54,25 @@ module Playbook
47
54
  def active_class
48
55
  active ? "active" : nil
49
56
  end
57
+
58
+ def font_weight_class
59
+ case font_weight
60
+ when "bold"
61
+ "font_bold"
62
+ when "bolder"
63
+ "font_bolder"
64
+ else
65
+ "font_regular"
66
+ end
67
+ end
68
+
69
+ def collapsible_trail_class
70
+ collapsible_trail ? "collapsible_trail" : nil
71
+ end
72
+
73
+ def font_size_class
74
+ font_size === "small" ? "font_size_small" : "font_size_normal"
75
+ end
50
76
  end
51
77
  end
52
78
  end
@@ -2,6 +2,7 @@
2
2
  @import "../pb_textarea/textarea_mixin";
3
3
  @import "../tokens/titles";
4
4
  @import "../tokens/colors";
5
+ @import "../tokens/spacing";
5
6
 
6
7
  [class^=pb_select] {
7
8
  select {
@@ -32,6 +33,42 @@
32
33
  opacity: 0.5;
33
34
  }
34
35
  }
36
+ select[multiple] {
37
+ @include pb_textarea_light;
38
+ @include pb_body_light;
39
+ background: none;
40
+ background-color: $white;
41
+ appearance: none;
42
+ cursor: pointer;
43
+ box-shadow: inset 0 -11px 20px rgba($primary, 0.05);
44
+ padding-right: 0px !important;
45
+ color: transparent !important;
46
+ text-shadow: 0 0 0 $text_lt_default;
47
+ white-space: nowrap;
48
+ text-overflow: ellipsis;
49
+ padding: $space_xs 0px !important;
50
+ max-height: unset !important;
51
+ @media (hover:hover) {
52
+ &:hover, &:active, &:focus {
53
+ background-color: rgba($focus_input_light, $opacity_5);
54
+ }
55
+ }
56
+ &:focus{
57
+ border-color: $primary;
58
+ @include transition_default;
59
+ }
60
+ option {
61
+ padding-left: $space_sm;
62
+ padding-top: $space_xxs;
63
+ padding-bottom: $space_xxs;
64
+ }
65
+ option:checked {
66
+ background-color: $hover_light;
67
+ }
68
+ option:hover {
69
+ background-color: $hover_light;
70
+ }
71
+ }
35
72
  option {
36
73
  color: $text_lt_default;
37
74
  }
@@ -115,6 +152,45 @@
115
152
  }
116
153
  }
117
154
  }
155
+ select[multiple] {
156
+ @include pb_textarea_dark;
157
+ @include pb_body_light_dark;
158
+ background: none;
159
+ background-color: rgba($white,.10);
160
+ appearance: none;
161
+ cursor: pointer;
162
+ box-shadow: inset 0 -11px 20px rgba($white, 0.05);
163
+ padding-right: 0px !important;
164
+ color: transparent !important;
165
+ text-shadow: 0 0 0 $text_dk_default;
166
+ white-space: nowrap;
167
+ text-overflow: ellipsis;
168
+ padding: $space_xs 0px !important;
169
+ max-height: unset !important;
170
+ @media (hover:hover) {
171
+ &:hover, &:active, &:focus {
172
+ background-color: rgba($white,.05);
173
+ }
174
+ }
175
+ &:focus{
176
+ border-color: $primary;
177
+ @include transition_default;
178
+ }
179
+ option {
180
+ padding-left: $space_sm;
181
+ padding-top: $space_xxs;
182
+ padding-bottom: $space_xxs;
183
+ }
184
+ option:checked {
185
+ background-color: $hover_dark;
186
+ }
187
+ option:hover {
188
+ background-color: $hover_dark;
189
+ }
190
+ }
191
+ option {
192
+ color: $text_dk_default;
193
+ }
118
194
  .pb_select_kit_caret {
119
195
  color: $white;
120
196
  }
@@ -124,11 +124,15 @@ const Select = ({
124
124
  htmlFor={name}
125
125
  >
126
126
  {selectBody}
127
- <Icon
128
- className="pb_select_kit_caret"
129
- fixedWidth
130
- icon="angle-down"
131
- />
127
+ { multiple !== true ?
128
+ <Icon
129
+ className="pb_select_kit_caret"
130
+ fixedWidth
131
+ icon="angle-down"
132
+ />
133
+ :
134
+ null
135
+ }
132
136
  {error &&
133
137
  <Body
134
138
  status="negative"
@@ -0,0 +1,26 @@
1
+ <%= pb_rails("select", props: {
2
+ attributes: {
3
+ data: { options: "data_attribute" },
4
+ },
5
+ label: "Favorite Food",
6
+ name: "food",
7
+ options: [
8
+ {
9
+ value: "1",
10
+ value_text: "Burgers",
11
+ },
12
+ {
13
+ value: "2",
14
+ selected: true,
15
+ value_text: "Pizza",
16
+ },
17
+ {
18
+ value: "3",
19
+ value_text: "Tacos",
20
+ },
21
+ {
22
+ value: "4",
23
+ value_text: "BBQ",
24
+ },
25
+ ]
26
+ }) %>
@@ -0,0 +1 @@
1
+ Inspect the element and notice the data-attribute being added to the `<select>` element
@@ -0,0 +1,36 @@
1
+ <%= pb_rails("select", props: {
2
+ label: "Favorite Food",
3
+ name: "food",
4
+ multiple: true,
5
+ options: [
6
+ {
7
+ value: "1",
8
+ value_text: "Burgers",
9
+ },
10
+ {
11
+ value: "2",
12
+ selected: true,
13
+ value_text: "Pizza",
14
+ },
15
+ {
16
+ value: "3",
17
+ value_text: "Tacos",
18
+ },
19
+ {
20
+ value: "4",
21
+ value_text: "BBQ",
22
+ },
23
+ {
24
+ value: "4",
25
+ value_text: "Sushi",
26
+ },
27
+ {
28
+ value: "4",
29
+ value_text: "Chinese",
30
+ },
31
+ {
32
+ value: "4",
33
+ value_text: "Hot Dogs",
34
+ },
35
+ ]
36
+ }) %>
@@ -0,0 +1,50 @@
1
+ import React from 'react'
2
+
3
+ import Select from '../_select'
4
+
5
+ const SelectMultiple = (props) => {
6
+ const options = [
7
+ {
8
+ value: '1',
9
+ text: 'Burgers',
10
+ },
11
+ {
12
+ value: '2',
13
+ text: 'Pizza',
14
+ },
15
+ {
16
+ value: '3',
17
+ text: 'Tacos',
18
+ },
19
+ {
20
+ value: '3',
21
+ text: 'BBQ',
22
+ },
23
+ {
24
+ value: '3',
25
+ text: 'Sushi',
26
+ },
27
+ {
28
+ value: '3',
29
+ text: 'Chinese',
30
+ },
31
+ {
32
+ value: '3',
33
+ text: 'Hot Dogs',
34
+ },
35
+ ]
36
+
37
+ return (
38
+ <div>
39
+ <Select
40
+ label="Favorite Food"
41
+ multiple
42
+ name="food"
43
+ options={options}
44
+ {...props}
45
+ />
46
+ </div>
47
+ )
48
+ }
49
+
50
+ export default SelectMultiple
@@ -0,0 +1 @@
1
+ We recommend using a typeahead for better UX
@@ -11,6 +11,8 @@ examples:
11
11
  - select_error: Select w/ Error
12
12
  - select_inline: Select Inline
13
13
  - select_inline_compact: Select Inline Compact
14
+ - select_attributes: Select W/ Attributes
15
+ - select_multiple: Select Multiple
14
16
 
15
17
 
16
18
 
@@ -25,3 +27,4 @@ examples:
25
27
  - select_error: Select w/ Error
26
28
  - select_inline: Select Inline
27
29
  - select_inline_compact: Select Inline Compact
30
+ - select_multiple: Select Multiple
@@ -8,3 +8,4 @@ export { default as SelectValueTextSame } from './_select_value_text_same.jsx'
8
8
  export { default as SelectError } from './_select_error.jsx'
9
9
  export { default as SelectInline } from './_select_inline.jsx'
10
10
  export { default as SelectInlineCompact } from './_select_inline_compact.jsx'
11
+ export { default as SelectMultiple } from './_select_multiple.jsx'
@@ -1,6 +1,6 @@
1
1
  <%= content_tag(:div,
2
- data: object.data,
3
2
  aria: object.aria,
3
+ data: object.data,
4
4
  class: object.classnames) do %>
5
5
  <% if object.label %>
6
6
  <label class="pb_select_kit_label" for="<%= object.name %>">
@@ -19,17 +19,13 @@
19
19
  selected: object.selected,
20
20
  disabled: object.disabled_options,
21
21
  ),
22
- id: object.id,
23
- prompt: object.blank_selection,
24
- disabled: object.disabled,
25
- required: object.required,
26
- multiple: object.multiple,
27
- onchange: object.onchange,
28
- include_blank: object.include_blank,
22
+ object.all_attributes
29
23
  )
30
24
  %>
31
25
  <%= pb_rails("body", props: { status: "negative", text: object.error }) %>
32
26
  <% end %>
33
- <%= pb_rails("icon", props: { icon: "angle-down", fixed_width: true, classname: "pb_select_kit_caret"}) %>
27
+ <% if object.multiple != true %>
28
+ <%= pb_rails("icon", props: { icon: "angle-down", fixed_width: true, classname: "pb_select_kit_caret"}) %>
29
+ <% end %>
34
30
  </label>
35
31
  <% end %>
@@ -6,6 +6,8 @@ require "action_view"
6
6
  module Playbook
7
7
  module PbSelect
8
8
  class Select < Playbook::KitBase
9
+ prop :attributes, type: Playbook::Props::Hash,
10
+ default: {}
9
11
  prop :blank_selection
10
12
  prop :compact, type: Playbook::Props::Boolean, default: false
11
13
  prop :disabled, type: Playbook::Props::Boolean, default: false
@@ -23,6 +25,18 @@ module Playbook
23
25
  classname + inline_class + compact_class
24
26
  end
25
27
 
28
+ def all_attributes
29
+ {
30
+ id: id,
31
+ prompt: blank_selection,
32
+ disabled: disabled,
33
+ required: required,
34
+ multiple: multiple,
35
+ onchange: onchange,
36
+ include_blank: include_blank,
37
+ }.merge(attributes)
38
+ end
39
+
26
40
  def classname
27
41
  generate_classname("pb_select", select_margin_bottom, separator: " ")
28
42
  end
@@ -49,3 +49,20 @@ test('returns dark class name', () => {
49
49
  const kit = screen.getByTestId(testId)
50
50
  expect(kit).toHaveClass(`${kitClass} dark`)
51
51
  })
52
+
53
+ test('returns multiple variant', () => {
54
+ render(
55
+ <Select
56
+ data={{ testid: "selectMultiple" }}
57
+ label="Favorite Food"
58
+ multiple
59
+ name="food"
60
+ options={options}
61
+ />
62
+ )
63
+
64
+ const kit = screen.getByTestId("selectMultiple");
65
+ const selectElement = kit.querySelector('select');
66
+
67
+ expect(selectElement).toHaveAttribute('multiple', '');
68
+ });
@@ -68,7 +68,7 @@ const Time = (props: TimeProps) => {
68
68
  )
69
69
  )}
70
70
 
71
- <time dateTime={date.toString()}>
71
+ <time dateTime={date.toLocaleString()}>
72
72
  <span>
73
73
  {unstyled
74
74
  ? (