plutonium 0.15.12 → 0.15.14

Sign up to get free protection for your applications and to get access to all the features.
Files changed (36) hide show
  1. checksums.yaml +4 -4
  2. data/app/assets/plutonium.css +1 -1
  3. data/app/assets/plutonium.js +155 -4
  4. data/app/assets/plutonium.js.map +4 -4
  5. data/app/assets/plutonium.min.js +8 -8
  6. data/app/assets/plutonium.min.js.map +4 -4
  7. data/app/views/components/resource_header/resource_header_component.rb +1 -1
  8. data/app/views/components/resource_layout/resource_layout_component.html.erb +6 -2
  9. data/app/views/layouts/resource.html.erb +1 -14
  10. data/app/views/layouts/rodauth.html.erb +2 -18
  11. data/app/views/plutonium/_resource_header.html.erb +4 -2
  12. data/app/views/plutonium/_resource_sidebar.html.erb +1 -1
  13. data/docs/public/templates/plutonium.rb +6 -12
  14. data/lib/generators/pu/gem/standard/standard_generator.rb +14 -1
  15. data/lib/generators/pu/lib/plutonium_generators/concerns/actions.rb +1 -1
  16. data/lib/generators/pu/rodauth/concerns/configuration.rb +1 -0
  17. data/lib/plutonium/ui/color_mode_selector.rb +86 -0
  18. data/lib/plutonium/ui/component/kit.rb +2 -0
  19. data/lib/plutonium/ui/component/methods.rb +2 -0
  20. data/lib/plutonium/ui/dyna_frame/host.rb +2 -2
  21. data/lib/plutonium/ui/layout/base.rb +135 -0
  22. data/lib/plutonium/ui/layout/header.rb +121 -0
  23. data/lib/plutonium/ui/layout/resource_layout.rb +26 -0
  24. data/lib/plutonium/ui/layout/rodauth_layout.rb +34 -0
  25. data/lib/plutonium/ui/layout/sidebar.rb +56 -0
  26. data/lib/plutonium/ui/table/resource.rb +1 -1
  27. data/lib/plutonium/version.rb +1 -1
  28. data/lib/plutonium.rb +2 -0
  29. data/lib/rodauth/features/case_insensitive_login.rb +21 -0
  30. data/lib/rodauth/plugins.rb +1 -0
  31. data/package-lock.json +2 -2
  32. data/package.json +1 -1
  33. data/src/js/controllers/header_controller.js +184 -0
  34. data/src/js/controllers/register_controllers.js +4 -2
  35. data/src/js/controllers/{resource_header_controller.js → sidebar_controller.js} +2 -2
  36. metadata +26 -3
@@ -2648,10 +2648,153 @@
2648
2648
  }
2649
2649
  };
2650
2650
 
