playbook_ui 14.1.0.pre.alpha.PA1477timestampkit3536 → 14.1.0.pre.alpha.PA1477timestampkit3601

Sign up to get free protection for your applications and to get access to all the features.
Files changed (91) hide show
  1. checksums.yaml +4 -4
  2. data/app/pb_kits/playbook/_playbook.scss +2 -0
  3. data/app/pb_kits/playbook/pb_advanced_table/_advanced_table.scss +3 -3
  4. data/app/pb_kits/playbook/pb_advanced_table/advanced_table.html.erb +1 -1
  5. data/app/pb_kits/playbook/pb_badge/_badge.scss +9 -0
  6. data/app/pb_kits/playbook/pb_badge/_badge.tsx +8 -3
  7. data/app/pb_kits/playbook/pb_badge/badge.rb +1 -1
  8. data/app/pb_kits/playbook/pb_badge/badge.test.js +17 -11
  9. data/app/pb_kits/playbook/pb_badge/docs/_badge_notification.html.erb +13 -0
  10. data/app/pb_kits/playbook/pb_badge/docs/_badge_notification.jsx +31 -12
  11. data/app/pb_kits/playbook/pb_button/_button.tsx +4 -1
  12. data/app/pb_kits/playbook/pb_button/button.html.erb +1 -1
  13. data/app/pb_kits/playbook/pb_button/button.rb +4 -0
  14. data/app/pb_kits/playbook/pb_date_time/dateTime.test.js +2 -2
  15. data/app/pb_kits/playbook/pb_dialog/_close_icon.tsx +5 -1
  16. data/app/pb_kits/playbook/pb_dialog/_dialog.tsx +3 -1
  17. data/app/pb_kits/playbook/pb_dialog/dialog.test.jsx +20 -1
  18. data/app/pb_kits/playbook/pb_dialog/dialog_header.html.erb +1 -1
  19. data/app/pb_kits/playbook/pb_dialog/dialog_header.rb +4 -0
  20. data/app/pb_kits/playbook/pb_dialog/docs/_dialog_default.jsx +1 -5
  21. data/app/pb_kits/playbook/pb_dialog/docs/_dialog_loading.jsx +46 -0
  22. data/app/pb_kits/playbook/pb_dialog/docs/example.yml +1 -0
  23. data/app/pb_kits/playbook/pb_dialog/docs/index.js +1 -0
  24. data/app/pb_kits/playbook/pb_filter/filter.rb +1 -1
  25. data/app/pb_kits/playbook/pb_form/docs/_form_form_with_validate.html.erb +1 -0
  26. data/app/pb_kits/playbook/pb_form_pill/_form_pill.scss +43 -25
  27. data/app/pb_kits/playbook/pb_form_pill/_form_pill.tsx +6 -2
  28. data/app/pb_kits/playbook/pb_form_pill/docs/example.yml +2 -2
  29. data/app/pb_kits/playbook/pb_form_pill/form_pill.html.erb +4 -4
  30. data/app/pb_kits/playbook/pb_form_pill/form_pill.rb +4 -0
  31. data/app/pb_kits/playbook/pb_gantt_chart/_gantt_chart.scss +3 -0
  32. data/app/pb_kits/playbook/pb_gantt_chart/_gantt_chart.tsx +72 -0
  33. data/app/pb_kits/playbook/pb_gantt_chart/docs/_gantt_chart_default.jsx +53 -0
  34. data/app/pb_kits/playbook/pb_gantt_chart/docs/example.yml +7 -0
  35. data/app/pb_kits/playbook/pb_gantt_chart/docs/index.js +1 -0
  36. data/app/pb_kits/playbook/pb_gantt_chart/gantt_chart.test.jsx +19 -0
  37. data/app/pb_kits/playbook/pb_icon/_icon.tsx +1 -1
  38. data/app/pb_kits/playbook/pb_multi_level_select/_multi_level_select.tsx +0 -2
  39. data/app/pb_kits/playbook/pb_pagination/_pagination.scss +49 -13
  40. data/app/pb_kits/playbook/pb_pagination/_pagination.tsx +164 -0
  41. data/app/pb_kits/playbook/pb_pagination/docs/_pagination_default.jsx +19 -0
  42. data/app/pb_kits/playbook/pb_pagination/docs/_pagination_default_react.md +1 -0
  43. data/app/pb_kits/playbook/pb_pagination/docs/_pagination_page_change.jsx +62 -0
  44. data/app/pb_kits/playbook/pb_pagination/docs/_pagination_page_change_react.md +1 -0
  45. data/app/pb_kits/playbook/pb_pagination/docs/data.js +23 -0
  46. data/app/pb_kits/playbook/pb_pagination/docs/example.yml +3 -1
  47. data/app/pb_kits/playbook/pb_pagination/docs/index.js +2 -0
  48. data/app/pb_kits/playbook/pb_phone_number_input/_phone_number_input.scss +0 -7
  49. data/app/pb_kits/playbook/pb_popover/_popover.tsx +10 -5
  50. data/app/pb_kits/playbook/pb_rich_text_editor/_previewer_mixin.scss +132 -0
  51. data/app/pb_kits/playbook/pb_rich_text_editor/_tiptap_styles.scss +50 -76
  52. data/app/pb_kits/playbook/pb_rich_text_editor/docs/_rich_text_editor_advanced_preview.jsx +73 -0
  53. data/app/pb_kits/playbook/pb_rich_text_editor/docs/example.yml +1 -0
  54. data/app/pb_kits/playbook/pb_rich_text_editor/docs/index.js +2 -1
  55. data/app/pb_kits/playbook/pb_star_rating/index.js +78 -41
  56. data/app/pb_kits/playbook/pb_star_rating/star_rating.html.erb +4 -2
  57. data/app/pb_kits/playbook/pb_star_rating/star_rating.rb +17 -0
  58. data/app/pb_kits/playbook/pb_star_rating/subcomponents/_star_rating_display.tsx +0 -2
  59. data/app/pb_kits/playbook/pb_star_rating/subcomponents/_star_rating_interactive.tsx +0 -1
  60. data/app/pb_kits/playbook/pb_time/_time.tsx +12 -8
  61. data/app/pb_kits/playbook/pb_time/time.html.erb +3 -3
  62. data/app/pb_kits/playbook/pb_time/time.rb +4 -0
  63. data/app/pb_kits/playbook/pb_timestamp/docs/_timestamp_elapsed.html.erb +2 -2
  64. data/app/pb_kits/playbook/pb_timestamp/timestamp.rb +18 -9
  65. data/app/pb_kits/playbook/tokens/_container.scss +21 -0
  66. data/app/pb_kits/playbook/utilities/_min_width.scss +45 -0
  67. data/app/pb_kits/playbook/utilities/globalPropNames.mjs +1 -0
  68. data/app/pb_kits/playbook/utilities/globalProps.ts +20 -3
  69. data/app/pb_kits/playbook/utilities/icons/allicons.tsx +59 -0
  70. data/app/pb_kits/playbook/utilities/icons/clock.svg +9 -0
  71. data/app/pb_kits/playbook/utilities/icons/spinner.svg +3 -0
  72. data/app/pb_kits/playbook/utilities/icons/times.svg +3 -0
  73. data/dist/chunks/_typeahead-Cq7RLPBA.js +22 -0
  74. data/dist/chunks/_weekday_stacked-Cykj5kLZ.js +45 -0
  75. data/dist/chunks/lazysizes-B7xYodB-.js +1 -0
  76. data/dist/chunks/{lib-BE0Z3F7x.js → lib-DErGXNy3.js} +2 -2
  77. data/dist/chunks/{pb_form_validation-TzZQ0Flx.js → pb_form_validation-BC6kh7Hu.js} +1 -1
  78. data/dist/chunks/vendor.js +1 -1
  79. data/dist/menu.yml +4 -0
  80. data/dist/playbook-doc.js +1 -1
  81. data/dist/playbook-rails-react-bindings.js +1 -1
  82. data/dist/playbook-rails.js +1 -1
  83. data/dist/playbook.css +1 -1
  84. data/lib/playbook/classnames.rb +1 -0
  85. data/lib/playbook/spacing.rb +31 -2
  86. data/lib/playbook/version.rb +1 -1
  87. metadata +32 -10
  88. data/dist/chunks/_typeahead-D-4y9pbv.js +0 -22
  89. data/dist/chunks/_weekday_stacked-Cax4nrUa.js +0 -45
  90. data/dist/chunks/lazysizes-DHz07jlL.js +0 -1
  91. /data/app/pb_kits/playbook/pb_pagination/docs/{_pagination_default.md → _pagination_default_rails.md} +0 -0
