coveragebook_components 0.7.10 → 0.8.0.beta.1
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.
- checksums.yaml +4 -4
- data/app/assets/build/coco/app.css +1065 -148
- data/app/assets/build/coco/app.js +255 -47
- data/app/assets/build/coco/book.css +26 -0
- data/app/assets/css/app/tippy.css +4 -0
- data/app/components/coco/app/blocks/header/header.css +43 -0
- data/app/components/coco/app/blocks/header/header.html.erb +30 -0
- data/app/components/coco/app/blocks/header/header.js +11 -0
- data/app/components/coco/app/blocks/header/header.rb +35 -0
- data/app/components/coco/app/blocks/nav_drawer/nav_drawer.css +48 -3
- data/app/components/coco/app/blocks/nav_drawer/nav_drawer.html.erb +14 -6
- data/app/components/coco/app/blocks/nav_drawer/nav_drawer.js +18 -1
- data/app/components/coco/app/blocks/nav_drawer/nav_drawer.rb +26 -1
- data/app/components/coco/app/blocks/sidebar_nav/sidebar_nav.css +104 -0
- data/app/components/coco/app/blocks/sidebar_nav/sidebar_nav.html.erb +42 -0
- data/app/components/coco/app/blocks/sidebar_nav/sidebar_nav.js +28 -0
- data/app/components/coco/app/blocks/sidebar_nav/sidebar_nav.rb +28 -0
- data/app/components/coco/app/blocks/sidebar_nav_item/sidebar_nav_item.css +165 -0
- data/app/components/coco/app/blocks/sidebar_nav_item/sidebar_nav_item.html.erb +43 -0
- data/app/components/coco/app/blocks/sidebar_nav_item/sidebar_nav_item.js +41 -0
- data/app/components/coco/app/blocks/sidebar_nav_item/sidebar_nav_item.rb +98 -0
- data/app/components/coco/app/elements/alert/alert.css +65 -18
- data/app/components/coco/app/elements/alert/alert.html.erb +4 -4
- data/app/components/coco/app/elements/alert/alert.js +4 -3
- data/app/components/coco/app/elements/alert/alert.rb +10 -0
- data/app/components/coco/app/elements/button/button.css +58 -0
- data/app/components/coco/app/elements/button/button.rb +1 -1
- data/app/components/coco/app/elements/button_group/button_group.rb +4 -0
- data/app/components/coco/app/elements/color_picker/color_picker.rb +1 -1
- data/app/components/coco/app/elements/menu/menu.css +1 -0
- data/app/components/coco/app/elements/menu/menu.html.erb +1 -1
- data/app/components/coco/app/elements/menu/menu.rb +2 -1
- data/app/components/coco/app/elements/menu_items/user_profile/user_profile.css +22 -0
- data/app/components/coco/app/elements/menu_items/user_profile/user_profile.html.erb +17 -0
- data/app/components/coco/app/elements/menu_items/user_profile/user_profile.rb +20 -0
- data/app/components/coco/app/elements/notice/notice.css +4 -0
- data/app/components/coco/app/elements/snackbar/snackbar.css +8 -1
- data/app/components/coco/app/elements/snackbar/snackbar.rb +2 -2
- data/app/components/coco/app/elements/system_banner/system_banner.html.erb +2 -1
- data/app/components/coco/app/elements/system_banner/system_banner.js +35 -2
- data/app/components/coco/app/elements/system_banner/system_banner.rb +47 -3
- data/app/components/coco/app/layouts/application/application.css +104 -4
- data/app/components/coco/app/layouts/application/application.html.erb +28 -7
- data/app/components/coco/app/layouts/application/application.js +16 -0
- data/app/components/coco/app/layouts/application/application.rb +11 -3
- data/app/components/coco/base/avatar/avatar.css +25 -0
- data/app/components/coco/base/avatar/avatar.rb +20 -0
- data/app/components/coco/base/modal/modal.html.erb +1 -1
- data/app/components/coco/concerns/accepts_tag_attributes.rb +6 -2
- data/app/components/coco/concerns/acts_as_button_group.rb +5 -0
- data/app/helpers/coco/app_helper.rb +16 -0
- data/app/helpers/coco/base_helper.rb +4 -0
- data/config/tokens.cjs +4 -1
- data/lib/coco.rb +1 -1
- metadata +22 -10
- data/app/components/coco/app/blocks/banner/banner.css +0 -5
- data/app/components/coco/app/blocks/banner/banner.rb +0 -8
- data/app/components/coco/app/blocks/nav_bar/nav_bar.css +0 -51
- data/app/components/coco/app/blocks/nav_bar/nav_bar.html.erb +0 -23
- data/app/components/coco/app/blocks/nav_bar/nav_bar.js +0 -31
- data/app/components/coco/app/blocks/nav_bar/nav_bar.rb +0 -19
@@ -3,7 +3,7 @@
|
|
3
3
|
@apply rounded-xl overflow-hidden border border-transparent @container;
|
4
4
|
|
5
5
|
.alert-container {
|
6
|
-
@apply flex items-start
|
6
|
+
@apply flex items-start px-4 py-2 relative;
|
7
7
|
}
|
8
8
|
|
9
9
|
.alert-icon {
|
@@ -23,7 +23,7 @@
|
|
23
23
|
}
|
24
24
|
|
25
25
|
.alert-title {
|
26
|
-
@apply text-
|
26
|
+
@apply text-heading-6 font-bold;
|
27
27
|
}
|
28
28
|
|
29
29
|
.alert-message {
|
@@ -34,10 +34,6 @@
|
|
34
34
|
}
|
35
35
|
}
|
36
36
|
|
37
|
-
&.with-title .alert-message {
|
38
|
-
@apply mt-1;
|
39
|
-
}
|
40
|
-
|
41
37
|
.alert-actions {
|
42
38
|
@apply space-x-1 flex items-center;
|
43
39
|
}
|
@@ -56,7 +52,7 @@
|
|
56
52
|
@apply rounded-none;
|
57
53
|
|
58
54
|
.alert-container {
|
59
|
-
@apply @[1000px]:justify-center;
|
55
|
+
@apply @[1000px]:justify-center px-app;
|
60
56
|
}
|
61
57
|
|
62
58
|
.alert-body {
|
@@ -71,14 +67,36 @@
|
|
71
67
|
@apply flex-none;
|
72
68
|
|
73
69
|
.coco-button .button-element {
|
74
|
-
@apply text-content-dark-2 hover:text-content-dark-1;
|
70
|
+
@apply text-content-dark-2 hover:text-content-dark-1 bg-transparent hover:bg-white/10 transition;
|
75
71
|
}
|
76
72
|
}
|
77
73
|
}
|
78
74
|
|
75
|
+
/* Condensed */
|
76
|
+
|
77
|
+
&[data-condensed="true"] {
|
78
|
+
.alert-icon {
|
79
|
+
.coco-icon {
|
80
|
+
@apply w-4 h-4;
|
81
|
+
}
|
82
|
+
}
|
83
|
+
|
84
|
+
.alert-body {
|
85
|
+
@apply pl-3;
|
86
|
+
}
|
87
|
+
|
88
|
+
.alert-title {
|
89
|
+
@apply text-para-sm;
|
90
|
+
}
|
91
|
+
|
92
|
+
.alert-message {
|
93
|
+
@apply text-para-sm;
|
94
|
+
}
|
95
|
+
}
|
96
|
+
|
79
97
|
/* Layout */
|
80
98
|
|
81
|
-
@apply app-alert-stacked @[
|
99
|
+
@apply app-alert-stacked @[576px]:app-alert-multi-line;
|
82
100
|
|
83
101
|
&[data-single-line="true"]:not(.force-multi-line) {
|
84
102
|
@apply @[1000px]:app-alert-single-line;
|
@@ -95,7 +113,7 @@
|
|
95
113
|
}
|
96
114
|
|
97
115
|
&[data-theme*="vivid"] {
|
98
|
-
@apply border-none;
|
116
|
+
@apply border-none antialiased;
|
99
117
|
|
100
118
|
.alert-content {
|
101
119
|
@apply text-content-light-1;
|
@@ -186,13 +204,16 @@
|
|
186
204
|
|
187
205
|
@layer utilities {
|
188
206
|
.app-alert-stacked {
|
189
|
-
.alert-
|
190
|
-
|
191
|
-
margin-bottom: 2px;
|
207
|
+
.alert-container {
|
208
|
+
@apply py-4;
|
192
209
|
}
|
193
210
|
|
194
211
|
.alert-actions {
|
195
|
-
@apply mt-
|
212
|
+
@apply mt-3;
|
213
|
+
}
|
214
|
+
|
215
|
+
&.with-title .alert-message {
|
216
|
+
@apply mt-1;
|
196
217
|
}
|
197
218
|
|
198
219
|
&[data-dismissable="true"] {
|
@@ -208,7 +229,7 @@
|
|
208
229
|
|
209
230
|
.app-alert-multi-line {
|
210
231
|
.alert-container {
|
211
|
-
@apply items-center;
|
232
|
+
@apply items-center py-2.5;
|
212
233
|
}
|
213
234
|
|
214
235
|
.alert-icon {
|
@@ -227,22 +248,34 @@
|
|
227
248
|
margin-bottom: 0;
|
228
249
|
}
|
229
250
|
|
251
|
+
&.with-title .alert-message {
|
252
|
+
@apply mt-1;
|
253
|
+
}
|
254
|
+
|
255
|
+
&[data-condensed="true"].with-title .alert-message {
|
256
|
+
@apply mt-0.5;
|
257
|
+
}
|
258
|
+
|
230
259
|
.alert-actions {
|
231
260
|
@apply mt-0 ml-auto;
|
232
261
|
}
|
233
262
|
|
234
263
|
&[data-dismissable="true"] {
|
235
|
-
.alert-
|
236
|
-
@apply pr-
|
264
|
+
.alert-body {
|
265
|
+
@apply pr-10;
|
237
266
|
}
|
238
267
|
|
239
268
|
.alert-dismiss {
|
240
|
-
@apply
|
269
|
+
@apply absolute right-3 top-1/2 -translate-y-1/2;
|
241
270
|
}
|
242
271
|
}
|
243
272
|
}
|
244
273
|
|
245
274
|
.app-alert-single-line {
|
275
|
+
.alert-container {
|
276
|
+
@apply py-3;
|
277
|
+
}
|
278
|
+
|
246
279
|
.alert-content {
|
247
280
|
@apply flex items-center w-full space-x-2;
|
248
281
|
}
|
@@ -251,8 +284,22 @@
|
|
251
284
|
@apply whitespace-nowrap;
|
252
285
|
}
|
253
286
|
|
287
|
+
&.with-title .alert-message {
|
288
|
+
@apply mt-0;
|
289
|
+
}
|
290
|
+
|
254
291
|
.alert-link {
|
255
292
|
@apply hidden;
|
256
293
|
}
|
294
|
+
|
295
|
+
&[data-dismissable="true"] {
|
296
|
+
.alert-container {
|
297
|
+
@apply px-12;
|
298
|
+
}
|
299
|
+
|
300
|
+
.alert-dismiss {
|
301
|
+
@apply absolute right-[21px] top-1/2 -translate-y-1/2;
|
302
|
+
}
|
303
|
+
}
|
257
304
|
}
|
258
305
|
}
|
@@ -1,8 +1,8 @@
|
|
1
1
|
<%= render component_tag(x: {
|
2
2
|
data: "appAlert",
|
3
|
-
show: "!dismissed",
|
4
3
|
bind: "root",
|
5
|
-
|
4
|
+
show: "!dismissed",
|
5
|
+
cloak: (true if cloak?)
|
6
6
|
}, class: {
|
7
7
|
"with-title": title?,
|
8
8
|
"vivid": vivid?
|
@@ -44,7 +44,7 @@
|
|
44
44
|
<%= coco_button(
|
45
45
|
*@action_data[:args],
|
46
46
|
**@action_data[:kwargs],
|
47
|
-
size:
|
47
|
+
size: button_size,
|
48
48
|
&@action_data[:block]
|
49
49
|
) %>
|
50
50
|
</div>
|
@@ -58,7 +58,7 @@
|
|
58
58
|
<%= coco_button(
|
59
59
|
*@secondary_action_data[:args],
|
60
60
|
**@secondary_action_data[:kwargs],
|
61
|
-
size:
|
61
|
+
size: button_size,
|
62
62
|
&@secondary_action_data[:block]
|
63
63
|
) %>
|
64
64
|
</div>
|
@@ -21,18 +21,19 @@ export default CocoComponent("appAlert", () => {
|
|
21
21
|
},
|
22
22
|
|
23
23
|
remove() {
|
24
|
+
this.$nextTick(() => this.$dispatch("alert:removed", { alert: this }));
|
24
25
|
this.$root.remove();
|
25
26
|
},
|
26
27
|
|
27
28
|
checkSingleLineWrap({ height }) {
|
28
|
-
|
29
|
+
this.forceMultiLine = false;
|
30
|
+
this.$nextTick(() => {
|
29
31
|
this.forceMultiLine = height > 24 && this.$options.singleLine;
|
30
|
-
}
|
32
|
+
});
|
31
33
|
},
|
32
34
|
|
33
35
|
root: {
|
34
36
|
"x-options": '["dismissable", "singleLine"]',
|
35
|
-
"x-show": "!dismissed",
|
36
37
|
":class": "{'force-multi-line': forceMultiLine}",
|
37
38
|
},
|
38
39
|
};
|
@@ -22,6 +22,8 @@ module Coco
|
|
22
22
|
accepts_option :banner, from: [true, false], default: false
|
23
23
|
accepts_option :theme, from: THEMES, default: "info"
|
24
24
|
accepts_option :single_line, from: [true, false]
|
25
|
+
accepts_option :cloak, from: [true, false], default: true, private: true
|
26
|
+
accepts_option :condensed, from: [true, false], default: false
|
25
27
|
|
26
28
|
renders_one :title
|
27
29
|
|
@@ -58,6 +60,10 @@ module Coco
|
|
58
60
|
get_option_value(:single_line)
|
59
61
|
end
|
60
62
|
|
63
|
+
def cloak?
|
64
|
+
get_option_value(:cloak)
|
65
|
+
end
|
66
|
+
|
61
67
|
def vivid?
|
62
68
|
theme = get_option_value(:theme)
|
63
69
|
theme.to_s.match?(/vivid$/)
|
@@ -66,6 +72,10 @@ module Coco
|
|
66
72
|
def unvividify(theme)
|
67
73
|
theme.to_s.match?(/vivid$/) ? theme.to_s.underscore.gsub("_vivid", "").to_sym : theme
|
68
74
|
end
|
75
|
+
|
76
|
+
def button_size
|
77
|
+
get_option_value(:condensed) ? :xs : :sm
|
78
|
+
end
|
69
79
|
end
|
70
80
|
end
|
71
81
|
end
|
@@ -286,6 +286,10 @@
|
|
286
286
|
|
287
287
|
/* Responsive resizing */
|
288
288
|
|
289
|
+
&[data-size="xs"] {
|
290
|
+
@apply app-button-xs;
|
291
|
+
}
|
292
|
+
|
289
293
|
&[data-size="sm"] {
|
290
294
|
@apply app-button-sm;
|
291
295
|
}
|
@@ -299,6 +303,10 @@
|
|
299
303
|
}
|
300
304
|
|
301
305
|
@media screen(md) {
|
306
|
+
&[data-size-md="xs"] {
|
307
|
+
@apply app-button-xs;
|
308
|
+
}
|
309
|
+
|
302
310
|
&[data-size-md="sm"] {
|
303
311
|
@apply app-button-sm;
|
304
312
|
}
|
@@ -313,6 +321,10 @@
|
|
313
321
|
}
|
314
322
|
|
315
323
|
@media screen(lg) {
|
324
|
+
&[data-size-lg="xs"] {
|
325
|
+
@apply app-button-xs;
|
326
|
+
}
|
327
|
+
|
316
328
|
&[data-size-lg="sm"] {
|
317
329
|
@apply app-button-sm;
|
318
330
|
}
|
@@ -327,6 +339,10 @@
|
|
327
339
|
}
|
328
340
|
|
329
341
|
@media screen(xl) {
|
342
|
+
&[data-size-xl="xs"] {
|
343
|
+
@apply app-button-xs;
|
344
|
+
}
|
345
|
+
|
330
346
|
&[data-size-xl="sm"] {
|
331
347
|
@apply app-button-sm;
|
332
348
|
}
|
@@ -341,6 +357,11 @@
|
|
341
357
|
}
|
342
358
|
|
343
359
|
@media screen(2xl) {
|
360
|
+
&[data-size-xxl="xs"],
|
361
|
+
&[data-size-2xl="xs"] {
|
362
|
+
@apply app-button-xs;
|
363
|
+
}
|
364
|
+
|
344
365
|
&[data-size-xxl="sm"],
|
345
366
|
&[data-size-2xl="sm"] {
|
346
367
|
@apply app-button-sm;
|
@@ -358,6 +379,10 @@
|
|
358
379
|
}
|
359
380
|
|
360
381
|
@media screen(max) {
|
382
|
+
&[data-size-max="xs"] {
|
383
|
+
@apply app-button-xs;
|
384
|
+
}
|
385
|
+
|
361
386
|
&[data-size-max="sm"] {
|
362
387
|
@apply app-button-sm;
|
363
388
|
}
|
@@ -374,6 +399,39 @@
|
|
374
399
|
}
|
375
400
|
|
376
401
|
@layer utilities {
|
402
|
+
.app-button-xs {
|
403
|
+
.button-content {
|
404
|
+
@apply text-label-xs;
|
405
|
+
}
|
406
|
+
|
407
|
+
.button-icon [data-component="icon"],
|
408
|
+
.button-toggle {
|
409
|
+
@apply w-3.5 h-3.5;
|
410
|
+
}
|
411
|
+
|
412
|
+
&[data-theme] {
|
413
|
+
.button-element {
|
414
|
+
@apply py-2 px-3;
|
415
|
+
}
|
416
|
+
|
417
|
+
&.icon-only > .button-element .button-icon,
|
418
|
+
&[data-collapsed="true"] > .button-element .button-icon {
|
419
|
+
@apply -ml-1.5 -mr-1.5;
|
420
|
+
}
|
421
|
+
}
|
422
|
+
|
423
|
+
&[data-theme|="text"] {
|
424
|
+
.button-element {
|
425
|
+
@apply px-1;
|
426
|
+
}
|
427
|
+
|
428
|
+
&.icon-only > .button-element .button-icon,
|
429
|
+
&[data-collapsed="true"] > .button-element .button-icon {
|
430
|
+
@apply px-2;
|
431
|
+
}
|
432
|
+
}
|
433
|
+
}
|
434
|
+
|
377
435
|
.app-button-sm {
|
378
436
|
.button-content {
|
379
437
|
@apply text-label-sm;
|
@@ -5,9 +5,10 @@ module Coco
|
|
5
5
|
include Concerns::ActsAsButtonGroup
|
6
6
|
include Concerns::AcceptsOptions
|
7
7
|
|
8
|
-
accepts_option :size, from: [:sm, :md, nil], default: :sm
|
8
|
+
accepts_option :size, from: [:xs, :sm, :md, nil], default: :sm
|
9
9
|
|
10
10
|
renders_many :htmls, ->(*args, **kwargs, &block) do
|
11
|
+
init_button_group
|
11
12
|
items << block.call
|
12
13
|
end
|
13
14
|
|
@@ -0,0 +1,22 @@
|
|
1
|
+
@layer components {
|
2
|
+
[data-coco][data-component="app-user-profile"] {
|
3
|
+
@apply px-4 py-1.5 grid grid-rows-1 gap-3;
|
4
|
+
grid-template-columns: min-content 1fr;
|
5
|
+
|
6
|
+
.user-profile-avatar {
|
7
|
+
@apply flex items-center;
|
8
|
+
}
|
9
|
+
|
10
|
+
.user-profile-details {
|
11
|
+
@apply space-y-1;
|
12
|
+
}
|
13
|
+
|
14
|
+
.user-profile-name {
|
15
|
+
@apply font-semibold truncate;
|
16
|
+
}
|
17
|
+
|
18
|
+
.user-profile-email {
|
19
|
+
@apply text-gray-500 text-label-sm italic truncate;
|
20
|
+
}
|
21
|
+
}
|
22
|
+
}
|
@@ -0,0 +1,17 @@
|
|
1
|
+
<%= render component_tag do %>
|
2
|
+
<div class="user-profile-avatar">
|
3
|
+
<%= avatar %>
|
4
|
+
</div>
|
5
|
+
<div class="user-profile-details">
|
6
|
+
<% if name.present? %>
|
7
|
+
<h5 class="user-profile-name">
|
8
|
+
<%= name %>
|
9
|
+
</h5>
|
10
|
+
<% end %>
|
11
|
+
<% if email.present? %>
|
12
|
+
<div class="user-profile-email">
|
13
|
+
<%= email %>
|
14
|
+
</div>
|
15
|
+
<% end %>
|
16
|
+
</div>
|
17
|
+
<% end %>
|
@@ -0,0 +1,20 @@
|
|
1
|
+
module Coco
|
2
|
+
module App
|
3
|
+
module Elements
|
4
|
+
module MenuItems
|
5
|
+
class UserProfile < Coco::Component
|
6
|
+
renders_one :avatar, ->(**kwargs) do
|
7
|
+
Coco::Avatar.new(name: name, **kwargs, size: :lg)
|
8
|
+
end
|
9
|
+
|
10
|
+
attr_reader :name, :email
|
11
|
+
|
12
|
+
def initialize(name:, email:, **)
|
13
|
+
@name = name
|
14
|
+
@email = email
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -1,3 +1,9 @@
|
|
1
|
+
@layer base {
|
2
|
+
:root {
|
3
|
+
--snackbar-bottom-offset: theme(spacing.8);
|
4
|
+
}
|
5
|
+
}
|
6
|
+
|
1
7
|
@layer components {
|
2
8
|
[data-coco][data-component="app-snackbar"] {
|
3
9
|
@apply bg-background-dark-2 rounded-xl overflow-hidden shadow-xl w-full;
|
@@ -46,7 +52,8 @@
|
|
46
52
|
}
|
47
53
|
|
48
54
|
&[data-position="fixed"] {
|
49
|
-
@apply fixed
|
55
|
+
@apply fixed left-1/2 -translate-x-1/2;
|
56
|
+
bottom: var(--snackbar-bottom-offset);
|
50
57
|
z-index: 10001;
|
51
58
|
}
|
52
59
|
|
@@ -14,8 +14,8 @@ module Coco
|
|
14
14
|
|
15
15
|
accepts_option :theme, from: [:positive, :warning, :negative, :pending]
|
16
16
|
|
17
|
-
renders_one :action, ->(**kwargs, &block) do
|
18
|
-
|
17
|
+
renders_one :action, ->(*args, **kwargs, &block) do
|
18
|
+
coco_button(*args, **kwargs, theme: :blank, size: :sm, icon: nil, &block)
|
19
19
|
end
|
20
20
|
|
21
21
|
before_render do
|
@@ -1,5 +1,38 @@
|
|
1
1
|
import { CocoComponent } from "@js/coco";
|
2
|
+
import Cookies from "js-cookie";
|
2
3
|
|
3
|
-
export default CocoComponent("appSystemBanner", () => {
|
4
|
-
return {
|
4
|
+
export default CocoComponent("appSystemBanner", (opts = {}) => {
|
5
|
+
return {
|
6
|
+
cookieName: null,
|
7
|
+
cookieValue: null,
|
8
|
+
cookieExpiry: null,
|
9
|
+
|
10
|
+
init() {
|
11
|
+
this.cookieName = opts.cookieName;
|
12
|
+
this.cookieValue = opts.cookieValue;
|
13
|
+
this.cookieExpiry = opts.cookieExpiry;
|
14
|
+
},
|
15
|
+
|
16
|
+
onDismiss() {
|
17
|
+
this.$dispatch("banner:dismiss", { banner: this });
|
18
|
+
if (this.shouldSetCookie) {
|
19
|
+
Cookies.set(this.cookieName, this.cookieValue, {
|
20
|
+
expires: this.cookieExpiry,
|
21
|
+
});
|
22
|
+
}
|
23
|
+
},
|
24
|
+
|
25
|
+
remove() {
|
26
|
+
this.$root.remove();
|
27
|
+
},
|
28
|
+
|
29
|
+
get shouldSetCookie() {
|
30
|
+
return Number.isInteger(this.cookieExpiry);
|
31
|
+
},
|
32
|
+
|
33
|
+
root: {
|
34
|
+
"@alert:dismiss": "onDismiss",
|
35
|
+
"@alert:removed": "remove",
|
36
|
+
},
|
37
|
+
};
|
5
38
|
});
|
@@ -5,17 +5,61 @@ module Coco
|
|
5
5
|
include Concerns::AcceptsOptions
|
6
6
|
include Concerns::WrapsComponent
|
7
7
|
|
8
|
+
accepts_option :dismissable, from: [true, false], default: false
|
9
|
+
|
8
10
|
wraps_component :alert do |args|
|
9
11
|
theme = vivid_theme_name(args.fetch(:theme, nil)) || :info_vivid
|
10
|
-
Coco::App::Elements::Alert.new(
|
12
|
+
Coco::App::Elements::Alert.new(
|
13
|
+
**args,
|
14
|
+
theme: theme,
|
15
|
+
banner: true,
|
16
|
+
cloak: false,
|
17
|
+
single_line: true,
|
18
|
+
dismissable: dismissable?,
|
19
|
+
condensed: true
|
20
|
+
)
|
11
21
|
end
|
12
22
|
|
13
23
|
%i[title action secondary_action link].each do |slot_name|
|
14
|
-
renders_one slot_name, ->(**kwargs, &block) do
|
15
|
-
alert.send("with_#{slot_name}".to_sym, **kwargs, &block)
|
24
|
+
renders_one slot_name, ->(*args, **kwargs, &block) do
|
25
|
+
alert.send("with_#{slot_name}".to_sym, *args, **kwargs, &block)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
before_render do
|
30
|
+
if dismissable? && id.blank?
|
31
|
+
raise ArgumentError, "Dismissable banners must be given an ID"
|
16
32
|
end
|
17
33
|
end
|
18
34
|
|
35
|
+
attr_reader :dismiss_for, :id
|
36
|
+
|
37
|
+
def initialize(id: nil, dismiss_for: nil, **)
|
38
|
+
@id = id
|
39
|
+
@dismiss_for = dismiss_for
|
40
|
+
set_tag_attr(:id, id)
|
41
|
+
end
|
42
|
+
|
43
|
+
def dismissable?
|
44
|
+
get_option_value(:dismissable) == true
|
45
|
+
end
|
46
|
+
|
47
|
+
def render?
|
48
|
+
helpers.cookies[dismiss_cookie_name] != "true"
|
49
|
+
end
|
50
|
+
|
51
|
+
def dismiss_cookie_name
|
52
|
+
"cb_system_banner_#{tag_attr(:id)&.underscore}_dismissed".to_sym
|
53
|
+
end
|
54
|
+
|
55
|
+
def alpine_data
|
56
|
+
dismissable? ? {
|
57
|
+
cookie_name: dismiss_cookie_name,
|
58
|
+
cookie_expiry: dismiss_for&.in_days&.to_i,
|
59
|
+
cookie_value: "true"
|
60
|
+
} : {}
|
61
|
+
end
|
62
|
+
|
19
63
|
private
|
20
64
|
|
21
65
|
def vivid_theme_name(theme)
|