coveragebook_components 0.10.0 → 0.10.1.beta.0

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 (140) hide show
  1. checksums.yaml +4 -4
  2. data/app/assets/build/coco/app.css +4339 -3025
  3. data/app/assets/build/coco/app.js +116 -104
  4. data/app/assets/build/coco/book.css +1492 -92
  5. data/app/assets/build/coco/book.js +278 -17
  6. data/app/assets/css/app/tippy.css +1 -1
  7. data/app/assets/css/app.css +3 -3
  8. data/app/assets/css/{base/base.css → base.css} +14 -7
  9. data/app/assets/css/book.css +2 -2
  10. data/app/assets/css/{libs → shared}/tippy.css +20 -1
  11. data/app/assets/css/shared/utils/text.css +143 -0
  12. data/app/assets/js/app.js +2 -2
  13. data/app/assets/js/book.js +2 -2
  14. data/app/assets/js/libs/alpine/directives/dropdown.js +1 -1
  15. data/app/assets/js/libs/alpine/directives/tooltip.js +1 -1
  16. data/app/assets/js/shared/components.js +4 -0
  17. data/app/components/coco/app/blocks/header/header.js +1 -1
  18. data/app/components/coco/app/blocks/header/header.rb +2 -2
  19. data/app/components/coco/app/blocks/nav_drawer/nav_drawer.css +4 -0
  20. data/app/components/coco/app/blocks/nav_drawer/nav_drawer.js +1 -1
  21. data/app/components/coco/app/blocks/sidebar_nav/item/item.css +3 -3
  22. data/app/components/coco/app/blocks/sidebar_nav/item/item.js +2 -2
  23. data/app/components/coco/app/blocks/sidebar_nav/menu/menu.css +3 -3
  24. data/app/components/coco/app/blocks/sidebar_nav/menu/menu.js +1 -1
  25. data/app/components/coco/app/blocks/sidebar_nav/navbar/navbar.js +1 -1
  26. data/app/components/coco/app/blocks/slide_editor/slide_editor.js +1 -1
  27. data/app/components/coco/app/elements/alert/alert.css +4 -4
  28. data/app/components/coco/app/elements/alert/alert.js +1 -1
  29. data/app/components/coco/app/elements/color_picker/color_picker.css +2 -2
  30. data/app/components/coco/app/elements/color_picker/color_picker.js +1 -1
  31. data/app/components/coco/app/elements/color_picker_button/color_picker_button.js +1 -1
  32. data/app/components/coco/app/elements/color_picker_button/color_picker_button.rb +3 -3
  33. data/app/components/coco/app/elements/confirm_panel/confirm_panel.css +1 -1
  34. data/app/components/coco/app/elements/confirm_panel/confirm_panel.js +1 -1
  35. data/app/components/coco/app/elements/image_picker/image_picker.css +4 -4
  36. data/app/components/coco/app/elements/image_picker/image_picker.js +1 -1
  37. data/app/components/coco/app/elements/image_picker_button/image_picker_button.js +1 -1
  38. data/app/components/coco/app/elements/image_picker_button/image_picker_button.rb +3 -3
  39. data/app/components/coco/app/elements/layout_picker_button/layout_picker_button.js +1 -1
  40. data/app/components/coco/app/elements/layout_picker_button/layout_picker_button.rb +3 -3
  41. data/app/components/coco/app/elements/link/link.rb +1 -1
  42. data/app/components/coco/app/elements/menu/menu.css +5 -5
  43. data/app/components/coco/app/elements/menu_button/menu_button.js +1 -1
  44. data/app/components/coco/app/elements/menu_button/menu_button.rb +3 -3
  45. data/app/components/coco/app/elements/menu_items/user_profile/user_profile.css +1 -1
  46. data/app/components/coco/app/elements/notice/notice.js +1 -1
  47. data/app/components/coco/app/elements/seamless_textarea/seamless_textarea.js +1 -1
  48. data/app/components/coco/app/elements/snackbar/snackbar.css +1 -1
  49. data/app/components/coco/app/elements/snackbar/snackbar.js +1 -1
  50. data/app/components/coco/app/elements/system_banner/system_banner.js +1 -1
  51. data/app/components/coco/app/elements/toast/toast.js +1 -1
  52. data/app/components/coco/app/elements/toolbar/toolbar.js +1 -1
  53. data/app/components/coco/app/elements/toolbar/toolbar.rb +1 -1
  54. data/app/components/coco/app/fields/button_component.rb +1 -1
  55. data/app/components/coco/app/fields/submit_component.rb +1 -0
  56. data/app/components/coco/app/layouts/application/application.js +1 -1
  57. data/app/components/coco/app/layouts/page/page.js +1 -1
  58. data/app/components/coco/{app/elements → shared}/button/button.css +104 -32
  59. data/app/components/coco/shared/button/button.html.erb +83 -0
  60. data/app/components/coco/{base → shared}/button/button.js +2 -1
  61. data/app/components/coco/{base → shared}/button/button.rb +107 -42
  62. data/app/components/coco/{base → shared}/button/button_dropdown.js +11 -2
  63. data/app/components/coco/{app/elements → shared}/button_group/button_group.css +1 -1
  64. data/app/components/coco/{app/elements → shared}/button_group/button_group.js +12 -4
  65. data/app/components/coco/shared/button_group/button_group.rb +40 -0
  66. data/app/components/coco/{app/elements → shared}/button_to/button_to.css +1 -1
  67. data/app/components/coco/shared/button_to/button_to.rb +50 -0
  68. data/app/components/coco/{base → shared}/dropdown/dropdown.js +1 -1
  69. data/app/components/coco/{base → shared}/icon/icon.js +1 -1
  70. data/app/components/coco/{base → shared}/image_uploader/image_uploader.js +1 -1
  71. data/app/components/coco/{base → shared}/modal/modal.js +2 -2
  72. data/app/components/coco/{base → shared}/modal_dialog/modal_dialog.js +1 -1
  73. data/app/components/coco/{base → shared}/modal_lightbox/modal_lightbox.js +1 -1
  74. data/app/components/coco/{base → shared}/poll_controller/poll_controller.js +1 -1
  75. data/app/helpers/coco/app_helper.rb +0 -23
  76. data/app/helpers/coco/component_helper.rb +1 -1
  77. data/app/helpers/coco/{base_helper.rb → shared_helper.rb} +24 -1
  78. data/app/helpers/coco/url_helper.rb +1 -1
  79. data/lib/coco/engine.rb +2 -2
  80. data/lib/coco.rb +1 -1
  81. data/lib/generators/coco/coco_generator.rb +1 -1
  82. metadata +74 -79
  83. data/app/assets/css/base/components/coco.css +0 -5
  84. data/app/assets/css/base/components/dropdown.css +0 -7
  85. data/app/assets/css/base/components/tooltip.css +0 -19
  86. data/app/assets/css/base/utils/text.css +0 -79
  87. data/app/assets/js/base/components.js +0 -4
  88. data/app/components/coco/app/elements/button/button.rb +0 -87
  89. data/app/components/coco/app/elements/button_group/button_group.rb +0 -42
  90. data/app/components/coco/app/elements/button_to/button_to.rb +0 -54
  91. data/app/components/coco/base/button/button.css +0 -75
  92. data/app/components/coco/base/button/button.html.erb +0 -71
  93. /data/app/assets/css/app/{utilities.css → utils.css} +0 -0
  94. /data/app/assets/css/{base → shared}/utils/colors.css +0 -0
  95. /data/app/assets/css/{base → shared}/utils/icons.css +0 -0
  96. /data/app/assets/js/{coco.js → shared/coco.js} +0 -0
  97. /data/app/components/coco/{base → shared}/avatar/avatar.css +0 -0
  98. /data/app/components/coco/{base → shared}/avatar/avatar.rb +0 -0
  99. /data/app/components/coco/{app/elements → shared}/button_group/button_group.html.erb +0 -0
  100. /data/app/components/coco/{app/elements → shared}/button_to/button_to.html.erb +0 -0
  101. /data/app/components/coco/{base → shared}/content/content.rb +0 -0
  102. /data/app/components/coco/{base → shared}/dropdown/dropdown.css +0 -0
  103. /data/app/components/coco/{base → shared}/dropdown/dropdown.html.erb +0 -0
  104. /data/app/components/coco/{base → shared}/dropdown/dropdown.rb +0 -0
  105. /data/app/components/coco/{base → shared}/embeds/youtube/youtube.css +0 -0
  106. /data/app/components/coco/{base → shared}/embeds/youtube/youtube.html.erb +0 -0
  107. /data/app/components/coco/{base → shared}/embeds/youtube/youtube.rb +0 -0
  108. /data/app/components/coco/{base → shared}/icon/icon.css +0 -0
  109. /data/app/components/coco/{base → shared}/icon/icon.html.erb +0 -0
  110. /data/app/components/coco/{base → shared}/icon/icon.rb +0 -0
  111. /data/app/components/coco/{base → shared}/image/image.css +0 -0
  112. /data/app/components/coco/{base → shared}/image/image.rb +0 -0
  113. /data/app/components/coco/{base → shared}/image_uploader/image_uploader.css +0 -0
  114. /data/app/components/coco/{base → shared}/image_uploader/image_uploader.html.erb +0 -0
  115. /data/app/components/coco/{base → shared}/image_uploader/image_uploader.rb +0 -0
  116. /data/app/components/coco/{base → shared}/link/link.css +0 -0
  117. /data/app/components/coco/{base → shared}/link/link.rb +0 -0
  118. /data/app/components/coco/{base → shared}/modal/modal.css +0 -0
  119. /data/app/components/coco/{base → shared}/modal/modal.html.erb +0 -0
  120. /data/app/components/coco/{base → shared}/modal/modal.rb +0 -0
  121. /data/app/components/coco/{base → shared}/modal_dialog/modal_dialog.css +0 -0
  122. /data/app/components/coco/{base → shared}/modal_dialog/modal_dialog.html.erb +0 -0
  123. /data/app/components/coco/{base → shared}/modal_dialog/modal_dialog.rb +0 -0
  124. /data/app/components/coco/{base → shared}/modal_lightbox/modal_lightbox.css +0 -0
  125. /data/app/components/coco/{base → shared}/modal_lightbox/modal_lightbox.html.erb +0 -0
  126. /data/app/components/coco/{base → shared}/modal_lightbox/modal_lightbox.rb +0 -0
  127. /data/app/components/coco/{base → shared}/pager_link/pager_link.css +0 -0
  128. /data/app/components/coco/{base → shared}/pager_link/pager_link.html.erb +0 -0
  129. /data/app/components/coco/{base → shared}/pager_link/pager_link.rb +0 -0
  130. /data/app/components/coco/{base → shared}/panel/panel.css +0 -0
  131. /data/app/components/coco/{base → shared}/panel/panel.html.erb +0 -0
  132. /data/app/components/coco/{base → shared}/panel/panel.rb +0 -0
  133. /data/app/components/coco/{base → shared}/placeholder/placeholder.css +0 -0
  134. /data/app/components/coco/{base → shared}/placeholder/placeholder.html.erb +0 -0
  135. /data/app/components/coco/{base → shared}/placeholder/placeholder.rb +0 -0
  136. /data/app/components/coco/{base → shared}/poll_controller/poll_controller.css +0 -0
  137. /data/app/components/coco/{base → shared}/poll_controller/poll_controller.html.erb +0 -0
  138. /data/app/components/coco/{base → shared}/poll_controller/poll_controller.rb +0 -0
  139. /data/app/components/coco/{base → shared}/svg/svg.html.erb +0 -0
  140. /data/app/components/coco/{base → shared}/svg/svg.rb +0 -0