@@ -3,4 +3,6 @@ examples:
3
3
  rails:
4
4
  - pagination_default: Default
5
5
 
6
-
6
+ react:
7
+ - pagination_default: Default
8
+ - pagination_page_change: Page Change
@@ -0,0 +1,2 @@
1
+ export { default as PaginationDefault } from './_pagination_default.jsx'
2
+ export { default as PaginationPageChange } from './_pagination_page_change.jsx'
@@ -60,7 +60,6 @@ $flag-min-resolution: 192dpi;
60
60
  }
61
61
 
62
62
  .iti__flag {
63
- background-image: url("https://intl-tel-input.com/intl-tel-input/img/flags.png");
64
63
  border-radius: 1px;
65
64
  }
66
65
 
@@ -197,10 +196,4 @@ $flag-min-resolution: 192dpi;
197
196
  }
198
197
  }
199
198
  }
200
-
201
- @media (-webkit-min-device-pixel-ratio: 2), (min-resolution: $flag-min-resolution) {
202
- .iti__flag {
203
- background-image: url("https://intl-tel-input.com/intl-tel-input/img/flags.png");
204
- }
205
- }
206
199
  }
@@ -21,6 +21,8 @@ import classnames from "classnames";
21
21
  import { globalProps, GlobalProps } from "../utilities/globalProps";