2651
- // src/js/controllers/resource_header_controller.js
2652
- var resource_header_controller_default = class extends Controller {
2651
+ // src/js/controllers/header_controller.js
2652
+ var header_controller_default = class extends Controller {
2653
+ static targets = ["open", "close"];
2654
+ static outlets = ["sidebar"];
2655
+ static values = {
2656
+ placement: { type: String, default: "left" },
2657
+ bodyScrolling: { type: Boolean, default: false },
2658
+ backdrop: { type: Boolean, default: true },
2659
+ edge: { type: Boolean, default: false },
2660
+ edgeOffset: { type: String, default: "bottom-[60px]" }
2661
+ };
2662
+ static classes = {
2663
+ backdrop: "bg-gray-900/50 dark:bg-gray-900/80 fixed inset-0 z-30"
2664
+ };
2665
+ initialize() {
2666
+ this.visible = false;
2667
+ this.handleEscapeKey = this.handleEscapeKey.bind(this);
2668
+ }
2653
2669
  connect() {
2654
- console.log(`resource-header connected: ${this.element}`);
2670
+ document.addEventListener("keydown", this.handleEscapeKey);
2671
+ }
2672
+ sidebarOutletConnected() {
2673
+ this.#setupDrawer(this.sidebarOutlet.element);
2674
+ }
2675
+ disconnect() {
2676
+ this.#removeBackdrop();
2677
+ document.removeEventListener("keydown", this.handleEscapeKey);
2678
+ if (!this.bodyScrollingValue) {
2679
+ document.body.classList.remove("overflow-hidden");
2680
+ }
2681
+ }
2682
+ #setupDrawer(drawerElement) {
2683
+ drawerElement.setAttribute("aria-hidden", "true");
2684
+ drawerElement.classList.add("transition-transform");
2685
+ this.#getPlacementClasses(this.placementValue).base.forEach((className) => {
2686
+ drawerElement.classList.add(className);
2687
+ });
2688
+ }
2689
+ toggleDrawer() {
2690
+ this.visible ? this.hideDrawer() : this.showDrawer();
2691
+ }
2692
+ showDrawer() {
2693
+ if (this.edgeValue) {
2694
+ this.#toggleEdgePlacementClasses(`${this.placementValue}-edge`, true);
2695
+ } else {
2696
+ this.#togglePlacementClasses(this.placementValue, true);
2697
+ }
2698
+ this.openTarget.classList.add("hidden");
2699
+ this.openTarget.setAttribute("aria-hidden", "true");
2700
+ this.closeTarget.classList.remove("hidden");
2701
+ this.closeTarget.setAttribute("aria-hidden", "false");
2702
+ this.sidebarOutlet.element.setAttribute("aria-modal", "true");
2703
+ this.sidebarOutlet.element.setAttribute("role", "dialog");
2704
+ this.sidebarOutlet.element.removeAttribute("aria-hidden");
2705
+ if (!this.bodyScrollingValue) {
2706
+ document.body.classList.add("overflow-hidden");
2707
+ }
2708
+ if (this.backdropValue) {
2709
+ this.#createBackdrop();
2710
+ }
2711
+ this.visible = true;
2712
+ this.dispatch("show");
2713
+ }
2714
+ hideDrawer() {
2715
+ if (this.edgeValue) {
2716
+ this.#toggleEdgePlacementClasses(`${this.placementValue}-edge`, false);
2717
+ } else {
2718
+ this.#togglePlacementClasses(this.placementValue, false);
2719
+ }
2720
+ this.openTarget.classList.remove("hidden");
2721
+ this.openTarget.setAttribute("aria-hidden", "false");
2722
+ this.closeTarget.classList.add("hidden");
2723
+ this.closeTarget.setAttribute("aria-hidden", "true");
2724
+ this.sidebarOutlet.element.setAttribute("aria-hidden", "true");
2725
+ this.sidebarOutlet.element.removeAttribute("aria-modal");
2726
+ this.sidebarOutlet.element.removeAttribute("role");
2727
+ if (!this.bodyScrollingValue) {
2728
+ document.body.classList.remove("overflow-hidden");
2729
+ }
2730
+ if (this.backdropValue) {
2731
+ this.#removeBackdrop();
2732
+ }
2733
+ this.visible = false;
2734
+ this.dispatch("hide");
2735
+ }
2736
+ handleEscapeKey(event) {
2737
+ if (event.key === "Escape" && this.visible) {
2738
+ this.hideDrawer();
2739
+ }
2740
+ }
2741
+ #createBackdrop() {
2742
+ if (!this.visible) {
2743
+ const backdrop = document.createElement("div");
2744
+ backdrop.setAttribute("data-drawer-backdrop", "");
2745
+ backdrop.classList.add(...this.constructor.classes.backdrop.split(" "));
2746
+ backdrop.addEventListener("click", () => this.hideDrawer());
2747
+ document.body.appendChild(backdrop);
2748
+ }
2749
+ }
2750
+ #removeBackdrop() {
2751
+ const backdrop = document.querySelector("[data-drawer-backdrop]");
2752
+ if (backdrop) {
2753
+ backdrop.remove();
2754
+ }
2755
+ }
2756
+ #getPlacementClasses(placement) {
2757
+ const placements2 = {
2758
+ top: {
2759
+ base: ["top-0", "left-0", "right-0"],
2760
+ active: ["transform-none"],
2761
+ inactive: ["-translate-y-full"]
2762
+ },
2763
+ right: {
2764
+ base: ["right-0", "top-0"],
2765
+ active: ["transform-none"],
2766
+ inactive: ["translate-x-full"]
2767
+ },
2768
+ bottom: {
2769
+ base: ["bottom-0", "left-0", "right-0"],
2770
+ active: ["transform-none"],
2771
+ inactive: ["translate-y-full"]
2772
+ },
2773
+ left: {
2774
+ base: ["left-0", "top-0"],
2775
+ active: ["transform-none"],
2776
+ inactive: ["-translate-x-full"]
2777
+ },
2778
+ "bottom-edge": {
2779
+ base: ["left-0", "top-0"],
2780
+ active: ["transform-none"],
2781
+ inactive: ["translate-y-full", this.edgeOffsetValue]
2782
+ }
2783
+ };
2784
+ return placements2[placement] || placements2.left;
2785
+ }
2786
+ #togglePlacementClasses(placement, show) {
2787
+ const classes = this.#getPlacementClasses(placement);
2788
+ if (show) {
2789
+ classes.active.forEach((c) => this.sidebarOutlet.element.classList.add(c));
2790
+ classes.inactive.forEach((c) => this.sidebarOutlet.element.classList.remove(c));
2791
+ } else {
2792
+ classes.active.forEach((c) => this.sidebarOutlet.element.classList.remove(c));
2793
+ classes.inactive.forEach((c) => this.sidebarOutlet.element.classList.add(c));
2794
+ }
2795
+ }
2796
+ #toggleEdgePlacementClasses(placement, show) {
2797
+ this.#togglePlacementClasses(placement, show);
2655
2798
  }
2656
2799
  };
2657
2800
 
@@ -2669,6 +2812,13 @@
2669
2812
  }
2670
2813
  };
2671
2814
 
2815
+ // src/js/controllers/sidebar_controller.js
2816
+ var sidebar_controller_default = class extends Controller {
2817
+ connect() {
2818
+ console.log(`sidebar connected: ${this.element}`);
2819
+ }
2820
+ };
2821
+
2672
2822
  // src/js/controllers/has_many_panel_controller.js
2673
2823
  var has_many_panel_controller_default = class extends Controller {
2674
2824
  connect() {
@@ -7290,9 +7440,10 @@
7290
7440
  application2.register("nav-user-section", nav_user_section_controller_default);
7291
7441
  application2.register("nav-user-link", nav_user_link_controller_default);
7292
7442
  application2.register("nav-user", nav_user_controller_default);
7293
- application2.register("resource-header", resource_header_controller_default);
7443
+ application2.register("header", header_controller_default);
7294
7444
  application2.register("sidebar-menu-item", sidebar_menu_item_controller_default);
7295
7445
  application2.register("sidebar-menu", sidebar_menu_controller_default);
7446
+ application2.register("sidebar", sidebar_controller_default);
7296
7447
  application2.register("has-many-panel", has_many_panel_controller_default);
7297
7448
  application2.register("nested-resource-form-fields", nested_resource_form_fields_controller_default);
7298
7449
  application2.register("toolbar", toolbar_controller_default);