@@ -1,5 +1,77 @@
1
1
  @layer components {
2
- [data-coco][data-component="app-button"] {
2
+ .coco-button-wrapper {
3
+ @apply !contents;
4
+ }
5
+
6
+ [data-coco].coco-button {
7
+ @apply flex transition-colors w-auto bg-transparent text-current border border-transparent select-none flex-none no-underline outline-none focus-visible:outline-0;
8
+ width: min-content;
9
+
10
+ .button-inner {
11
+ @apply inline-flex items-center text-center mx-auto gap-2;
12
+ width: fit-content;
13
+ }
14
+
15
+ .button-content {
16
+ @apply whitespace-nowrap relative leading-none inline-flex items-center order-2;
17
+ }
18
+
19
+ .button-state-content {
20
+ @apply contents;
21
+ }
22
+
23
+ .button-icon {
24
+ @apply inline-flex items-center order-1;
25
+ }
26
+
27
+ .button-dropdown {
28
+ @apply contents rounded-md;
29
+ }
30
+
31
+ .button-toggle {
32
+ @apply order-3;
33
+ }
34
+
35
+ /* disabled */
36
+
37
+ &[data-disabled="true"] {
38
+ @apply cursor-not-allowed pointer-events-none;
39
+ }
40
+
41
+ /* loading */
42
+
43
+ &[data-state="loading"] .button-icon {
44
+ @apply animate-spin;
45
+ }
46
+
47
+ /* Fit */
48
+
49
+ &[data-fit="full"] {
50
+ @apply w-full;
51
+ }
52
+
53
+ /* Icons */
54
+
55
+ &[data-icon-position="end"] {
56
+ .button-content {
57
+ @apply order-1;
58
+ }
59
+
60
+ .button-icon {
61
+ @apply order-2;
62
+ }
63
+
64
+ .button-toggle {
65
+ @apply order-3;
66
+ }
67
+ }
68
+
69
+ &.with-icon[data-collapsed="true"] {
70
+ .button-content {
71
+ display: none;
72
+ }
73
+ }
74
+
3
75
  /* Themes */
4
76
 
5
77
  &[data-theme] {
@@ -287,119 +359,119 @@
287
359
  /* Responsive resizing */
288
360
 
289
361
  &[data-size="xs"] {
290
- @apply app-button-xs;
362
+ @apply coco-button-xs;
291
363
  }
292
364
 
293
365
  &[data-size="sm"] {
294
- @apply app-button-sm;
366
+ @apply coco-button-sm;
295
367
  }
296
368
 
297
369
  &[data-size="md"] {
298
- @apply app-button-md;
370
+ @apply coco-button-md;
299
371
  }
300
372
 
301
373
  &[data-size="lg"] {
302
- @apply app-button-lg;
374
+ @apply coco-button-lg;
303
375
  }
304
376
 
305
377
  @media screen(md) {
306
378
  &[data-size-md="xs"] {
307
- @apply app-button-xs;
379
+ @apply coco-button-xs;
308
380
  }
309
381
 
310
382
  &[data-size-md="sm"] {
311
- @apply app-button-sm;
383
+ @apply coco-button-sm;
312
384
  }
313
385
 
314
386
  &[data-size-md="md"] {
315
- @apply app-button-md;
387
+ @apply coco-button-md;
316
388
  }
317
389
 
318
390
  &[data-size-md="lg"] {
319
- @apply app-button-lg;
391
+ @apply coco-button-lg;
320
392
  }
321
393
  }
322
394
 
323
395
  @media screen(lg) {
324
396
  &[data-size-lg="xs"] {
325
- @apply app-button-xs;
397
+ @apply coco-button-xs;
326
398
  }
327
399
 
328
400
  &[data-size-lg="sm"] {
329
- @apply app-button-sm;
401
+ @apply coco-button-sm;
330
402
  }
331
403
 
332
404
  &[data-size-lg="md"] {
333
- @apply app-button-md;
405
+ @apply coco-button-md;
334
406
  }
335
407
 
336
408
  &[data-size-lg="lg"] {
337
- @apply app-button-lg;
409
+ @apply coco-button-lg;
338
410
  }
339
411
  }
340
412
 
341
413
  @media screen(xl) {
342
414
  &[data-size-xl="xs"] {
343
- @apply app-button-xs;
415
+ @apply coco-button-xs;
344
416
  }
345
417
 
346
418
  &[data-size-xl="sm"] {
347
- @apply app-button-sm;
419
+ @apply coco-button-sm;
348
420
  }
349
421
 
350
422
  &[data-size-xl="md"] {
351
- @apply app-button-md;
423
+ @apply coco-button-md;
352
424
  }
353
425
 
354
426
  &[data-size-xl="lg"] {
355
- @apply app-button-lg;
427
+ @apply coco-button-lg;
356
428
  }
357
429
  }
358
430
 
359
431
  @media screen(2xl) {
360
432
  &[data-size-xxl="xs"],
361
433
  &[data-size-2xl="xs"] {
362
- @apply app-button-xs;
434
+ @apply coco-button-xs;
363
435
  }
364
436
 
365
437
  &[data-size-xxl="sm"],
366
438
  &[data-size-2xl="sm"] {
367
- @apply app-button-sm;
439
+ @apply coco-button-sm;
368
440
  }
369
441
 
370
442
  &[data-size-xxl="md"],
371
443
  &[data-size-2xl="md"] {
372
- @apply app-button-md;
444
+ @apply coco-button-md;
373
445
  }
374
446
 
375
447
  &[data-size-xxl="lg"],
376
448
  &[data-size-2xl="lg"] {
377
- @apply app-button-lg;
449
+ @apply coco-button-lg;
378
450
  }
379
451
  }
380
452
 
381
453
  @media screen(max) {
382
454
  &[data-size-max="xs"] {
383
- @apply app-button-xs;
455
+ @apply coco-button-xs;
384
456
  }
385
457
 
386
458
  &[data-size-max="sm"] {
387
- @apply app-button-sm;
459
+ @apply coco-button-sm;
388
460
  }
389
461
 
390
462
  &[data-size-max="md"] {
391
- @apply app-button-md;
463
+ @apply coco-button-md;
392
464
  }
393
465
 
394
466
  &[data-size-max="lg"] {
395
- @apply app-button-lg;
467
+ @apply coco-button-lg;
396
468
  }
397
469
  }
398
470
  }
399
471
  }
400
472
 
401
473
  @layer utilities {
402
- .app-button-xs {
474
+ .coco-button-xs {
403
475
  .button-content {
404
476
  font-size: 14px;
405
477
  line-height: 14px;
@@ -429,9 +501,9 @@
429
501
  }
430
502
  }
431
503
 
432
- .app-button-sm {
504
+ .coco-button-sm {
433
505
  .button-content {
434
- @apply text-label-sm;
506
+ @apply coco-label-sm;
435
507
  }
436
508
 
437
509
  .button-icon [data-component="icon"],
@@ -458,9 +530,9 @@
458
530
  }
459
531
  }
460
532
 
461
- .app-button-md {
533
+ .coco-button-md {
462
534
  .button-content {
463
- @apply text-label-md;
535
+ @apply coco-label-md;
464
536
  }
465
537
 
466
538
  .button-icon [data-component="icon"],
@@ -487,9 +559,9 @@
487
559
  }
488
560
  }
489
561
 
490
- .app-button-lg {
562
+ .coco-button-lg {
491
563
  .button-content {
492
- @apply text-label-lg;
564
+ @apply coco-label-lg;
493
565
  }
494
566
 
495
567
  .button-icon [data-component="icon"],
@@ -0,0 +1,83 @@
1
+ <%= coco_tag(:div, class: "coco-button-wrapper", x: alpine_wrapper_attrs.to_h) do %>
2
+ <%= render component_tag(button_tag,
3
+ class: {
4
+ "coco-button": true,
5
+ "icon-only": icon_only?,
6
+ "with-icon": (icon? && !icon_only?)
7
+ },
8
+ x: {
9
+ data: (x_data("button", alpine_data) unless static?),
10
+ bind: ("root" unless static?),
11
+ "dropdown:trigger": (true if dropdown?),
12
+ "dropdown:anchor": (true if dropdown?),
13
+ "@click": ("#{"checkConfirmation($event);" if confirm?} #{on_click}" if confirm? || on_click.present?)
14
+ }
15
+ ) do %>
16
+ <span class="button-inner">
17
+ <% if static? %>
18
+ <% if icon? %>
19
+ <span class="button-icon">
20
+ <%= icon %>
21
+ </span>
22
+ <% end %>
23
+ <% if button_text.present? %>
24
+ <span class="button-content">
25
+ <%= button_text %>
26
+ </span>
27
+ <% end %>
28
+ <% else %>
29
+ <% states.each do |name, props| %>
30
+ <% if props[:icon].present? %>
31
+ <% if states.many? %>
32
+ <span
33
+ class="button-icon"
34
+ x-ref="<%= name %>Icon"
35
+ x-show="showIcon('<%= name %>')"
36
+ <%= "x-cloak" unless name.to_sym == :default %>>
37
+ <%= props[:icon] %>
38
+ </span>
39
+ <% else %>
40
+ <span class="button-icon" x-ref="defaultIcon">
41
+ <%= props[:icon] %>
42
+ </span>
43
+ <% end %>
44
+ <% end %>
45
+ <% end %>
46
+
47
+ <% unless icon_only? %>
48
+ <% states.each do |name, props| %>
49
+ <% if states.many? %>
50
+ <span
51
+ class="button-content"
52
+ x-ref="<%= name %>Content"
53
+ x-show="showContent('<%= name %>')"
54
+ <%= "x-cloak" unless name.to_sym == :default %>>
55
+ <%= props[:text] %>
56
+ </span>
57
+ <% else %>
58
+ <span class="button-content" x-ref="defaultContent">
59
+ <%= props[:text] %>
60
+ </span>
61
+ <% end %>
62
+ <% end %>
63
+ <% end %>
64
+
65
+ <% if toggle? %>
66
+ <% if toggle_direction == :horizontal %>
67
+ <%= coco_icon(:chevron_right, class: "button-toggle") %>
68
+ <% else %>
69
+ <%= coco_icon(:chevron_down, class: "button-toggle") %>
70
+ <% end %>
71
+ <% end %>
72
+ <% end %>
73
+ </span>
74
+ <% end %>
75
+
76
+ <% if dropdown? %>
77
+ <div x-dropdown:content>
78
+ <div class="button-dropdown">
79
+ <%= dropdown %>
80
+ </div>
81
+ </div>
82
+ <% end %>
83
+ <% end %>
@@ -1,4 +1,4 @@
1
- import { CocoComponent } from "@js/coco.js";
1
+ import { CocoComponent } from "@assets/js/shared/coco.js";
2
2
  import { camelCase } from "lodash";
3
3
 
4
4
  export default CocoComponent("button", (data = {}) => {
@@ -181,6 +181,7 @@ export default CocoComponent("button", (data = {}) => {
181
181
  "x-options": "options",
182
182
  "x-tooltip": "tooltipText",
183
183
  "x-effect": "setTooltipText",
184
+ ":disabled": "disabled",
184
185
  },
185
186
  };
186
187
  });
@@ -6,73 +6,90 @@ module Coco
6
6
  include Concerns::WithTooltip
7
7
  include Concerns::AcceptsTheme
8
8
 
9
- SIZES = [:sm, :md, :lg, nil]
9
+ SIZES = [:xs, :sm, :md, :lg, nil]
10
10
 
11
11
  SIZE_ALIASES = {
12
12
  default: [:sm, {xl: :md}]
13
13
  }
14
14
 
15
- THEMES = []
16
-
17
- DEFAULT_THEME = nil
15
+ THEMES = [
16
+ "primary",
17
+ "text-primary",
18
+ "secondary",
19
+ "text-secondary",
20
+ "positive",
21
+ "text-positive",
22
+ "negative",
23
+ "text-negative",
24
+ "warning",
25
+ "text-warning",
26
+ "info",
27
+ "text-info",
28
+ "toolbar",
29
+ "toolbar-floating",
30
+ "text-toolbar",
31
+ "neutral-dark",
32
+ "neutral-light",
33
+ "text-neutral-light",
34
+ "text-neutral-dark",
35
+ "blank",
36
+ nil
37
+ ]
38
+
39
+ DEFAULT_THEME = "primary"
18
40
 
19
41
  tag_attr :type, :value, :name, :disabled, :href, :target
20
42
 
43
+ accepts_option :size, from: SIZES, default: :md
44
+ accepts_option :theme, from: THEMES, default: DEFAULT_THEME
21
45
  accepts_option :disabled, from: [true, false]
22
46
  accepts_option :confirm, from: [true, false, nil], default: nil
23
47
  accepts_option :fit, from: [:auto, :full]
24
48
  accepts_option :collapsible, from: [true, false, nil]
25
49
  accepts_option :toggle, from: [:horizontal, :vertical]
26
50
  accepts_option :state
51
+ accepts_option :variant
27
52
 
28
53
  accepts_option :dropdown do |dd|
29
54
  dd.accepts_option :placement,
30
- from: %w[top top-start top-end right right-start right-end bottom bottom-start bottom-end left left-start left-end auto auto-start auto-end]
55
+ from: %w[top top-start top-end right right-start right-end bottom bottom-start bottom-end left left-start left-end auto auto-start auto-end],
56
+ private: true
31
57
  end
32
58
 
33
59
  renders_one :text, Coco::Content
34
60
 
61
+ renders_one :dropdown, types: {
62
+ content: ->(&block) { block.call },
63
+ confirmation: ->(**kwargs) do
64
+ set_option_value(:confirm, true)
65
+ Coco::App::Elements::ConfirmPanel.new(**kwargs)
66
+ end
67
+ }
68
+
35
69
  renders_many :states, ->(name = nil, **kwargs) do
36
70
  name ||= kwargs.fetch(:name)
37
71
  @states[name.to_sym] = kwargs.except!(:name)
38
72
  end
39
73
 
40
- before_initialize do |kwargs|
41
- button_size = kwargs.fetch(:size, :default)&.to_sym
42
- if button_size.in?(self::SIZE_ALIASES.keys) && !kwargs.key?(:resize)
43
- kwargs[:size], kwargs[:resize] = self::SIZE_ALIASES.fetch(button_size)
44
- end
45
-
46
- kwargs
47
- end
48
-
49
- before_render do
50
- resize.each { set_tag_data_attr("size-#{_1}", _2) }
51
-
52
- if loading?
53
- set_option_value(:state, "loading")
54
- elsif active?
55
- set_option_value(:state, "active")
56
- end
57
-
58
- set_tag_attr(:disabled, true) if disabled?
59
- set_tag_attr(:type, "button") unless tag_attr?(:type) || link?
60
-
61
- if dropdown? || confirm? && get_option(:dropdown, :placement).blank?
62
- set_option_value(:dropdown, :placement, "bottom-start")
63
- end
64
- end
65
-
66
74
  attr_reader :on_click, :resize
67
75
 
68
- def initialize(click: nil, resize: nil, states: nil, loading: false, active: false, tooltip: nil, **kwargs)
76
+ def initialize(click: nil, resize: nil, states: nil, loading: false, active: false, static: nil, **kwargs)
69
77
  @on_click = click
70
78
  @resize = resize.to_h
71
79
  @states = states.to_h
72
80
  @loading = loading
81
+ @static = static
73
82
  @active = active
74
83
  end
75
84
 
85
+ def with_dropdown(...)
86
+ with_dropdown_content(...)
87
+ end
88
+
89
+ def with_confirmation(...)
90
+ with_dropdown_confirmation(...)
91
+ end
92
+
76
93
  def toggle?
77
94
  toggle_direction.present? && button_text.present?
78
95
  end
@@ -89,6 +106,14 @@ module Coco
89
106
  text&.to_s || content&.to_s || ""
90
107
  end
91
108
 
109
+ def static?
110
+ if @static.nil?
111
+ !(confirm? || dropdown? || tooltip? || @states.any? || on_click.present? || get_option_value(:collapsible))
112
+ else
113
+ @static
114
+ end
115
+ end
116
+
92
117
  def loading?
93
118
  @loading == true
94
119
  end
@@ -101,6 +126,10 @@ module Coco
101
126
  get_option_value(:confirm)
102
127
  end
103
128
 
129
+ def tooltip?
130
+ get_option_value(:tooltip, :content).present?
131
+ end
132
+
104
133
  def disabled?
105
134
  get_option_value(:disabled)
106
135
  end
@@ -114,22 +143,16 @@ module Coco
114
143
  end
115
144
 
116
145
  def icon_only?
117
- !states.find { _2[:text].present? }
118
- end
119
-
120
- def dropdown?
121
- false
146
+ (@states.none? && button_text.blank?) ||
147
+ !states.find { _2[:text].present? }
122
148
  end
123
149
 
124
150
  def alpine_wrapper_attrs
125
151
  if dropdown? || confirm?
126
152
  {
127
153
  data: x_data("buttonDropdown"),
128
- dropdown: jsify_data({offset: [0, 1], placement: get_option_value(:dropdown, :placement)}.compact),
129
- "@dropdown:show": ("button.setState('active')" if dropdown?),
130
- "@dropdown:hide": ("button.resetState()" if dropdown?),
131
- "@confirmation:confirm": ("button.approveAndRun($event)" if confirm?),
132
- "@confirmation:cancel": ("button.cancelConfirmation($event)" if confirm?)
154
+ dropdown: jsify_data({placement: get_option_value(:dropdown, :placement)}.compact),
155
+ bind: "root"
133
156
  }
134
157
  end
135
158
  end
@@ -193,5 +216,47 @@ module Coco
193
216
  icon = icon.is_a?(Symbol) ? {name: icon} : icon
194
217
  icon.is_a?(Hash) ? render(Coco::Icon.new(**icon)) : icon
195
218
  end
219
+
220
+ before_initialize do |kwargs|
221
+ if kwargs.key?(:modal)
222
+ modal_name = (kwargs[:modal] == true) ? "default" : kwargs[:modal]
223
+ kwargs[:data] = kwargs.fetch(:data, {}).merge(coco_modal_data_attributes(modal_name))
224
+ kwargs.delete(:modal)
225
+ end
226
+
227
+ button_size = kwargs.fetch(:size, :default)&.to_sym
228
+ if button_size.in?(SIZE_ALIASES.keys) && !kwargs.key?(:resize)
229
+ kwargs[:size], kwargs[:resize] = SIZE_ALIASES.fetch(button_size)
230
+ end
231
+
232
+ kwargs
233
+ end
234
+
235
+ before_render do
236
+ resize.each { set_tag_data_attr("size-#{_1}", _2) }
237
+
238
+ if loading?
239
+ set_option_value(:state, "loading")
240
+ elsif active?
241
+ set_option_value(:state, "active")
242
+ end
243
+
244
+ set_tag_attr(:disabled, true) if disabled?
245
+ set_tag_attr(:type, "button") unless tag_attr?(:type) || link?
246
+
247
+ if confirm? && !dropdown?
248
+ with_confirmation do |confirm|
249
+ confirm.with_text { "Are you sure?" }
250
+ confirm.with_button { "Yes, continue" }
251
+ end
252
+ end
253
+
254
+ if (dropdown? || confirm?) && get_option(:dropdown, :placement).blank?
255
+ set_option_value(:dropdown, :placement, "bottom-start")
256
+ end
257
+ end
258
+ class << self
259
+ include Coco::SharedHelper
260
+ end
196
261
  end
197
262
  end
@@ -1,7 +1,7 @@
1
- import { CocoComponent } from "@js/coco.js";
1
+ import { CocoComponent } from "@assets/js/shared/coco.js";
2
2
  import { getComponent } from "@helpers/alpine";
3
3
 
4
- export default CocoComponent("buttonDropdown", (data = {}) => {
4
+ export default CocoComponent("buttonDropdown", () => {
5
5
  return {
6
6
  dropdown: null,
7
7
  button: null,
@@ -23,5 +23,14 @@ export default CocoComponent("buttonDropdown", (data = {}) => {
23
23
  this.dropdown.show();
24
24
  }
25
25
  },
26
+
27
+ /* bindings */
28
+
29
+ root: {
30
+ "@dropdown:show": "button.setState('active')",
31
+ "@dropdown:hide": "button.resetState()",
32
+ "@confirmation:confirm": "button.approveAndRun($event)",
33
+ "@confirmation:cancel": "button.cancelConfirmation($event)",
34
+ },
26
35
  };
27
36
  });
@@ -1,5 +1,5 @@
1
1
  @layer components {
2
- [data-coco][data-component="app-button-group"] {
2
+ [data-coco][data-component="button-group"] {
3
3
  width: fit-content;
4
4
  border-radius: 44px;
5
5
 
@@ -1,6 +1,6 @@
1
- import { CocoComponent } from "@js/coco.js";
1
+ import { CocoComponent } from "@assets/js/shared/coco.js";
2
2
  import { getComponent } from "@helpers/alpine";
3
- import { createSingleton } from "@libs/tippy";
3
+ import { createSingleton } from "@assets/js/libs/tippy";
4
4
 
5
5
  export default CocoComponent("appButtonGroup", () => {
6
6
  return {
@@ -19,7 +19,7 @@ export default CocoComponent("appButtonGroup", () => {
19
19
 
20
20
  get buttons() {
21
21
  const buttonElements = this.$el.querySelectorAll(
22
- "[data-component='app-button']"
22
+ "[data-component='button']"
23
23
  );
24
24
  return Array.from(buttonElements).map((el) => getComponent(el));
25
25
  },
@@ -51,7 +51,15 @@ export default CocoComponent("appButtonGroup", () => {
51
51
  this.destroySingletonTooltip();
52
52
 
53
53
  this.tooltipInstances = this.buttons
54
- .map((button) => button.shouldShowTooltip() && button.tippyInstance)
54
+ .map((button) => {
55
+ if (
56
+ button.tippyInstance &&
57
+ button.shouldShowTooltip &&
58
+ button.shouldShowTooltip()
59
+ ) {
60
+ return button.tippyInstance;
61
+ }
62
+ })
55
63
  .filter((t) => t);
56
64
 
57
65
  this.singletonTooltip = createSingleton(this.tooltipInstances, {
@@ -0,0 +1,40 @@
1
+ module Coco
2
+ class ButtonGroup < Coco::Component
3
+ include Concerns::ActsAsButtonGroup
4
+ include Concerns::AcceptsOptions
5
+
6
+ accepts_option :size, default: :default, private: true
7
+ accepts_option :theme, default: :primary, private: true
8
+ accepts_option :segmented, from: [true, false], default: false
9
+ accepts_option :floating, from: [true, false], default: false
10
+ accepts_option :collapsible, from: [true, false, nil]
11
+
12
+ before_initialize do |kwargs|
13
+ if kwargs[:floating] == true
14
+ kwargs[:segmented] = true
15
+ kwargs[:theme] = :toolbar_floating
16
+ end
17
+ kwargs
18
+ end
19
+
20
+ def button_kwargs(kwargs, type = nil)
21
+ args = {
22
+ theme: get_option_value(:theme),
23
+ size: get_option_value(:size),
24
+ **kwargs
25
+ }
26
+
27
+ if component_args.key?(:resize)
28
+ args[:resize] = component_args[:resize]
29
+ end
30
+
31
+ if get_option_value(:collapsible) == false
32
+ args[:collapsible] = false
33
+ elsif get_option_value(:collapsible) == true
34
+ args[:static] = false
35
+ end
36
+
37
+ args
38
+ end
39
+ end
40
+ end
@@ -1,5 +1,5 @@
1
1
  @layer components {
2
- [data-coco][data-component="app-button-to"] {
2
+ [data-coco][data-component="button-to"] {
3
3
  @apply contents;
4
4
 
5
5
  form,