22
22
  import { uniqueId } from 'lodash';
23
23
 
24
+ type ModifiedGlobalProps = Omit<GlobalProps, 'minWidth'>
25
+
24
26
  type PbPopoverProps = {
25
27
  aria?: { [key: string]: string };
26
28
  className?: string;
@@ -32,7 +34,7 @@ type PbPopoverProps = {
32
34
  reference: PopperReference & any;
33
35
  show?: boolean;
34
36
  shouldClosePopover?: (arg0: boolean) => void;
35
- } & GlobalProps & Omit<PopperProps<any>, 'children'>
37
+ } & ModifiedGlobalProps & Omit<PopperProps<any>, 'children'>
36
38
  & { children?: React.ReactChild[] | React.ReactChild }
37
39
 
38
40
  // Prop enabled default modifiers here
@@ -80,10 +82,13 @@ const Popover = (props: PbPopoverProps) => {
80
82
  targetId,
81
83
  } = props;
82
84
 
85
+ const items = globalProps(props).split(' ')
86
+ const filteredItems = items.filter(item => !item.includes('min_width'))
87
+ const filteredGlobalProps = filteredItems.join(' ')
83
88
  const popoverSpacing =
84
- globalProps(props).includes("dark") || !globalProps(props)
89
+ filteredGlobalProps.includes("dark") || !filteredGlobalProps
85
90
  ? "p_sm"
86
- : globalProps(props);
91
+ : filteredGlobalProps
87
92
  const overflowHandling = maxHeight || maxWidth ? "overflow_handling" : "";
88
93
  const zIndexStyle = zIndex ? { zIndex: zIndex } : {};
89
94
  const widthHeightStyles = () => {
@@ -100,7 +105,7 @@ const Popover = (props: PbPopoverProps) => {
100
105
  const htmlProps = buildHtmlProps(htmlOptions);
101
106
  const classes = classnames(
102
107
  buildCss("pb_popover_kit"),
103
- globalProps(props),
108
+ filteredGlobalProps,
104
109
  className
105
110
  );
106
111
 
@@ -250,4 +255,4 @@ const PbReactPopover = (props: PbPopoverProps): React.ReactElement => {
250
255
  );
251
256
  };
252
257
 
253
- export default PbReactPopover;
258
+ export default PbReactPopover;
@@ -0,0 +1,132 @@
1
+ @import "../tokens/border_radius";
2
+ @import "../tokens/colors";
3
+ @import "../tokens/spacing";
4
+ @import "../tokens/typography";
5
+
6
+ @mixin preview_first_child {
7
+ :first-child {
8
+ margin-top: 0;
9
+ }
10
+ }
11
+
12
+ @mixin preview_p {
13
+ margin: 1rem 0 0 0;
14
+ min-height: 1rem;
15
+ }
16
+
17
+ @mixin preview_code {
18
+ font-family: monospace;
19
+ background: $bg_light;
20
+ padding: 0.1rem 0.3rem;
21
+ box-shadow: 0 2px 10px $shadow;
22
+ border-radius: 0.25rem;
23
+ overflow: hidden;
24
+ }
25
+
26
+ @mixin preview_pre_codeblock {
27
+ display: inline-block;
28
+ width: 100%;
29
+ vertical-align: top;
30
+ font-family: monospace;
31
+ font-size: 0.9em;
32
+ padding: 0.5em;
33
+ overflow-x: auto;
34
+ background: $bg_dark;
35
+ padding: $space_sm;
36
+ border-radius: $border_rad_heaviest;
37
+ margin: 1.5rem 0 2rem 0;
38
+
39
+ code {
40
+ background: transparent !important;
41
+ box-shadow: none;
42
+ border: 0;
43
+ color: #faf6e4;
44
+ }
45
+ }
46
+
47
+ @mixin preview_a {
48
+ color: $primary;
49
+ border-bottom: 1px solid $primary;
50
+ &:hover {
51
+ color: $text_lt_default;
52
+ border-bottom: 1px solid $text_lt_default;
53
+ }
54
+ }
55
+
56
+ @mixin preview_blockquote {
57
+ font-size: $font_larger;
58
+ padding: $space_sm $space_md;
59
+ font-style: italic;
60
+ margin: 1rem 0 0 0;
61
+ p {
62
+ margin: 0;
63
+ }
64
+ }
65
+
66
+ @mixin preview_h1 {
67
+ font-size: $text_largest;
68
+ line-height: $text_larger;
69
+ font-weight: $bolder;
70
+ letter-spacing: $lspace_tight;
71
+ margin: 2.1rem 0 0 0;
72
+ }
73
+
74
+ @mixin preview_h2 {
75
+ font-size: $text_larger;
76
+ line-height: $text_larger;
77
+ font-weight: $bolder;
78
+ letter-spacing: $lspace_tight;
79
+ margin: 1.9rem 0 0 0;
80
+ }
81
+
82
+ @mixin preview_h3 {
83
+ font-size: $text_large;
84
+ line-height: $text_large;
85
+ font-weight: $bolder;
86
+ letter-spacing: $lspace_tight;
87
+ margin: 1.7rem 0 0 0;
88
+ }
89
+
90
+ @mixin preview_smaller_headings {
91
+ font-size: $text_base;
92
+ line-height: $text_base;
93
+ letter-spacing: $lspace_tight;
94
+ font-weight: $bolder;
95
+ margin: 1rem 0 0 0;
96
+ }
97
+
98
+ @mixin preview_hr {
99
+ margin: 2.2rem 0;
100
+ box-sizing: content-box;
101
+ overflow: hidden;
102
+ background: transparent;
103
+ border-bottom: 1px solid $transparent;
104
+ height: 1px;
105
+ padding: 0;
106
+ background-color: $border_light;
107
+ border: 0;
108
+ }
109
+
110
+ @mixin preview_ol {
111
+ margin: 1rem 0 0 0;
112
+ padding-left: $space_md;
113
+ list-style: decimal;
114
+ li {
115
+ margin: 2px 0;
116
+ p {
117
+ margin: 0;
118
+ }
119
+ }
120
+ }
121
+
122
+ @mixin preview_ul {
123
+ list-style-position: disc;
124
+ margin: 1rem 0 0 0;
125
+ padding-left: $space_md;
126
+ li {
127
+ margin: 2px 0;
128
+ p {
129
+ margin: 0;
130
+ }
131
+ }
132
+ }
@@ -6,6 +6,7 @@
6
6
  @import "../tokens/typography";
7
7
  @import "../tokens/shadows";
8
8
  @import "../tokens/transition";
9
+ @import "previewer_mixin";
9
10
 
10
11
  [class^="pb_rich_text_editor_kit"] {
11
12
  .toolbar_button {
@@ -85,109 +86,44 @@
85
86
  }
86
87
 
87
88
  code {
88
- font-family: monospace;
89
- background: $bg_light;
90
- padding: 0.1rem 0.3rem;
91
- margin: 0 5px;
92
- box-shadow: 0 2px 10px $shadow;
93
- border-radius: 0.25rem;
94
- overflow: hidden;
95
- font-size: ($text_small - 1px);
89
+ @include preview_code;
96
90
  }
97
91
 
98
92
  pre {
99
- background: $bg_dark;
100
- padding: $space_sm;
101
- border-radius: $border_rad_heaviest;
102
- margin: 1.5rem 0 2rem 0;
103
- code {
104
- background: transparent;
105
- box-shadow: none;
106
- border: 0;
107
- color: #faf6e4;
108
- }
93
+ @include preview_pre_codeblock;
109
94
  }
110
95
  a {
111
- color: $primary;
112
- border-bottom: 1px solid $primary;
113
- &:hover {
114
- color: $text_lt_default;
115
- border-bottom: 1px solid $text_lt_default;
116
- }
96
+ @include preview_a;
117
97
  }
118
98
  blockquote {
119
- font-size: $font_larger;
120
- padding: $space_sm $space_md;
121
- font-style: italic;
122
- p {
123
- margin: 0;
124
- }
99
+ @include preview_blockquote;
125
100
  }
126
101
  &:focus-visible {
127
102
  outline: unset;
128
103
  @include transition_default;
129
104
  }
130
105
  h1 {
131
- font-size: $text_largest;
132
- line-height: $text_larger;
133
- font-weight: $bolder;
134
- letter-spacing: $lspace_tight;
135
- margin: 2.1rem 0 0 0;
106
+ @include preview_h1;
136
107
  }
137
108
  h2 {
138
- font-size: $text_larger;
139
- line-height: $text_larger;
140
- font-weight: $bolder;
141
- letter-spacing: $lspace_tight;
142
- margin: 1.9rem 0 0 0;
109
+ @include preview_h2;
143
110
  }
144
111
  h3 {
145
- font-size: $text_large;
146
- line-height: $text_large;
147
- font-weight: $bolder;
148
- letter-spacing: $lspace_tight;
149
- margin: 1.7rem 0 0 0;
112
+ @include preview_h3;
150
113
  }
151
114
  h4,
152
115
  h5,
153
116
  h6 {
154
- font-size: $text_base;
155
- line-height: $text_base;
156
- letter-spacing: $lspace_tight;
157
- font-weight: $bolder;
117
+ @include preview_smaller_headings;
158
118
  }
159
119
  hr {
160
- margin: 2.2rem 0;
161
- box-sizing: content-box;
162
- overflow: hidden;
163
- background: transparent;
164
- border-bottom: 1px solid $transparent;
165
- height: 1px;
166
- padding: 0;
167
- background-color: $border_light;
168
- border: 0;
120
+ @include preview_hr;
169
121
  }
170
122
  ol {
171
- margin: 1rem 0 0 0;
172
- padding-left: $space_md;
173
- list-style: decimal;
174
- li {
175
- margin: 2px 0;
176
- p {
177
- margin: 0;
178
- }
179
- }
123
+ @include preview_ol;
180
124
  }
181
125
  ul {
182
- list-style-position: disc;
183
- margin: 1rem 0 0 0;
184
- padding-left: $space_md;
185
- li {
186
- margin: 2px 0;
187
- p {
188
- margin: 0;
189
- }
190
- }
126
+ @include preview_ul;
191
127
  }
192
128
  }
193
129
  }
@@ -233,3 +169,41 @@
233
169
  }
234
170
  }
235
171
  }
172
+ .tiptap-content {
173
+ @include preview_first_child;
174
+ a {
175
+ @include preview_a;
176
+ }
177
+ blockquote {
178
+ @include preview_blockquote;
179
+ }
180
+ h1 {
181
+ @include preview_h1;
182
+ }
183
+ h2 {
184
+ @include preview_h2;
185
+ }
186
+ h3 {
187
+ @include preview_h3;
188
+ }
189
+ h4,
190
+ h5,
191
+ h6 {
192
+ @include preview_smaller_headings;
193
+ }
194
+ hr {
195
+ @include preview_hr;
196
+ }
197
+ ol {
198
+ @include preview_ol;
199
+ }
200
+ p {
201
+ @include preview_p;
202
+ }
203
+ pre {
204
+ @include preview_pre_codeblock;
205
+ }
206
+ ul {
207
+ @include preview_ul;
208
+ }
209
+ }
@@ -0,0 +1,73 @@
1
+ import React, { useState } from 'react'
2
+ import { Button, Card, RichTextEditor } from 'playbook-ui'
3
+ import { useEditor, EditorContent } from "@tiptap/react"
4
+ import StarterKit from "@tiptap/starter-kit"
5
+ import Link from '@tiptap/extension-link'
6
+
7
+
8
+ const RichTextEditorAdvancedPreview = (props) => {
9
+
10
+ const editor = useEditor({
11
+ extensions: [
12
+ StarterKit,
13
+ Link
14
+ ],
15
+ content: "Add text here, format it, and press \"Preview Output\" to see what your stylized output will look like on the page."
16
+ })
17
+
18
+ const [showPreview, setShowPreview] = useState(false)
19
+ const [previewText, setPreviewText] = useState(<div />)
20
+
21
+ const handleChange = () => {
22
+ if (editor) {
23
+ setPreviewText(editor.getHTML())
24
+ }
25
+ }
26
+
27
+ const handleClick = () => {
28
+ handleChange()
29
+ setShowPreview(true)
30
+ }
31
+ if (!editor) {
32
+ return null
33
+ }
34
+
35
+
36
+ return (
37
+ <div>
38
+ <RichTextEditor
39
+ advancedEditor={editor}
40
+ id="content-advanced-preview-editor"
41
+ onChange={handleChange}
42
+ {...props}
43
+ >
44
+ <EditorContent editor={editor}/>
45
+ </RichTextEditor>
46
+ {showPreview && (
47
+ <Card
48
+ marginTop="md"
49
+ maxWidth="md"
50
+ >
51
+ <div
52
+ className="tiptap-content"
53
+ // eslint-disable-next-line react/no-danger
54
+ dangerouslySetInnerHTML={{ __html: previewText }}
55
+ id="advanced-preview-content"
56
+ />
57
+ </Card>
58
+ )}
59
+ {!showPreview && (
60
+ <div />
61
+ )}
62
+ <Button
63
+ id="preview-button"
64
+ marginTop="md"
65
+ onClick={handleClick}
66
+ text="Preview Output"
67
+ variant="secondary"
68
+ />
69
+ </div>
70
+ )
71
+ }
72
+
73
+ export default RichTextEditorAdvancedPreview
@@ -24,3 +24,4 @@ examples:
24
24
  - rich_text_editor_toolbar_bottom: Toolbar Bottom
25
25
  - rich_text_editor_inline: Inline
26
26
  - rich_text_editor_preview: Preview
27
+ - rich_text_editor_advanced_preview: Advanced Preview
@@ -9,4 +9,5 @@ export { default as RichTextEditorInline } from './_rich_text_editor_inline.jsx'
9
9
  export { default as RichTextEditorPreview } from './_rich_text_editor_preview.jsx'
10
10
  export { default as RichTextEditorAdvancedDefault } from './_rich_text_editor_advanced_default.jsx'
11
11
  export { default as RichTextEditorMoreExtensions } from './_rich_text_editor_more_extensions.jsx'
12
- export { default as RichTextEditorToolbarDisabled } from './_rich_text_editor_toolbar_disabled.jsx'
12
+ export { default as RichTextEditorToolbarDisabled } from './_rich_text_editor_toolbar_disabled.jsx'
13
+ export { default as RichTextEditorAdvancedPreview } from './_rich_text_editor_advanced_preview.jsx'
@@ -1,119 +1,156 @@
1
- import PbEnhancedElement from "../pb_enhanced_element";
1
+ import PbEnhancedElement from "../pb_enhanced_element"
2
2
 
3
- const STAR_RATING_SELECTOR = "[data-pb-star-rating]";
4
- const STAR_RATING_INPUT_ID = "star-rating-input";
3
+ const STAR_RATING_WRAPPER_SELECTOR = "[data-pb-star-rating-wrapper]"
4
+ const STAR_RATING_SELECTOR = "[data-pb-star-rating]"
5
+ const STAR_RATING_INPUT_DATA_SELECTOR = "[data-pb-star-rating-input]"
5
6
 
6
7
  export default class PbStarRating extends PbEnhancedElement {
7
8
  static get selector() {
8
- return STAR_RATING_SELECTOR;
9
+ return STAR_RATING_WRAPPER_SELECTOR
9
10
  }
10
11
 
11
12
  connect() {
12
- this.element.addEventListener("click", (event) => {
13
- const clickedStarId = event.currentTarget.id;
14
- this.updateStarColors(clickedStarId);
15
- this.updateHiddenInputValue(clickedStarId);
16
- });
13
+ this.addEventListeners()
14
+ this.handleFormReset()
15
+ }
16
+
17
+ addEventListeners() {
18
+ this.element.querySelectorAll(STAR_RATING_SELECTOR).forEach(star => {
19
+ star.addEventListener("click", (event) => {
20
+ const clickedStarId = event.currentTarget.id
21
+ this.updateStarColors(clickedStarId)
22
+ this.updateHiddenInputValue(clickedStarId)
23
+ this.clearFormValidation()
24
+ })
17
25
 
18
- document.querySelectorAll(STAR_RATING_SELECTOR).forEach(star => {
19
26
  star.addEventListener("mouseenter", (event) => {
20
27
  const hoveredStarId = event.currentTarget.id
21
- this.updateStarHoverColors(hoveredStarId);
28
+ this.updateStarHoverColors(hoveredStarId)
22
29
  })
23
30
 
24
31
  star.addEventListener("mouseleave", () => {
25
- this.removeStarHoverColors();
32
+ this.removeStarHoverColors()
26
33
  })
27
34
 
28
35
  star.addEventListener("keydown", (event) => {
29
36
  if (event.key === 'Enter' || event.key === ' ') {
30
- event.preventDefault();
31
- this.handleStarClick(star.id);
37
+ event.preventDefault()
38
+ this.handleStarClick(star.id)
32
39
  }
33
40
  })
34
41
  })
35
42
  }
36
43
 
37
44
  handleStarClick(starId) {
38
- this.updateStarColors(starId);
39
- this.updateHiddenInputValue(starId);
45
+ this.updateStarColors(starId)
46
+ this.updateHiddenInputValue(starId)
40
47
  }
41
48
 
42
49
  updateStarColors(clickedStarId) {
43
- const allStars = document.querySelectorAll(STAR_RATING_SELECTOR);
50
+ const allStars = this.element.querySelectorAll(STAR_RATING_SELECTOR)
44
51
 
45
52
  allStars.forEach(star => {
46
- const starId = star.id;
47
- const icon = star.querySelector(".interactive-star-icon");
53
+ const starId = star.id
54
+ const icon = star.querySelector(".interactive-star-icon")
48
55
 
49
56
  if (icon) {
50
57
  if (starId <= clickedStarId) {
51
58
  if (star.classList.contains("yellow_star")) {
52
- icon.classList.add("yellow-star-selected");
59
+ icon.classList.add("yellow-star-selected")
53
60
  } else if (star.classList.contains("primary_star_light")) {
54
- icon.classList.add("primary-star-selected");
61
+ icon.classList.add("primary-star-selected")
55
62
  } else if (star.classList.contains("primary_star_dark")) {
56
- icon.classList.add("primary-star-selected");
63
+ icon.classList.add("primary-star-selected")
57
64
  } else if (star.classList.contains("subtle_star_light")) {
58
- icon.classList.add("subtle-star-selected");
65
+ icon.classList.add("subtle-star-selected")
59
66
  } else if (star.classList.contains("subtle_star_dark")) {
60
- icon.classList.add("subtle-star-selected");
67
+ icon.classList.add("subtle-star-selected")
61
68
  } else {
62
- icon.classList.add("yellow-star-selected");
69
+ icon.classList.add("yellow-star-selected")
63
70
  }
64
71
  } else {
65
- icon.classList.remove("yellow-star-selected", "primary-star-selected", "subtle-star-selected");
72
+ icon.classList.remove("yellow-star-selected", "primary-star-selected", "subtle-star-selected")
66
73
  }
67
- icon.classList.remove("star-hovered");
74
+ icon.classList.remove("star-hovered")
68
75
  }
69
- });
76
+ })
70
77
  }
71
78
 
72
79
  updateHiddenInputValue(value) {
73
- const hiddenInput = document.getElementById(STAR_RATING_INPUT_ID);
80
+ const hiddenInput = this.element.querySelector(STAR_RATING_INPUT_DATA_SELECTOR)
74
81
  if (hiddenInput) {
75
- hiddenInput.value = value;
82
+ hiddenInput.value = value
76
83
  }
77
84
  }
78
85
 
79
86
  updateStarHoverColors(hoveredStarId) {
80
- const allStars = document.querySelectorAll(STAR_RATING_SELECTOR);
87
+ const allStars = this.element.querySelectorAll(STAR_RATING_SELECTOR)
81
88
 
82
89
  allStars.forEach(star => {
83
- const starId = star.id;
84
- const icon = star.querySelector(".interactive-star-icon");
90
+ const starId = star.id
91
+ const icon = star.querySelector(".interactive-star-icon")
85
92
 
86
93
  if (icon) {
87
94
  if (starId <= hoveredStarId) {
88
95
  if (!icon.classList.contains("yellow-star-selected") &&
89
96
  !icon.classList.contains("primary-star-selected") &&
90
97
  !icon.classList.contains("subtle-star-selected")) {
91
- icon.classList.add("star-hovered");
98
+ icon.classList.add("star-hovered")
92
99
  }
93
100
  } else {
94
- icon.classList.remove("star-hovered");
101
+ icon.classList.remove("star-hovered")
95
102
  }
96
103
  }
97
- });
104
+ })
98
105
  }
99
106
 
100
107
 
101
108
  removeStarHoverColors() {
102
- const allStars = document.querySelectorAll(STAR_RATING_SELECTOR);
109
+ const allStars = this.element.querySelectorAll(STAR_RATING_SELECTOR)
103
110
 
104
111
  allStars.forEach(star => {
105
- const icon = star.querySelector(".interactive-star-icon");
112
+ const icon = star.querySelector(".interactive-star-icon")
106
113
  if (icon) {
107
114
  if (!icon.classList.contains("yellow-star-selected") &&
108
115
  !icon.classList.contains("primary-star-selected") &&
109
116
  !icon.classList.contains("subtle-star-selected")) {
110
- icon.classList.remove("star-hovered");
117
+ icon.classList.remove("star-hovered")
111
118
  }
112
119
  }
113
- });
120
+ })
114
121
  }
115
122
 
116
123
  isStarSelected() {
117
- return document.querySelectorAll(".yellow-star-selected, .primary-star-selected, .subtle-star-selected").length > 0;
124
+ return this.element.querySelectorAll(".yellow-star-selected, .primary-star-selected, .subtle-star-selected").length > 0
125
+ }
126
+
127
+ handleFormReset() {
128
+ const form = this.element.closest("form")
129
+ if (form) {
130
+ form.addEventListener("reset", () => {
131
+ this.updateHiddenInputValue("")
132
+ this.resetStarRatingValues()
133
+ })
134
+ }
135
+ }
136
+
137
+ resetStarRatingValues() {
138
+ const allStars = this.element.querySelectorAll(STAR_RATING_SELECTOR)
139
+ allStars.forEach(star => {
140
+ const icon = star.querySelector(".interactive-star-icon")
141
+ if (icon) {
142
+ icon.classList.remove("yellow-star-selected", "primary-star-selected", "subtle-star-selected")
143
+ }
144
+ })
145
+ }
146
+
147
+ clearFormValidation() {
148
+ const hiddenInput = this.element.querySelector(STAR_RATING_INPUT_DATA_SELECTOR)
149
+ if (hiddenInput.checkValidity()) {
150
+ const errorLabelElement = this.element.querySelector(".pb_body_kit_negative")
151
+ if (errorLabelElement) {
152
+ errorLabelElement.remove()
153
+ }
154
+ }
118
155
  }
119
156
  }
@@ -39,11 +39,13 @@
39
39
  <% end %>
40
40
 
41
41
  <% else %>
42
- <%= pb_rails("flex", props: { orientation: "column" }) do %>
42
+ <%= pb_rails("flex", props: { data: {"pb-star-rating-wrapper": "true" }, orientation: "column" }) do %>
43
43
  <% if object.label.present? %>
44
44
  <%= pb_rails("caption", props: {text: object.label, margin_bottom:"xs"}) %>
45
45
  <% end %>
46
- <input type="hidden" id="star-rating-input" value="" name="<%= object.name %>"/>
46
+
47
+ <%= hidden_input_tag %>
48
+
47
49
  <%= pb_rails("flex", props: { orientation: "row" }) do %>
48
50
  <% object.denominator.times do |index| %>
49
51
  <div data-pb-star-rating id="<%= index + 1 %>" class="<%= star_color %>">