aw-wizard-forms 3.1.3 → 4.2.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.
@@ -177,7 +177,7 @@ function createRevenueHeroAdapter(config) {
177
177
  * Copyright 2019 Google LLC
178
178
  * SPDX-License-Identifier: BSD-3-Clause
179
179
  */
180
- const t$2 = globalThis, e$2 = t$2.ShadowRoot && (void 0 === t$2.ShadyCSS || t$2.ShadyCSS.nativeShadow) && "adoptedStyleSheets" in Document.prototype && "replace" in CSSStyleSheet.prototype, s$2 = Symbol(), o$4 = /* @__PURE__ */ new WeakMap();
180
+ const t$2 = globalThis, e$4 = t$2.ShadowRoot && (void 0 === t$2.ShadyCSS || t$2.ShadyCSS.nativeShadow) && "adoptedStyleSheets" in Document.prototype && "replace" in CSSStyleSheet.prototype, s$2 = Symbol(), o$4 = /* @__PURE__ */ new WeakMap();
181
181
  let n$3 = class n {
182
182
  constructor(t2, e2, o2) {
183
183
  if (this._$cssResult$ = true, o2 !== s$2) throw Error("CSSResult is not constructable. Use `unsafeCSS` or `css` instead.");
@@ -186,7 +186,7 @@ let n$3 = class n {
186
186
  get styleSheet() {
187
187
  let t2 = this.o;
188
188
  const s2 = this.t;
189
- if (e$2 && void 0 === t2) {
189
+ if (e$4 && void 0 === t2) {
190
190
  const e2 = void 0 !== s2 && 1 === s2.length;
191
191
  e2 && (t2 = o$4.get(s2)), void 0 === t2 && ((this.o = t2 = new CSSStyleSheet()).replaceSync(this.cssText), e2 && o$4.set(s2, t2));
192
192
  }
@@ -196,13 +196,20 @@ let n$3 = class n {
196
196
  return this.cssText;
197
197
  }
198
198
  };
199
- const r$4 = (t2) => new n$3("string" == typeof t2 ? t2 : t2 + "", void 0, s$2), S$1 = (s2, o2) => {
200
- if (e$2) s2.adoptedStyleSheets = o2.map((t2) => t2 instanceof CSSStyleSheet ? t2 : t2.styleSheet);
199
+ const r$4 = (t2) => new n$3("string" == typeof t2 ? t2 : t2 + "", void 0, s$2), i$3 = (t2, ...e2) => {
200
+ const o2 = 1 === t2.length ? t2[0] : e2.reduce((e3, s2, o3) => e3 + ((t3) => {
201
+ if (true === t3._$cssResult$) return t3.cssText;
202
+ if ("number" == typeof t3) return t3;
203
+ throw Error("Value passed to 'css' function must be a 'css' function result: " + t3 + ". Use 'unsafeCSS' to pass non-literal values, but take care to ensure page security.");
204
+ })(s2) + t2[o3 + 1], t2[0]);
205
+ return new n$3(o2, t2, s$2);
206
+ }, S$1 = (s2, o2) => {
207
+ if (e$4) s2.adoptedStyleSheets = o2.map((t2) => t2 instanceof CSSStyleSheet ? t2 : t2.styleSheet);
201
208
  else for (const e2 of o2) {
202
209
  const o3 = document.createElement("style"), n3 = t$2.litNonce;
203
210
  void 0 !== n3 && o3.setAttribute("nonce", n3), o3.textContent = e2.cssText, s2.appendChild(o3);
204
211
  }
205
- }, c$2 = e$2 ? (t2) => t2 : (t2) => t2 instanceof CSSStyleSheet ? ((t3) => {
212
+ }, c$2 = e$4 ? (t2) => t2 : (t2) => t2 instanceof CSSStyleSheet ? ((t3) => {
206
213
  let e2 = "";
207
214
  for (const s2 of t3.cssRules) e2 += s2.cssText;
208
215
  return r$4(e2);
@@ -212,7 +219,7 @@ const r$4 = (t2) => new n$3("string" == typeof t2 ? t2 : t2 + "", void 0, s$2),
212
219
  * Copyright 2017 Google LLC
213
220
  * SPDX-License-Identifier: BSD-3-Clause
214
221
  */
215
- const { is: i$2, defineProperty: e$1, getOwnPropertyDescriptor: h$1, getOwnPropertyNames: r$3, getOwnPropertySymbols: o$3, getPrototypeOf: n$2 } = Object, a$1 = globalThis, c$1 = a$1.trustedTypes, l$1 = c$1 ? c$1.emptyScript : "", p$1 = a$1.reactiveElementPolyfillSupport, d$1 = (t2, s2) => t2, u$1 = { toAttribute(t2, s2) {
222
+ const { is: i$2, defineProperty: e$3, getOwnPropertyDescriptor: h$1, getOwnPropertyNames: r$3, getOwnPropertySymbols: o$3, getPrototypeOf: n$2 } = Object, a$1 = globalThis, c$1 = a$1.trustedTypes, l$1 = c$1 ? c$1.emptyScript : "", p$1 = a$1.reactiveElementPolyfillSupport, d$1 = (t2, s2) => t2, u$1 = { toAttribute(t2, s2) {
216
223
  switch (s2) {
217
224
  case Boolean:
218
225
  t2 = t2 ? l$1 : null;
@@ -252,7 +259,7 @@ let y$1 = class y extends HTMLElement {
252
259
  static createProperty(t2, s2 = b$1) {
253
260
  if (s2.state && (s2.attribute = false), this._$Ei(), this.prototype.hasOwnProperty(t2) && ((s2 = Object.create(s2)).wrapped = true), this.elementProperties.set(t2, s2), !s2.noAccessor) {
254
261
  const i2 = Symbol(), h2 = this.getPropertyDescriptor(t2, i2, s2);
255
- void 0 !== h2 && e$1(this.prototype, t2, h2);
262
+ void 0 !== h2 && e$3(this.prototype, t2, h2);
256
263
  }
257
264
  }
258
265
  static getPropertyDescriptor(t2, s2, i2) {
@@ -429,11 +436,11 @@ y$1.elementStyles = [], y$1.shadowRootOptions = { mode: "open" }, y$1[d$1("eleme
429
436
  * Copyright 2017 Google LLC
430
437
  * SPDX-License-Identifier: BSD-3-Clause
431
438
  */
432
- const t$1 = globalThis, i$1 = (t2) => t2, s$1 = t$1.trustedTypes, e = s$1 ? s$1.createPolicy("lit-html", { createHTML: (t2) => t2 }) : void 0, h = "$lit$", o$2 = `lit$${Math.random().toFixed(9).slice(2)}$`, n$1 = "?" + o$2, r$2 = `<${n$1}>`, l = document, c = () => l.createComment(""), a = (t2) => null === t2 || "object" != typeof t2 && "function" != typeof t2, u = Array.isArray, d = (t2) => u(t2) || "function" == typeof t2?.[Symbol.iterator], f = "[ \n\f\r]", v = /<(?:(!--|\/[^a-zA-Z])|(\/?[a-zA-Z][^>\s]*)|(\/?$))/g, _ = /-->/g, m = />/g, p = RegExp(`>|${f}(?:([^\\s"'>=/]+)(${f}*=${f}*(?:[^
439
+ const t$1 = globalThis, i$1 = (t2) => t2, s$1 = t$1.trustedTypes, e$2 = s$1 ? s$1.createPolicy("lit-html", { createHTML: (t2) => t2 }) : void 0, h = "$lit$", o$2 = `lit$${Math.random().toFixed(9).slice(2)}$`, n$1 = "?" + o$2, r$2 = `<${n$1}>`, l = document, c = () => l.createComment(""), a = (t2) => null === t2 || "object" != typeof t2 && "function" != typeof t2, u = Array.isArray, d = (t2) => u(t2) || "function" == typeof t2?.[Symbol.iterator], f = "[ \n\f\r]", v = /<(?:(!--|\/[^a-zA-Z])|(\/?[a-zA-Z][^>\s]*)|(\/?$))/g, _ = /-->/g, m = />/g, p = RegExp(`>|${f}(?:([^\\s"'>=/]+)(${f}*=${f}*(?:[^
433
440
  \f\r"'\`<>=]|("|')|))|$)`, "g"), g = /'/g, $ = /"/g, y2 = /^(?:script|style|textarea|title)$/i, x = (t2) => (i2, ...s2) => ({ _$litType$: t2, strings: i2, values: s2 }), b = x(1), E = Symbol.for("lit-noChange"), A = Symbol.for("lit-nothing"), C = /* @__PURE__ */ new WeakMap(), P = l.createTreeWalker(l, 129);
434
441
  function V(t2, i2) {
435
442
  if (!u(t2) || !t2.hasOwnProperty("raw")) throw Error("invalid template strings array");
436
- return void 0 !== e ? e.createHTML(i2) : i2;
443
+ return void 0 !== e$2 ? e$2.createHTML(i2) : i2;
437
444
  }
438
445
  const N = (t2, i2) => {
439
446
  const s2 = t2.length - 1, e2 = [];
@@ -736,6 +743,323 @@ function n2(t2) {
736
743
  function r(r2) {
737
744
  return n2({ ...r2, state: true, attribute: false });
738
745
  }
746
+ /**
747
+ * @license
748
+ * Copyright 2017 Google LLC
749
+ * SPDX-License-Identifier: BSD-3-Clause
750
+ */
751
+ const e$1 = (e2, t2, c2) => (c2.configurable = true, c2.enumerable = true, Reflect.decorate && "object" != typeof t2 && Object.defineProperty(e2, t2, c2), c2);
752
+ /**
753
+ * @license
754
+ * Copyright 2017 Google LLC
755
+ * SPDX-License-Identifier: BSD-3-Clause
756
+ */
757
+ function e(e2, r2) {
758
+ return (n3, s2, i2) => {
759
+ const o2 = (t2) => t2.renderRoot?.querySelector(e2) ?? null;
760
+ return e$1(n3, s2, { get() {
761
+ return o2(this);
762
+ } });
763
+ };
764
+ }
765
+ const designTokens = i$3`
766
+ /* Colors */
767
+ --wf-color-primary: #8040f0;
768
+ --wf-color-primary-border: #602cbb;
769
+ --wf-color-primary-light: rgba(128, 64, 240, 0.08);
770
+ --wf-color-surface: #f3f3f5;
771
+ --wf-color-surface-hover: #e9e9eb;
772
+ --wf-color-border: #d4d4d4;
773
+ --wf-color-text: #0a0a0a;
774
+ --wf-color-text-secondary: #404040;
775
+ --wf-color-text-muted: #646464;
776
+ --wf-color-error: #dc3545;
777
+ --wf-color-error-light: rgba(220, 53, 69, 0.1);
778
+ --wf-color-badge-bg: #fcfcfc;
779
+ --wf-color-badge-border: #d4d4d4;
780
+ --wf-color-badge-text: #5f5f5f;
781
+ --wf-color-progress-active: rgba(0, 0, 0, 0.1);
782
+ --wf-color-progress-inactive: rgba(0, 0, 0, 0.05);
783
+
784
+ /* Focus ring */
785
+ --wf-focus-ring-width: 3px;
786
+ --wf-focus-ring-primary: rgba(128, 64, 240, 0.2);
787
+ --wf-focus-ring-error: rgba(220, 53, 69, 0.2);
788
+
789
+ /* Spacing scale */
790
+ --wf-spacing-05: 2px;
791
+ --wf-spacing-1: 4px;
792
+ --wf-spacing-2: 8px;
793
+ --wf-spacing-3: 12px;
794
+ --wf-spacing-4: 16px;
795
+ --wf-spacing-5: 20px;
796
+ --wf-spacing-6: 24px;
797
+ --wf-spacing-8: 32px;
798
+
799
+ /* Border radius */
800
+ --wf-radius-sm: 4px;
801
+ --wf-radius-md: 8px;
802
+ --wf-radius-lg: 8px;
803
+ --wf-radius-full: 99px;
804
+
805
+ /* Typography */
806
+ --wf-font-size-xs: 0.75rem;
807
+ --wf-font-size-sm: 0.875rem;
808
+ --wf-font-size-base: 1rem;
809
+ --wf-font-size-lg: 1.25rem;
810
+ --wf-font-size-xl: 1.5rem;
811
+ --wf-font-size-2xl: 2rem;
812
+ --wf-font-size-3xl: 2.5rem;
813
+ --wf-font-family-mono: ui-monospace, SFMono-Regular, SF Mono, Menlo, Consolas, Liberation Mono, monospace;
814
+ --wf-font-weight-input: 400;
815
+ --wf-font-weight-label: 500;
816
+ --wf-font-weight-heading: 600;
817
+ --wf-font-weight-button: 400;
818
+
819
+ /* Input dimensions */
820
+ --wf-input-min-height: 56px;
821
+ --wf-textarea-min-height: 100px;
822
+
823
+ /* Component dimensions */
824
+ --wf-btn-min-height: 48px;
825
+ --wf-badge-size: 24px;
826
+ --wf-spinner-size: 20px;
827
+ --wf-progress-height: 4px;
828
+
829
+ /* Frosted glass effect (iOS-style) */
830
+ --wf-glass-bg: rgba(255, 255, 255, 0.7);
831
+ --wf-glass-bg-hover: rgba(255, 255, 255, 0.85);
832
+ --wf-glass-border: rgba(0, 0, 0, 0.1);
833
+ --wf-glass-blur: 20px;
834
+ --wf-glass-shadow: 0 2px 4px rgba(0, 0, 0, 0.03);
835
+ `;
836
+ const hostTokens = i$3`
837
+ :host {
838
+ ${designTokens}
839
+ }
840
+ `;
841
+ i$3`
842
+ --wf-color-surface: #2d2d2d;
843
+ --wf-color-surface-hover: #3d3d3d;
844
+ --wf-color-border: #4d4d4d;
845
+ --wf-color-text: #f8f9fa;
846
+ --wf-color-text-secondary: #d0d0d0;
847
+ --wf-color-text-muted: #adb5bd;
848
+ --wf-color-badge-bg: #3d3d3d;
849
+ --wf-color-badge-border: #4d4d4d;
850
+ --wf-color-badge-text: #adb5bd;
851
+ --wf-color-progress-active: rgba(200, 200, 200, 0.6);
852
+ --wf-color-progress-inactive: rgba(100, 100, 100, 0.6);
853
+
854
+ /* Dark theme frosted glass */
855
+ --wf-glass-bg: rgba(45, 45, 45, 0.7);
856
+ --wf-glass-bg-hover: rgba(60, 60, 60, 0.8);
857
+ --wf-glass-border: rgba(255, 255, 255, 0.1);
858
+ `;
859
+ const sharedAnimations = i$3`@keyframes wf-spin{to{transform:rotate(360deg)}}@keyframes wf-blink{0%,to{opacity:1}50%{opacity:.5}}@keyframes wf-stepFadeIn{0%{opacity:0;transform:translateY(10px)}to{opacity:1;transform:translateY(0)}}@keyframes wf-stepFadeOut{0%{opacity:1;transform:translateY(0)}to{opacity:0;transform:translateY(-10px)}}@keyframes wf-stepSlideInRight{0%{opacity:0;transform:translate(30px)}to{opacity:1;transform:translate(0)}}@keyframes wf-stepSlideInLeft{0%{opacity:0;transform:translate(-30px)}to{opacity:1;transform:translate(0)}}`;
860
+ const buttonBaseStyles = i$3`.wf-btn{justify-content:center;align-items:center;gap:var(--wf-spacing-2);padding:var(--wf-spacing-3)var(--wf-spacing-4);min-height:var(--wf-btn-min-height);font-size:var(--wf-font-size-base);font-weight:var(--wf-font-weight-button);border-radius:var(--wf-radius-md);cursor:pointer;box-sizing:border-box;border:1px solid #0000;outline:none;font-family:inherit;transition:all .15s;display:inline-flex}.wf-btn:focus-visible{box-shadow:0 0 0 var(--wf-focus-ring-width)var(--wf-focus-ring-primary)}.wf-btn:disabled{opacity:.5;cursor:not-allowed}`;
861
+ i$3`.wf-glass{background:var(--wf-glass-bg);-webkit-backdrop-filter:blur(var(--wf-glass-blur));border:1px solid var(--wf-glass-border);box-shadow:var(--wf-glass-shadow)}.wf-glass:hover{background:var(--wf-glass-bg-hover)}`;
862
+ i$3`
863
+ ${sharedAnimations}
864
+
865
+ * {
866
+ box-sizing: border-box;
867
+ }
868
+ `;
869
+ const wizardFormStyles = [
870
+ sharedAnimations,
871
+ i$3`
872
+ /* ----------------------------------------
873
+ :host - Design tokens & base styles
874
+ ---------------------------------------- */
875
+ :host {
876
+ display: block;
877
+
878
+ /* Color tokens */
879
+ --wf-color-primary: #8040f0;
880
+ --wf-color-primary-border: #602cbb;
881
+ --wf-color-primary-light: rgba(128, 64, 240, 0.08);
882
+ --wf-color-surface: #f3f3f5;
883
+ --wf-color-surface-hover: #e9e9eb;
884
+ --wf-color-border: #d4d4d4;
885
+ --wf-color-text: #0a0a0a;
886
+ --wf-color-text-secondary: #404040;
887
+ --wf-color-text-muted: #646464;
888
+ --wf-color-error: #dc3545;
889
+ --wf-color-error-light: rgba(220, 53, 69, 0.1);
890
+ --wf-color-badge-bg: #fcfcfc;
891
+ --wf-color-badge-border: #d4d4d4;
892
+ --wf-color-badge-text: #5f5f5f;
893
+ --wf-color-progress-active: rgba(0, 0, 0, 0.1);
894
+ --wf-color-progress-inactive: rgba(0, 0, 0, 0.05);
895
+
896
+ /* Focus ring */
897
+ --wf-focus-ring-width: 3px;
898
+ --wf-focus-ring-primary: rgba(128, 64, 240, 0.2);
899
+ --wf-focus-ring-error: rgba(220, 53, 69, 0.2);
900
+
901
+ /* Spacing tokens */
902
+ --wf-spacing-05: 2px;
903
+ --wf-spacing-1: 4px;
904
+ --wf-spacing-2: 8px;
905
+ --wf-spacing-3: 12px;
906
+ --wf-spacing-4: 16px;
907
+ --wf-spacing-5: 20px;
908
+ --wf-spacing-6: 24px;
909
+ --wf-spacing-8: 32px;
910
+
911
+ /* Border radius tokens */
912
+ --wf-radius-sm: 4px;
913
+ --wf-radius-md: 8px;
914
+ --wf-radius-lg: 8px;
915
+ --wf-radius-full: 99px;
916
+
917
+ /* Typography tokens */
918
+ --wf-font-size-xs: 0.75rem;
919
+ --wf-font-size-sm: 0.875rem;
920
+ --wf-font-size-base: 1rem;
921
+ --wf-font-size-lg: 1.25rem;
922
+ --wf-font-size-xl: 1.5rem;
923
+ --wf-font-size-2xl: 2rem;
924
+ --wf-font-size-3xl: 2.5rem;
925
+ --wf-font-family-mono: ui-monospace, SFMono-Regular, SF Mono, Menlo, Consolas, Liberation Mono, monospace;
926
+ --wf-font-weight-input: 400;
927
+ --wf-font-weight-label: 500;
928
+ --wf-font-weight-heading: 600;
929
+ --wf-font-weight-button: 400;
930
+
931
+ /* Input tokens */
932
+ --wf-input-min-height: 56px;
933
+ --wf-textarea-min-height: 100px;
934
+
935
+ /* Component dimensions */
936
+ --wf-btn-min-height: 48px;
937
+ --wf-badge-size: 24px;
938
+ --wf-spinner-size: 20px;
939
+ --wf-progress-height: 4px;
940
+
941
+ /* Frosted glass effect (iOS-style) */
942
+ --wf-glass-bg: rgba(255, 255, 255, 0.7);
943
+ --wf-glass-bg-hover: rgba(255, 255, 255, 0.85);
944
+ --wf-glass-border: rgba(0, 0, 0, 0.1);
945
+ --wf-glass-blur: 20px;
946
+ --wf-glass-shadow: 0 2px 4px rgba(0, 0, 0, 0.03);
947
+ }
948
+
949
+ :host([hidden]) {
950
+ display: none;
951
+ }
952
+
953
+ /* Dark theme */
954
+ :host([theme='dark']) {
955
+ --wf-color-surface: #2d2d2d;
956
+ --wf-color-surface-hover: #3d3d3d;
957
+ --wf-color-border: #4d4d4d;
958
+ --wf-color-text: #f8f9fa;
959
+ --wf-color-text-secondary: #d0d0d0;
960
+ --wf-color-text-muted: #adb5bd;
961
+ --wf-color-badge-bg: #3d3d3d;
962
+ --wf-color-badge-border: #4d4d4d;
963
+ --wf-color-badge-text: #adb5bd;
964
+ --wf-color-progress-active: rgba(200, 200, 200, 0.6);
965
+ --wf-color-progress-inactive: rgba(100, 100, 100, 0.6);
966
+
967
+ /* Dark theme frosted glass */
968
+ --wf-glass-bg: rgba(45, 45, 45, 0.7);
969
+ --wf-glass-bg-hover: rgba(60, 60, 60, 0.8);
970
+ --wf-glass-border: rgba(255, 255, 255, 0.1);
971
+ }
972
+
973
+ /* Auto theme (respects system preference) */
974
+ @media (prefers-color-scheme: dark) {
975
+ :host([theme='auto']) {
976
+ --wf-color-surface: #2d2d2d;
977
+ --wf-color-surface-hover: #3d3d3d;
978
+ --wf-color-border: #4d4d4d;
979
+ --wf-color-text: #f8f9fa;
980
+ --wf-color-text-secondary: #d0d0d0;
981
+ --wf-color-text-muted: #adb5bd;
982
+ --wf-color-badge-bg: #3d3d3d;
983
+ --wf-color-badge-border: #4d4d4d;
984
+ --wf-color-badge-text: #adb5bd;
985
+ --wf-color-progress-active: rgba(200, 200, 200, 0.6);
986
+ --wf-color-progress-inactive: rgba(100, 100, 100, 0.6);
987
+
988
+ /* Dark theme frosted glass */
989
+ --wf-glass-bg: rgba(45, 45, 45, 0.7);
990
+ --wf-glass-bg-hover: rgba(60, 60, 60, 0.8);
991
+ --wf-glass-border: rgba(255, 255, 255, 0.1);
992
+ }
993
+ }
994
+
995
+ /* ----------------------------------------
996
+ Container
997
+ ---------------------------------------- */
998
+ .wf-container {
999
+ margin: 0 auto;
1000
+ }
1001
+
1002
+ /* ----------------------------------------
1003
+ Success screen
1004
+ ---------------------------------------- */
1005
+ .wf-success-screen {
1006
+ text-align: center;
1007
+ padding: var(--wf-spacing-6);
1008
+ }
1009
+
1010
+ /* ----------------------------------------
1011
+ Error message
1012
+ ---------------------------------------- */
1013
+ .wf-form-error {
1014
+ padding: var(--wf-spacing-4);
1015
+ margin-bottom: var(--wf-spacing-4);
1016
+ background-color: var(--wf-color-error-light);
1017
+ border: 1px solid var(--wf-color-error);
1018
+ border-radius: var(--wf-radius-md);
1019
+ color: var(--wf-color-error);
1020
+ font-size: var(--wf-font-size-base);
1021
+ }
1022
+
1023
+ /* ----------------------------------------
1024
+ Slot styles
1025
+ ---------------------------------------- */
1026
+ ::slotted(wf-step) {
1027
+ display: none;
1028
+ width: 100%;
1029
+ }
1030
+
1031
+ ::slotted(wf-step[active]) {
1032
+ display: block;
1033
+ animation: wf-stepFadeIn 0.3s ease forwards;
1034
+ }
1035
+
1036
+ ::slotted(wf-step[direction='forward'][active]) {
1037
+ animation: wf-stepSlideInRight 0.3s ease forwards;
1038
+ }
1039
+
1040
+ ::slotted(wf-step[direction='backward'][active]) {
1041
+ animation: wf-stepSlideInLeft 0.3s ease forwards;
1042
+ }
1043
+
1044
+ ::slotted(wf-step[leaving]) {
1045
+ display: block;
1046
+ animation: wf-stepFadeOut 0.2s ease forwards;
1047
+ }
1048
+
1049
+ /* Success slot hidden by default, shown when submitted */
1050
+ ::slotted([slot='success']) {
1051
+ display: none;
1052
+ }
1053
+
1054
+ :host([submitted]) ::slotted([slot='success']) {
1055
+ display: block;
1056
+ }
1057
+
1058
+ :host([submitted]) ::slotted(wf-step) {
1059
+ display: none !important;
1060
+ }
1061
+ `
1062
+ ];
739
1063
  class FormStateController {
740
1064
  constructor(host) {
741
1065
  this._formData = {};
@@ -1065,14 +1389,67 @@ class KeyboardController {
1065
1389
  return this._enabled;
1066
1390
  }
1067
1391
  }
1068
- var __defProp$d = Object.defineProperty;
1069
- var __getOwnPropDesc$c = Object.getOwnPropertyDescriptor;
1070
- var __decorateClass$d = (decorators, target, key, kind) => {
1071
- var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$c(target, key) : target;
1392
+ const wfBadgeStyles = i$3`
1393
+ :host {
1394
+ display: inline-flex;
1395
+ }
1396
+
1397
+ :host([hidden]) {
1398
+ display: none;
1399
+ }
1400
+
1401
+ .wf-badge {
1402
+ display: inline-flex;
1403
+ align-items: center;
1404
+ justify-content: center;
1405
+ box-sizing: border-box;
1406
+ min-width: var(--wf-badge-size);
1407
+ height: var(--wf-badge-size);
1408
+ padding: var(--wf-spacing-1) var(--wf-spacing-2);
1409
+ font-size: var(--wf-font-size-xs);
1410
+ font-weight: var(--wf-font-weight-label);
1411
+ font-family: var(--wf-font-family-mono);
1412
+ text-transform: uppercase;
1413
+ flex-shrink: 0;
1414
+ line-height: 1;
1415
+ }
1416
+
1417
+ .wf-badge--default {
1418
+ background-color: var(--wf-color-badge-bg);
1419
+ border: 1px solid var(--wf-color-badge-border);
1420
+ border-radius: var(--wf-radius-sm);
1421
+ color: var(--wf-color-badge-text);
1422
+ }
1423
+
1424
+ .wf-badge--selected {
1425
+ background-color: var(--wf-color-primary);
1426
+ border: 1px solid var(--wf-color-primary);
1427
+ border-radius: var(--wf-radius-sm);
1428
+ color: white;
1429
+ }
1430
+
1431
+ .wf-badge--button {
1432
+ background-color: transparent;
1433
+ border: none;
1434
+ border-radius: var(--wf-radius-sm);
1435
+ color: rgba(255, 255, 255, 0.65);
1436
+ }
1437
+
1438
+ .wf-badge--button-secondary {
1439
+ background-color: transparent;
1440
+ border: none;
1441
+ border-radius: var(--wf-radius-sm);
1442
+ color: var(--wf-color-text-muted);
1443
+ }
1444
+ `;
1445
+ var __defProp$f = Object.defineProperty;
1446
+ var __getOwnPropDesc$d = Object.getOwnPropertyDescriptor;
1447
+ var __decorateClass$f = (decorators, target, key, kind) => {
1448
+ var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$d(target, key) : target;
1072
1449
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
1073
1450
  if (decorator = decorators[i2])
1074
1451
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
1075
- if (kind && result) __defProp$d(target, key, result);
1452
+ if (kind && result) __defProp$f(target, key, result);
1076
1453
  return result;
1077
1454
  };
1078
1455
  let WfBadge = class extends i {
@@ -1081,40 +1458,36 @@ let WfBadge = class extends i {
1081
1458
  this.shortcut = "";
1082
1459
  this.variant = "default";
1083
1460
  }
1084
- /**
1085
- * Disable Shadow DOM - render to Light DOM for external styling
1086
- */
1087
- createRenderRoot() {
1088
- return this;
1089
- }
1090
1461
  render() {
1091
1462
  return b`
1092
1463
  <span
1093
1464
  class="wf-badge wf-badge--${this.variant}"
1094
1465
  aria-hidden="true"
1466
+ data-testid="wf-badge"
1095
1467
  >
1096
1468
  ${this.shortcut}
1097
1469
  </span>
1098
1470
  `;
1099
1471
  }
1100
1472
  };
1101
- __decorateClass$d([
1473
+ WfBadge.styles = wfBadgeStyles;
1474
+ __decorateClass$f([
1102
1475
  n2({ type: String })
1103
1476
  ], WfBadge.prototype, "shortcut", 2);
1104
- __decorateClass$d([
1477
+ __decorateClass$f([
1105
1478
  n2({ type: String })
1106
1479
  ], WfBadge.prototype, "variant", 2);
1107
- WfBadge = __decorateClass$d([
1480
+ WfBadge = __decorateClass$f([
1108
1481
  t("wf-badge")
1109
1482
  ], WfBadge);
1110
- var __defProp$c = Object.defineProperty;
1111
- var __getOwnPropDesc$b = Object.getOwnPropertyDescriptor;
1112
- var __decorateClass$c = (decorators, target, key, kind) => {
1113
- var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$b(target, key) : target;
1483
+ var __defProp$e = Object.defineProperty;
1484
+ var __getOwnPropDesc$c = Object.getOwnPropertyDescriptor;
1485
+ var __decorateClass$e = (decorators, target, key, kind) => {
1486
+ var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$c(target, key) : target;
1114
1487
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
1115
1488
  if (decorator = decorators[i2])
1116
1489
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
1117
- if (kind && result) __defProp$c(target, key, result);
1490
+ if (kind && result) __defProp$e(target, key, result);
1118
1491
  return result;
1119
1492
  };
1120
1493
  let WizardForm = class extends i {
@@ -1133,9 +1506,10 @@ let WizardForm = class extends i {
1133
1506
  this._totalSteps = 0;
1134
1507
  this._formData = {};
1135
1508
  this._submitting = false;
1136
- this._submitted = false;
1509
+ this.submitted = false;
1137
1510
  this._error = "";
1138
- this._cachedSuccessContent = null;
1511
+ this._otherInputActive = false;
1512
+ this._partialSubmitting = false;
1139
1513
  this._stateController = new FormStateController(this);
1140
1514
  this._handleFieldChange = (e2) => {
1141
1515
  const { name, value, extraFields } = e2.detail;
@@ -1146,6 +1520,10 @@ let WizardForm = class extends i {
1146
1520
  this._formData[fieldName] = fieldValue;
1147
1521
  this._stateController.setValue(fieldName, fieldValue);
1148
1522
  });
1523
+ const hasOtherText = Object.values(extraFields).some((v2) => v2 && String(v2).trim());
1524
+ this._otherInputActive = hasOtherText;
1525
+ } else {
1526
+ this._otherInputActive = false;
1149
1527
  }
1150
1528
  this._error = "";
1151
1529
  this.dispatchEvent(
@@ -1161,6 +1539,9 @@ let WizardForm = class extends i {
1161
1539
  );
1162
1540
  };
1163
1541
  this._handleOptionSelect = (e2) => {
1542
+ if (this._stepHasComposableNav()) {
1543
+ return;
1544
+ }
1164
1545
  if (this.autoAdvance) {
1165
1546
  const target = e2.target;
1166
1547
  const optionsParent = target.closest("wf-options");
@@ -1171,17 +1552,22 @@ let WizardForm = class extends i {
1171
1552
  }
1172
1553
  }
1173
1554
  };
1555
+ this._handleNavNext = async (e2) => {
1556
+ e2.stopPropagation();
1557
+ await this._goNext();
1558
+ };
1559
+ this._handleNavBack = (e2) => {
1560
+ e2.stopPropagation();
1561
+ this._goBack();
1562
+ };
1563
+ this._handleNavStateRequest = () => {
1564
+ this._broadcastNavState();
1565
+ };
1174
1566
  new KeyboardController(this, {
1175
1567
  onEnter: () => this._handleEnter(),
1176
1568
  onEscape: () => this._handleEscape()
1177
1569
  });
1178
1570
  }
1179
- /**
1180
- * Disable Shadow DOM - render to Light DOM for external styling
1181
- */
1182
- createRenderRoot() {
1183
- return this;
1184
- }
1185
1571
  // ============================================
1186
1572
  // Lifecycle
1187
1573
  // ============================================
@@ -1189,56 +1575,56 @@ let WizardForm = class extends i {
1189
1575
  super.connectedCallback();
1190
1576
  this.addEventListener("wf-change", this._handleFieldChange);
1191
1577
  this.addEventListener("wf-option-select", this._handleOptionSelect);
1578
+ this.addEventListener("wf:nav-next", this._handleNavNext);
1579
+ this.addEventListener("wf:nav-back", this._handleNavBack);
1580
+ this.addEventListener("wf:nav-state-request", this._handleNavStateRequest);
1192
1581
  }
1193
1582
  disconnectedCallback() {
1194
1583
  super.disconnectedCallback();
1195
1584
  this.removeEventListener("wf-change", this._handleFieldChange);
1196
1585
  this.removeEventListener("wf-option-select", this._handleOptionSelect);
1586
+ this.removeEventListener("wf:nav-next", this._handleNavNext);
1587
+ this.removeEventListener("wf:nav-back", this._handleNavBack);
1588
+ this.removeEventListener("wf:nav-state-request", this._handleNavStateRequest);
1197
1589
  }
1198
1590
  firstUpdated() {
1199
- this._cachedSuccessContent = this.querySelector('[slot="success"]');
1200
1591
  this._discoverSteps();
1201
1592
  this._showCurrentStep();
1593
+ this._broadcastNavState();
1202
1594
  }
1203
1595
  // ============================================
1204
1596
  // Rendering
1205
1597
  // ============================================
1206
1598
  render() {
1207
- if (this._submitted) {
1599
+ if (this.submitted) {
1208
1600
  this._steps.forEach((step) => {
1209
1601
  step.active = false;
1210
- step.style.display = "none";
1211
1602
  });
1212
- if (this._cachedSuccessContent) {
1213
- this._cachedSuccessContent.style.display = "";
1214
- return b`
1215
- <div class="wf-container wf-submitted">
1603
+ return b`
1604
+ <div class="wf-container" data-testid="wf-container">
1605
+ <slot name="success">
1216
1606
  <div class="wf-success-screen">
1217
- ${this._cachedSuccessContent}
1607
+ <h2>Thank you!</h2>
1608
+ <p>Your submission has been received.</p>
1218
1609
  </div>
1219
- </div>
1220
- `;
1221
- }
1222
- return b`
1223
- <div class="wf-container wf-submitted">
1224
- <div class="wf-success-screen">
1225
- <h2>Thank you!</h2>
1226
- <p>Your submission has been received.</p>
1227
- </div>
1610
+ </slot>
1228
1611
  </div>
1229
1612
  `;
1230
1613
  }
1231
- if (this._cachedSuccessContent) {
1232
- this._cachedSuccessContent.style.display = "none";
1233
- }
1234
1614
  return b`
1235
- <div class="wf-container">
1236
- ${this._error ? b`<div class="wf-form-error" role="alert">${this._error}</div>` : A}
1615
+ <div class="wf-container" data-testid="wf-container">
1616
+ ${this._error ? b`<div class="wf-form-error" role="alert" data-testid="wf-form-error">${this._error}</div>` : A}
1237
1617
 
1238
- ${this._renderNavigation()}
1618
+ <slot @slotchange="${this._handleSlotChange}"></slot>
1239
1619
  </div>
1240
1620
  `;
1241
1621
  }
1622
+ /**
1623
+ * Handle slot changes to re-discover steps when DOM changes
1624
+ */
1625
+ _handleSlotChange() {
1626
+ this._discoverSteps();
1627
+ }
1242
1628
  _renderProgress() {
1243
1629
  const segments = [];
1244
1630
  for (let i2 = 1; i2 <= this._totalSteps; i2++) {
@@ -1252,41 +1638,27 @@ let WizardForm = class extends i {
1252
1638
  }
1253
1639
  return b`<div class="wf-progress">${segments}</div>`;
1254
1640
  }
1641
+ /**
1642
+ * Centralized navigation is no longer rendered.
1643
+ * All navigation is now fully composable via <wf-next-btn> and <wf-back-btn>.
1644
+ * Keyboard shortcuts (Enter/Esc) still work regardless of button presence.
1645
+ */
1255
1646
  _renderNavigation() {
1256
- const isFirst = this._currentStep === 1;
1257
- const isLast = this._currentStep === this._totalSteps;
1258
- const showBack = !this.hideBack && !isFirst;
1259
- return b`
1260
- <div class="wf-navigation">
1261
- ${showBack ? b`
1262
- <button
1263
- class="wf-btn wf-btn-back"
1264
- @click="${this._goBack}"
1265
- ?disabled="${this._submitting}"
1266
- data-testid="wf-back-btn"
1267
- >
1268
- <span class="wf-btn-shortcut"><wf-badge shortcut="Esc" variant="button-secondary"></wf-badge></span>
1269
- Back
1270
- </button>
1271
- ` : A}
1272
-
1273
- <button
1274
- class="wf-btn wf-btn-next"
1275
- @click="${this._goNext}"
1276
- ?disabled="${this._submitting}"
1277
- data-testid="wf-next-btn"
1278
- >
1279
- ${this._submitting ? b`<span class="wf-loading"></span>` : isLast ? "Submit" : "Continue"}
1280
- <span class="wf-btn-shortcut"><wf-badge shortcut="Enter ↵" variant="button"></wf-badge></span>
1281
- </button>
1282
- </div>
1283
- `;
1647
+ return A;
1284
1648
  }
1285
1649
  // ============================================
1286
1650
  // Step Discovery
1287
1651
  // ============================================
1288
1652
  _discoverSteps() {
1289
- this._steps = Array.from(this.querySelectorAll(":scope > wf-step"));
1653
+ const slot = this.shadowRoot?.querySelector("slot:not([name])");
1654
+ if (slot) {
1655
+ const assignedElements = slot.assignedElements({ flatten: true });
1656
+ this._steps = assignedElements.filter(
1657
+ (el) => el.tagName.toLowerCase() === "wf-step"
1658
+ );
1659
+ } else {
1660
+ this._steps = Array.from(this.querySelectorAll(":scope > wf-step"));
1661
+ }
1290
1662
  this._steps.forEach((step, index) => {
1291
1663
  step.step = index + 1;
1292
1664
  });
@@ -1323,6 +1695,71 @@ let WizardForm = class extends i {
1323
1695
  // ============================================
1324
1696
  // Navigation
1325
1697
  // ============================================
1698
+ /**
1699
+ * Check if the current step requires manual navigation (Continue button).
1700
+ * Returns true if step contains typing inputs or multi-select options.
1701
+ * Returns false if step only has single-select options (auto-advance handles it).
1702
+ */
1703
+ _stepRequiresManualNav() {
1704
+ if (!this.autoAdvance) {
1705
+ return true;
1706
+ }
1707
+ const currentStep = this._getStepByNumber(this._currentStep);
1708
+ if (!currentStep) {
1709
+ return true;
1710
+ }
1711
+ const typingControls = ["wf-input", "wf-email", "wf-textarea", "wf-number"];
1712
+ for (const selector of typingControls) {
1713
+ if (currentStep.querySelector(selector)) {
1714
+ return true;
1715
+ }
1716
+ }
1717
+ const multiSelectOptions = currentStep.querySelector("wf-options[multi]");
1718
+ if (multiSelectOptions) {
1719
+ return true;
1720
+ }
1721
+ const allowOtherOptions = currentStep.querySelector("wf-options[allow-other]");
1722
+ if (allowOtherOptions && this._otherInputActive) {
1723
+ return true;
1724
+ }
1725
+ return false;
1726
+ }
1727
+ /**
1728
+ * Check if the current step has composable navigation buttons at the step level.
1729
+ * Excludes buttons inside wf-other (those are for inline "Others" input only).
1730
+ * When present, auto-advance is disabled for the step.
1731
+ */
1732
+ _stepHasComposableNav() {
1733
+ const currentStep = this._getStepByNumber(this._currentStep);
1734
+ if (!currentStep) {
1735
+ return false;
1736
+ }
1737
+ const navButtons = currentStep.querySelectorAll("wf-next-btn, wf-back-btn");
1738
+ for (const btn of navButtons) {
1739
+ if (!btn.closest("wf-other")) {
1740
+ return true;
1741
+ }
1742
+ }
1743
+ return false;
1744
+ }
1745
+ /**
1746
+ * Broadcast navigation state to composable buttons.
1747
+ * Called on step changes and submit state changes.
1748
+ */
1749
+ _broadcastNavState() {
1750
+ this.dispatchEvent(
1751
+ new CustomEvent("wf:nav-state", {
1752
+ detail: {
1753
+ currentStep: this._currentStep,
1754
+ totalSteps: this._totalSteps,
1755
+ isFirstStep: this._currentStep === 1,
1756
+ isLastStep: this._currentStep === this._totalSteps,
1757
+ isSubmitting: this._submitting
1758
+ },
1759
+ bubbles: false
1760
+ })
1761
+ );
1762
+ }
1326
1763
  async _goNext() {
1327
1764
  if (this._submitting) {
1328
1765
  return;
@@ -1367,8 +1804,9 @@ let WizardForm = class extends i {
1367
1804
  const previousStep = this._currentStep;
1368
1805
  let submitted = false;
1369
1806
  let adapter;
1370
- if (this.submitOnStep && this.hubspotPortal && this.hubspotForm) {
1807
+ if (this.submitOnStep && this.hubspotPortal && this.hubspotForm && direction === "forward" && !this._partialSubmitting) {
1371
1808
  try {
1809
+ this._partialSubmitting = true;
1372
1810
  await this._submitPartialToHubSpot();
1373
1811
  submitted = true;
1374
1812
  adapter = "hubspot";
@@ -1385,6 +1823,8 @@ let WizardForm = class extends i {
1385
1823
  })
1386
1824
  );
1387
1825
  return;
1826
+ } finally {
1827
+ this._partialSubmitting = false;
1388
1828
  }
1389
1829
  }
1390
1830
  const currentStepEl = this._getStepByNumber(this._currentStep);
@@ -1393,6 +1833,8 @@ let WizardForm = class extends i {
1393
1833
  }
1394
1834
  this._currentStep = targetStep;
1395
1835
  this._stateController.goToStep(targetStep);
1836
+ this._otherInputActive = false;
1837
+ this._broadcastNavState();
1396
1838
  targetStepEl.show(direction);
1397
1839
  this.dispatchEvent(
1398
1840
  new CustomEvent("wf:step-change", {
@@ -1434,6 +1876,7 @@ let WizardForm = class extends i {
1434
1876
  }
1435
1877
  this._submitting = true;
1436
1878
  this._error = "";
1879
+ this._broadcastNavState();
1437
1880
  let submitData = rawData;
1438
1881
  if (this.serialize) {
1439
1882
  submitData = this.serialize(rawData);
@@ -1449,7 +1892,7 @@ let WizardForm = class extends i {
1449
1892
  console.warn("[WizardForm] No submission target configured. Use hubspot-portal/hubspot-form or mock.");
1450
1893
  response = { success: true };
1451
1894
  }
1452
- this._submitted = true;
1895
+ this.submitted = true;
1453
1896
  this.dispatchEvent(
1454
1897
  new CustomEvent("wf:success", {
1455
1898
  detail: {
@@ -1475,6 +1918,7 @@ let WizardForm = class extends i {
1475
1918
  );
1476
1919
  } finally {
1477
1920
  this._submitting = false;
1921
+ this._broadcastNavState();
1478
1922
  }
1479
1923
  }
1480
1924
  async _submitToHubSpot(formData) {
@@ -1526,6 +1970,7 @@ let WizardForm = class extends i {
1526
1970
  /**
1527
1971
  * Submit partial form data to HubSpot.
1528
1972
  * Only includes fields from steps up to and including the current step.
1973
+ * Filters out empty/blank values to avoid submitting unfilled fields.
1529
1974
  */
1530
1975
  async _submitPartialToHubSpot() {
1531
1976
  const partialData = this._getFieldsUpToStep(this._currentStep);
@@ -1533,7 +1978,18 @@ let WizardForm = class extends i {
1533
1978
  if (this.serialize) {
1534
1979
  submitData = this.serialize(submitData);
1535
1980
  }
1536
- await this._submitToHubSpot(submitData);
1981
+ const filteredData = Object.fromEntries(
1982
+ Object.entries(submitData).filter(([, value]) => {
1983
+ if (value === null || value === void 0 || value === "") {
1984
+ return false;
1985
+ }
1986
+ if (Array.isArray(value) && value.length === 0) {
1987
+ return false;
1988
+ }
1989
+ return true;
1990
+ })
1991
+ );
1992
+ await this._submitToHubSpot(filteredData);
1537
1993
  }
1538
1994
  // ============================================
1539
1995
  // Public API
@@ -1566,7 +2022,7 @@ let WizardForm = class extends i {
1566
2022
  * Check if form was submitted
1567
2023
  */
1568
2024
  get isSubmitted() {
1569
- return this._submitted;
2025
+ return this.submitted;
1570
2026
  }
1571
2027
  /**
1572
2028
  * Go to a specific step
@@ -1600,7 +2056,7 @@ let WizardForm = class extends i {
1600
2056
  this._formData = {};
1601
2057
  this._currentStep = 1;
1602
2058
  this._submitting = false;
1603
- this._submitted = false;
2059
+ this.submitted = false;
1604
2060
  this._error = "";
1605
2061
  this._stateController.reset();
1606
2062
  this._showCurrentStep();
@@ -1623,79 +2079,142 @@ let WizardForm = class extends i {
1623
2079
  });
1624
2080
  }
1625
2081
  };
1626
- __decorateClass$c([
2082
+ WizardForm.styles = wizardFormStyles;
2083
+ __decorateClass$e([
1627
2084
  n2({ type: String, attribute: "hubspot-portal" })
1628
2085
  ], WizardForm.prototype, "hubspotPortal", 2);
1629
- __decorateClass$c([
2086
+ __decorateClass$e([
1630
2087
  n2({ type: String, attribute: "hubspot-form" })
1631
2088
  ], WizardForm.prototype, "hubspotForm", 2);
1632
- __decorateClass$c([
2089
+ __decorateClass$e([
1633
2090
  n2({ type: String, reflect: true })
1634
2091
  ], WizardForm.prototype, "theme", 2);
1635
- __decorateClass$c([
2092
+ __decorateClass$e([
1636
2093
  n2({ type: Boolean })
1637
2094
  ], WizardForm.prototype, "mock", 2);
1638
- __decorateClass$c([
2095
+ __decorateClass$e([
1639
2096
  n2({ type: Boolean, attribute: "show-progress" })
1640
2097
  ], WizardForm.prototype, "showProgress", 2);
1641
- __decorateClass$c([
2098
+ __decorateClass$e([
1642
2099
  n2({ type: Boolean, attribute: "auto-advance" })
1643
2100
  ], WizardForm.prototype, "autoAdvance", 2);
1644
- __decorateClass$c([
2101
+ __decorateClass$e([
1645
2102
  n2({ type: Boolean, attribute: "hide-back" })
1646
2103
  ], WizardForm.prototype, "hideBack", 2);
1647
- __decorateClass$c([
2104
+ __decorateClass$e([
1648
2105
  n2({ attribute: false })
1649
2106
  ], WizardForm.prototype, "serialize", 2);
1650
- __decorateClass$c([
2107
+ __decorateClass$e([
1651
2108
  n2({ type: Boolean, attribute: "submit-on-step" })
1652
2109
  ], WizardForm.prototype, "submitOnStep", 2);
1653
- __decorateClass$c([
2110
+ __decorateClass$e([
1654
2111
  r()
1655
2112
  ], WizardForm.prototype, "_steps", 2);
1656
- __decorateClass$c([
2113
+ __decorateClass$e([
1657
2114
  r()
1658
2115
  ], WizardForm.prototype, "_currentStep", 2);
1659
- __decorateClass$c([
2116
+ __decorateClass$e([
1660
2117
  r()
1661
2118
  ], WizardForm.prototype, "_totalSteps", 2);
1662
- __decorateClass$c([
2119
+ __decorateClass$e([
1663
2120
  r()
1664
2121
  ], WizardForm.prototype, "_formData", 2);
1665
- __decorateClass$c([
2122
+ __decorateClass$e([
1666
2123
  r()
1667
2124
  ], WizardForm.prototype, "_submitting", 2);
1668
- __decorateClass$c([
1669
- r()
1670
- ], WizardForm.prototype, "_submitted", 2);
1671
- __decorateClass$c([
2125
+ __decorateClass$e([
2126
+ n2({ type: Boolean, reflect: true })
2127
+ ], WizardForm.prototype, "submitted", 2);
2128
+ __decorateClass$e([
1672
2129
  r()
1673
2130
  ], WizardForm.prototype, "_error", 2);
1674
- WizardForm = __decorateClass$c([
2131
+ __decorateClass$e([
2132
+ r()
2133
+ ], WizardForm.prototype, "_otherInputActive", 2);
2134
+ WizardForm = __decorateClass$e([
1675
2135
  t("wizard-form")
1676
2136
  ], WizardForm);
1677
2137
  let WfSuccess = class extends i {
1678
- /**
1679
- * Disable Shadow DOM - render to Light DOM for external styling
1680
- */
1681
- createRenderRoot() {
1682
- return this;
1683
- }
1684
2138
  render() {
1685
- return b``;
2139
+ return b`<slot></slot>`;
1686
2140
  }
1687
2141
  };
1688
- WfSuccess = __decorateClass$c([
2142
+ WfSuccess.styles = i$3`
2143
+ :host {
2144
+ display: block;
2145
+ }
2146
+
2147
+ :host([hidden]) {
2148
+ display: none;
2149
+ }
2150
+ `;
2151
+ WfSuccess = __decorateClass$e([
1689
2152
  t("wf-success")
1690
2153
  ], WfSuccess);
1691
- var __defProp$b = Object.defineProperty;
1692
- var __getOwnPropDesc$a = Object.getOwnPropertyDescriptor;
1693
- var __decorateClass$b = (decorators, target, key, kind) => {
1694
- var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$a(target, key) : target;
2154
+ const wfStepStyles = [
2155
+ sharedAnimations,
2156
+ i$3`
2157
+ :host {
2158
+ display: none;
2159
+ width: 100%;
2160
+ }
2161
+
2162
+ :host([hidden]) {
2163
+ display: none !important;
2164
+ }
2165
+
2166
+ :host([active]) {
2167
+ display: block;
2168
+ animation: wf-stepFadeIn 0.3s ease forwards;
2169
+ }
2170
+
2171
+ :host([direction='forward'][active]) {
2172
+ animation: wf-stepSlideInRight 0.3s ease forwards;
2173
+ }
2174
+
2175
+ :host([direction='backward'][active]) {
2176
+ animation: wf-stepSlideInLeft 0.3s ease forwards;
2177
+ }
2178
+
2179
+ :host([leaving]) {
2180
+ display: block;
2181
+ animation: wf-stepFadeOut 0.2s ease forwards;
2182
+ }
2183
+
2184
+ .wf-step-content {
2185
+ display: flex;
2186
+ flex-direction: column;
2187
+ gap: var(--wf-spacing-4);
2188
+ }
2189
+
2190
+ /* Slotted heading styles */
2191
+ ::slotted(h1),
2192
+ ::slotted(h2),
2193
+ ::slotted(h3) {
2194
+ margin: 0;
2195
+ font-weight: var(--wf-font-weight-heading);
2196
+ color: var(--wf-color-text);
2197
+ }
2198
+
2199
+ ::slotted(h2) {
2200
+ font-size: var(--wf-font-size-3xl);
2201
+ }
2202
+
2203
+ ::slotted(p) {
2204
+ margin: 0;
2205
+ color: var(--wf-color-text-muted);
2206
+ font-size: var(--wf-font-size-xl);
2207
+ }
2208
+ `
2209
+ ];
2210
+ var __defProp$d = Object.defineProperty;
2211
+ var __getOwnPropDesc$b = Object.getOwnPropertyDescriptor;
2212
+ var __decorateClass$d = (decorators, target, key, kind) => {
2213
+ var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$b(target, key) : target;
1695
2214
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
1696
2215
  if (decorator = decorators[i2])
1697
2216
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
1698
- if (kind && result) __defProp$b(target, key, result);
2217
+ if (kind && result) __defProp$d(target, key, result);
1699
2218
  return result;
1700
2219
  };
1701
2220
  let WfStep = class extends i {
@@ -1708,15 +2227,11 @@ let WfStep = class extends i {
1708
2227
  this.skipIf = "";
1709
2228
  this._fields = [];
1710
2229
  }
1711
- /**
1712
- * Disable Shadow DOM - render to Light DOM for external styling
1713
- */
1714
- createRenderRoot() {
1715
- return this;
1716
- }
1717
2230
  render() {
1718
2231
  return b`
1719
- <div class="wf-step-content"></div>
2232
+ <div class="wf-step-content" data-testid="wf-step-content">
2233
+ <slot></slot>
2234
+ </div>
1720
2235
  `;
1721
2236
  }
1722
2237
  firstUpdated() {
@@ -1884,35 +2399,59 @@ let WfStep = class extends i {
1884
2399
  return allValid;
1885
2400
  }
1886
2401
  };
1887
- __decorateClass$b([
2402
+ WfStep.styles = wfStepStyles;
2403
+ __decorateClass$d([
1888
2404
  n2({ type: Number, attribute: "data-step" })
1889
2405
  ], WfStep.prototype, "step", 2);
1890
- __decorateClass$b([
2406
+ __decorateClass$d([
1891
2407
  n2({ type: Boolean, reflect: true })
1892
2408
  ], WfStep.prototype, "active", 2);
1893
- __decorateClass$b([
2409
+ __decorateClass$d([
1894
2410
  n2({ type: String, reflect: true })
1895
2411
  ], WfStep.prototype, "direction", 2);
1896
- __decorateClass$b([
2412
+ __decorateClass$d([
1897
2413
  n2({ type: Boolean, reflect: true })
1898
2414
  ], WfStep.prototype, "leaving", 2);
1899
- __decorateClass$b([
2415
+ __decorateClass$d([
1900
2416
  n2({ type: String, attribute: "data-skip-if" })
1901
2417
  ], WfStep.prototype, "skipIf", 2);
1902
- __decorateClass$b([
2418
+ __decorateClass$d([
1903
2419
  r()
1904
2420
  ], WfStep.prototype, "_fields", 2);
1905
- WfStep = __decorateClass$b([
2421
+ WfStep = __decorateClass$d([
1906
2422
  t("wf-step")
1907
2423
  ], WfStep);
1908
- var __defProp$a = Object.defineProperty;
1909
- var __getOwnPropDesc$9 = Object.getOwnPropertyDescriptor;
1910
- var __decorateClass$a = (decorators, target, key, kind) => {
1911
- var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$9(target, key) : target;
2424
+ const wfLayoutStyles = i$3`
2425
+ :host {
2426
+ display: block;
2427
+ box-sizing: border-box;
2428
+ }
2429
+
2430
+ :host([hidden]) {
2431
+ display: none;
2432
+ }
2433
+
2434
+ /* Width classes */
2435
+ :host(.wf-layout--width-full) {
2436
+ width: 100%;
2437
+ }
2438
+
2439
+ :host(.wf-layout--width-auto) {
2440
+ width: auto;
2441
+ }
2442
+
2443
+ :host(.wf-layout--width-fit) {
2444
+ width: fit-content;
2445
+ }
2446
+ `;
2447
+ var __defProp$c = Object.defineProperty;
2448
+ var __getOwnPropDesc$a = Object.getOwnPropertyDescriptor;
2449
+ var __decorateClass$c = (decorators, target, key, kind) => {
2450
+ var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$a(target, key) : target;
1912
2451
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
1913
2452
  if (decorator = decorators[i2])
1914
2453
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
1915
- if (kind && result) __defProp$a(target, key, result);
2454
+ if (kind && result) __defProp$c(target, key, result);
1916
2455
  return result;
1917
2456
  };
1918
2457
  const SPACING_SCALE = {
@@ -1942,13 +2481,7 @@ let WfLayout = class extends i {
1942
2481
  this.minItemWidth = "200px";
1943
2482
  }
1944
2483
  /**
1945
- * Disable Shadow DOM - render to Light DOM for external styling
1946
- */
1947
- createRenderRoot() {
1948
- return this;
1949
- }
1950
- /**
1951
- * Convert spacing value to pixels
2484
+ * Convert spacing value to pixels
1952
2485
  */
1953
2486
  _resolveSpacing(value) {
1954
2487
  if (!value || value === "none") {
@@ -2030,6 +2563,53 @@ let WfLayout = class extends i {
2030
2563
  }
2031
2564
  return styles.join("; ");
2032
2565
  }
2566
+ /**
2567
+ * Apply data-* attributes from children as inline styles
2568
+ * Supports: data-span, data-row-span, data-grow, data-shrink, data-align, data-order
2569
+ */
2570
+ _applyChildStyles() {
2571
+ if (!this._slot) {
2572
+ return;
2573
+ }
2574
+ const children = this._slot.assignedElements({ flatten: true });
2575
+ for (const child of children) {
2576
+ const el = child;
2577
+ const styles = [];
2578
+ const span = el.getAttribute("data-span");
2579
+ if (span) {
2580
+ styles.push(`grid-column: span ${span}`);
2581
+ }
2582
+ const rowSpan = el.getAttribute("data-row-span");
2583
+ if (rowSpan) {
2584
+ styles.push(`grid-row: span ${rowSpan}`);
2585
+ }
2586
+ if (el.hasAttribute("data-grow")) {
2587
+ styles.push("flex-grow: 1");
2588
+ }
2589
+ if (el.hasAttribute("data-shrink")) {
2590
+ styles.push("flex-shrink: 0");
2591
+ }
2592
+ const align = el.getAttribute("data-align");
2593
+ if (align) {
2594
+ styles.push(`align-self: ${align}`);
2595
+ }
2596
+ const order = el.getAttribute("data-order");
2597
+ if (order) {
2598
+ styles.push(`order: ${order}`);
2599
+ }
2600
+ if (styles.length > 0) {
2601
+ const existingStyles = el.style.cssText;
2602
+ const newStyles = styles.join("; ");
2603
+ el.style.cssText = existingStyles ? `${existingStyles}; ${newStyles}` : newStyles;
2604
+ }
2605
+ }
2606
+ }
2607
+ /**
2608
+ * Handle slot changes to apply child styles
2609
+ */
2610
+ _handleLayoutSlotChange() {
2611
+ this._applyChildStyles();
2612
+ }
2033
2613
  /**
2034
2614
  * Apply styles to host element when properties change
2035
2615
  */
@@ -2038,92 +2618,379 @@ let WfLayout = class extends i {
2038
2618
  this.style.cssText = this._buildStyles();
2039
2619
  this.classList.remove("wf-layout--width-full", "wf-layout--width-auto", "wf-layout--width-fit");
2040
2620
  this.classList.add(`wf-layout--width-${this.width}`);
2621
+ this._applyChildStyles();
2041
2622
  }
2042
2623
  render() {
2043
- return b``;
2624
+ return b`<slot @slotchange="${this._handleLayoutSlotChange}"></slot>`;
2044
2625
  }
2045
2626
  };
2046
- __decorateClass$a([
2627
+ WfLayout.styles = wfLayoutStyles;
2628
+ __decorateClass$c([
2047
2629
  n2({ type: String })
2048
2630
  ], WfLayout.prototype, "mode", 2);
2049
- __decorateClass$a([
2631
+ __decorateClass$c([
2050
2632
  n2({ type: String })
2051
2633
  ], WfLayout.prototype, "direction", 2);
2052
- __decorateClass$a([
2634
+ __decorateClass$c([
2053
2635
  n2({ type: String })
2054
2636
  ], WfLayout.prototype, "gap", 2);
2055
- __decorateClass$a([
2637
+ __decorateClass$c([
2056
2638
  n2({ type: String, attribute: "gap-x" })
2057
2639
  ], WfLayout.prototype, "gapX", 2);
2058
- __decorateClass$a([
2640
+ __decorateClass$c([
2059
2641
  n2({ type: String, attribute: "gap-y" })
2060
2642
  ], WfLayout.prototype, "gapY", 2);
2061
- __decorateClass$a([
2643
+ __decorateClass$c([
2062
2644
  n2({ type: String })
2063
2645
  ], WfLayout.prototype, "align", 2);
2064
- __decorateClass$a([
2646
+ __decorateClass$c([
2065
2647
  n2({ type: String })
2066
2648
  ], WfLayout.prototype, "justify", 2);
2067
- __decorateClass$a([
2649
+ __decorateClass$c([
2068
2650
  n2({ type: String })
2069
2651
  ], WfLayout.prototype, "padding", 2);
2070
- __decorateClass$a([
2652
+ __decorateClass$c([
2071
2653
  n2({ type: String, attribute: "padding-x" })
2072
2654
  ], WfLayout.prototype, "paddingX", 2);
2073
- __decorateClass$a([
2655
+ __decorateClass$c([
2074
2656
  n2({ type: String, attribute: "padding-y" })
2075
2657
  ], WfLayout.prototype, "paddingY", 2);
2076
- __decorateClass$a([
2658
+ __decorateClass$c([
2077
2659
  n2({ type: Boolean })
2078
2660
  ], WfLayout.prototype, "wrap", 2);
2079
- __decorateClass$a([
2661
+ __decorateClass$c([
2080
2662
  n2({ type: String })
2081
2663
  ], WfLayout.prototype, "width", 2);
2082
- __decorateClass$a([
2664
+ __decorateClass$c([
2083
2665
  n2({ type: String })
2084
2666
  ], WfLayout.prototype, "columns", 2);
2085
- __decorateClass$a([
2667
+ __decorateClass$c([
2086
2668
  n2({ type: String, attribute: "min-item-width" })
2087
2669
  ], WfLayout.prototype, "minItemWidth", 2);
2088
- WfLayout = __decorateClass$a([
2670
+ __decorateClass$c([
2671
+ e("slot")
2672
+ ], WfLayout.prototype, "_slot", 2);
2673
+ WfLayout = __decorateClass$c([
2089
2674
  t("wf-layout")
2090
2675
  ], WfLayout);
2091
- var __defProp$9 = Object.defineProperty;
2676
+ const wfOptionsStyles = i$3`
2677
+ :host {
2678
+ display: grid;
2679
+ box-sizing: border-box;
2680
+ }
2681
+
2682
+ :host([hidden]) {
2683
+ display: none;
2684
+ }
2685
+
2686
+ /* Width classes inherited from WfLayout */
2687
+ :host(.wf-layout--width-full) {
2688
+ width: 100%;
2689
+ }
2690
+
2691
+ :host(.wf-layout--width-auto) {
2692
+ width: auto;
2693
+ }
2694
+
2695
+ :host(.wf-layout--width-fit) {
2696
+ width: fit-content;
2697
+ }
2698
+
2699
+ /* Error wrapper for animated expand/collapse */
2700
+ .wf-error-wrapper {
2701
+ grid-column: 1 / -1;
2702
+ order: 1000;
2703
+ display: grid;
2704
+ grid-template-rows: 0fr;
2705
+ transition: grid-template-rows 200ms ease-out;
2706
+ }
2707
+
2708
+ .wf-error-wrapper.wf-has-error {
2709
+ grid-template-rows: 1fr;
2710
+ }
2711
+
2712
+ .wf-error-message {
2713
+ overflow: hidden;
2714
+ min-height: 0;
2715
+ font-size: var(--wf-font-size-sm);
2716
+ color: var(--wf-color-error);
2717
+ opacity: 0;
2718
+ transform: translateY(-4px);
2719
+ transition: opacity 200ms ease-out, transform 200ms ease-out;
2720
+ }
2721
+
2722
+ .wf-has-error .wf-error-message {
2723
+ margin-top: var(--wf-spacing-2);
2724
+ opacity: 1;
2725
+ transform: translateY(0);
2726
+ }
2727
+
2728
+ /* Slotted wf-other spans full width and appears after options */
2729
+ ::slotted(wf-other) {
2730
+ grid-column: 1 / -1;
2731
+ order: 999;
2732
+ }
2733
+ `;
2734
+ const wfOtherStyles = i$3`
2735
+ :host {
2736
+ display: block;
2737
+ }
2738
+
2739
+ :host([hidden]) {
2740
+ display: none;
2741
+ }
2742
+
2743
+ .wf-other-container {
2744
+ margin-top: var(--wf-spacing-4);
2745
+ }
2746
+
2747
+ .wf-other-label {
2748
+ display: block;
2749
+ margin-bottom: var(--wf-spacing-2);
2750
+ font-size: var(--wf-font-size-sm);
2751
+ font-weight: var(--wf-font-weight-label);
2752
+ color: var(--wf-color-text);
2753
+ }
2754
+
2755
+ .wf-other-label span {
2756
+ font-weight: var(--wf-font-weight-input);
2757
+ color: var(--wf-color-text-muted);
2758
+ }
2759
+
2760
+ .wf-other-input-wrapper {
2761
+ display: flex;
2762
+ align-items: center;
2763
+ gap: var(--wf-spacing-3);
2764
+ min-height: var(--wf-input-min-height);
2765
+ background: var(--wf-glass-bg);
2766
+ backdrop-filter: blur(var(--wf-glass-blur));
2767
+ -webkit-backdrop-filter: blur(var(--wf-glass-blur));
2768
+ border: 1px solid var(--wf-glass-border);
2769
+ border-radius: var(--wf-radius-md);
2770
+ box-shadow: var(--wf-glass-shadow);
2771
+ padding-left: var(--wf-spacing-3);
2772
+ transition: border-color 150ms ease, box-shadow 150ms ease, background 150ms ease;
2773
+ }
2774
+
2775
+ .wf-other-input-wrapper:focus-within {
2776
+ border-color: var(--wf-color-primary);
2777
+ box-shadow: 0 0 0 var(--wf-focus-ring-width) var(--wf-focus-ring-primary);
2778
+ }
2779
+
2780
+ .wf-other-input {
2781
+ flex: 1;
2782
+ min-height: calc(var(--wf-input-min-height) - 2px);
2783
+ padding: var(--wf-spacing-3);
2784
+ padding-left: 0;
2785
+ font-size: var(--wf-font-size-base);
2786
+ font-weight: var(--wf-font-weight-input);
2787
+ color: var(--wf-color-text);
2788
+ background: transparent;
2789
+ border: none;
2790
+ outline: none;
2791
+ box-sizing: border-box;
2792
+ }
2793
+
2794
+ .wf-other-input::placeholder {
2795
+ color: var(--wf-color-text-muted);
2796
+ font-weight: var(--wf-font-weight-input);
2797
+ }
2798
+
2799
+ .wf-other-actions {
2800
+ display: flex;
2801
+ align-items: center;
2802
+ justify-content: stretch;
2803
+ }
2804
+
2805
+ /* Ensure slotted button fills the action column */
2806
+ .wf-other-actions ::slotted(*) {
2807
+ width: 100%;
2808
+ }
2809
+ `;
2810
+ var __defProp$b = Object.defineProperty;
2811
+ var __getOwnPropDesc$9 = Object.getOwnPropertyDescriptor;
2812
+ var __decorateClass$b = (decorators, target, key, kind) => {
2813
+ var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$9(target, key) : target;
2814
+ for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
2815
+ if (decorator = decorators[i2])
2816
+ result = (kind ? decorator(target, key, result) : decorator(result)) || result;
2817
+ if (kind && result) __defProp$b(target, key, result);
2818
+ return result;
2819
+ };
2820
+ let WfOther = class extends i {
2821
+ constructor() {
2822
+ super(...arguments);
2823
+ this.label = "Others, please specify:";
2824
+ this.placeholder = "";
2825
+ this.parentValue = "Others";
2826
+ this.required = false;
2827
+ this.disabled = false;
2828
+ this.shortcut = "";
2829
+ this._value = "";
2830
+ this._handleInput = (e2) => {
2831
+ const input = e2.target;
2832
+ this._value = input.value;
2833
+ this._notifyChange();
2834
+ };
2835
+ }
2836
+ // ============================================
2837
+ // Public API
2838
+ // ============================================
2839
+ /**
2840
+ * Get current value
2841
+ */
2842
+ get value() {
2843
+ return this._value;
2844
+ }
2845
+ /**
2846
+ * Set value
2847
+ */
2848
+ set value(val) {
2849
+ this._value = val;
2850
+ }
2851
+ /**
2852
+ * Clear the input value
2853
+ */
2854
+ clear() {
2855
+ this._value = "";
2856
+ this._notifyChange();
2857
+ }
2858
+ /**
2859
+ * Focus the input
2860
+ */
2861
+ focusInput() {
2862
+ const input = this.shadowRoot?.querySelector(".wf-other-input");
2863
+ input?.focus();
2864
+ }
2865
+ _notifyChange() {
2866
+ this.dispatchEvent(
2867
+ new CustomEvent("wf-other-change", {
2868
+ detail: {
2869
+ value: this._value,
2870
+ name: this.name
2871
+ },
2872
+ bubbles: true,
2873
+ composed: true
2874
+ })
2875
+ );
2876
+ }
2877
+ // ============================================
2878
+ // Render
2879
+ // ============================================
2880
+ render() {
2881
+ return b`
2882
+ <div class="wf-other-container" data-testid="wf-other">
2883
+ <label class="wf-other-label">
2884
+ ${this.label}
2885
+ ${this.labelHint ? b`<span>${this.labelHint}</span>` : A}
2886
+ </label>
2887
+ <wf-layout mode="grid" columns="4" gap="md">
2888
+ <div class="wf-other-input-wrapper" data-span="3">
2889
+ ${this.shortcut ? b`<wf-badge shortcut="${this.shortcut}"></wf-badge>` : A}
2890
+ <input
2891
+ type="text"
2892
+ class="wf-other-input"
2893
+ placeholder="${this.placeholder}"
2894
+ .value="${this._value}"
2895
+ ?disabled="${this.disabled}"
2896
+ ?required="${this.required}"
2897
+ @input="${this._handleInput}"
2898
+ data-testid="wf-other-input"
2899
+ />
2900
+ </div>
2901
+ <!-- Slot for action buttons (like wf-next-btn) -->
2902
+ <div class="wf-other-actions">
2903
+ <slot></slot>
2904
+ </div>
2905
+ </wf-layout>
2906
+ </div>
2907
+ `;
2908
+ }
2909
+ };
2910
+ WfOther.styles = wfOtherStyles;
2911
+ __decorateClass$b([
2912
+ n2({ type: String })
2913
+ ], WfOther.prototype, "label", 2);
2914
+ __decorateClass$b([
2915
+ n2({ type: String, attribute: "label-hint" })
2916
+ ], WfOther.prototype, "labelHint", 2);
2917
+ __decorateClass$b([
2918
+ n2({ type: String })
2919
+ ], WfOther.prototype, "placeholder", 2);
2920
+ __decorateClass$b([
2921
+ n2({ type: String })
2922
+ ], WfOther.prototype, "name", 2);
2923
+ __decorateClass$b([
2924
+ n2({ type: String, attribute: "parent-value" })
2925
+ ], WfOther.prototype, "parentValue", 2);
2926
+ __decorateClass$b([
2927
+ n2({ type: Boolean })
2928
+ ], WfOther.prototype, "required", 2);
2929
+ __decorateClass$b([
2930
+ n2({ type: Boolean })
2931
+ ], WfOther.prototype, "disabled", 2);
2932
+ __decorateClass$b([
2933
+ n2({ type: String })
2934
+ ], WfOther.prototype, "shortcut", 2);
2935
+ __decorateClass$b([
2936
+ r()
2937
+ ], WfOther.prototype, "_value", 2);
2938
+ WfOther = __decorateClass$b([
2939
+ t("wf-other")
2940
+ ], WfOther);
2941
+ var __defProp$a = Object.defineProperty;
2092
2942
  var __getOwnPropDesc$8 = Object.getOwnPropertyDescriptor;
2093
- var __decorateClass$9 = (decorators, target, key, kind) => {
2943
+ var __decorateClass$a = (decorators, target, key, kind) => {
2094
2944
  var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$8(target, key) : target;
2095
2945
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
2096
2946
  if (decorator = decorators[i2])
2097
2947
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
2098
- if (kind && result) __defProp$9(target, key, result);
2948
+ if (kind && result) __defProp$a(target, key, result);
2099
2949
  return result;
2100
2950
  };
2101
- let WfOptions = class extends i {
2951
+ let WfOptions = class extends WfLayout {
2102
2952
  constructor() {
2103
2953
  super(...arguments);
2954
+ this.mode = "grid";
2955
+ this.gap = "md";
2104
2956
  this.name = "";
2105
2957
  this.multi = false;
2106
2958
  this.required = false;
2107
2959
  this.min = 0;
2108
2960
  this.max = 0;
2109
- this.columns = 2;
2110
- this.allowOther = false;
2111
- this.otherLabel = "Other, please specify:";
2112
- this.otherPlaceholder = "Enter your answer";
2113
- this.otherRequired = false;
2114
- this.otherName = "";
2115
- this.otherFieldValue = "Others";
2961
+ this.columns = "2";
2116
2962
  this._selected = /* @__PURE__ */ new Set();
2117
2963
  this._otherValue = "";
2118
2964
  this._errorMessage = "";
2119
2965
  this._validationActivated = false;
2120
2966
  this._options = [];
2121
2967
  this._shortcutMap = /* @__PURE__ */ new Map();
2122
- this._otherShortcut = "";
2968
+ this._composableOther = null;
2969
+ this._handleComposableOtherChange = (e2) => {
2970
+ e2.stopPropagation();
2971
+ this._otherValue = e2.detail.value;
2972
+ if (this._otherValue.trim() && this._selected.size > 0) {
2973
+ this._selected.clear();
2974
+ this._updateOptionStates();
2975
+ }
2976
+ this._dispatchChange();
2977
+ };
2123
2978
  this._handleOptionSelect = (e2) => {
2979
+ if (e2.detail.forwarded) {
2980
+ return;
2981
+ }
2124
2982
  e2.stopPropagation();
2125
2983
  const { value } = e2.detail;
2126
2984
  this._selectValue(value);
2985
+ if (!this.multi) {
2986
+ this.dispatchEvent(
2987
+ new CustomEvent("wf-option-select", {
2988
+ detail: { ...e2.detail, forwarded: true },
2989
+ bubbles: true,
2990
+ composed: true
2991
+ })
2992
+ );
2993
+ }
2127
2994
  };
2128
2995
  this._handleKeydown = (e2) => {
2129
2996
  const parentStep = this.closest("wf-step");
@@ -2135,18 +3002,11 @@ let WfOptions = class extends i {
2135
3002
  if (actualTarget?.tagName === "INPUT" || actualTarget?.tagName === "TEXTAREA") {
2136
3003
  return;
2137
3004
  }
2138
- const otherInput = this.querySelector(".wf-other-input");
2139
- if (otherInput && document.activeElement === otherInput) {
2140
- return;
2141
- }
2142
3005
  const key = e2.key.toUpperCase();
2143
3006
  if (key.length === 1 && key >= "A" && key <= "Z") {
2144
- if (this.allowOther && key === this._otherShortcut) {
3007
+ if (this._composableOther && key === this._composableOther.shortcut) {
2145
3008
  e2.preventDefault();
2146
- const otherInput2 = this.querySelector(".wf-other-input");
2147
- if (otherInput2) {
2148
- otherInput2.focus();
2149
- }
3009
+ this._composableOther.focusInput();
2150
3010
  return;
2151
3011
  }
2152
3012
  const option = this._shortcutMap.get(key);
@@ -2157,88 +3017,72 @@ let WfOptions = class extends i {
2157
3017
  }
2158
3018
  };
2159
3019
  }
2160
- /**
2161
- * Disable Shadow DOM - render to Light DOM for external styling
2162
- */
2163
- createRenderRoot() {
2164
- return this;
2165
- }
2166
3020
  connectedCallback() {
2167
3021
  super.connectedCallback();
2168
3022
  this._errorMessage = "";
2169
3023
  this._validationActivated = false;
2170
3024
  this.addEventListener("wf-option-select", this._handleOptionSelect);
3025
+ this.addEventListener("wf-other-change", this._handleComposableOtherChange);
2171
3026
  document.addEventListener("keydown", this._handleKeydown);
2172
3027
  }
2173
3028
  disconnectedCallback() {
2174
3029
  super.disconnectedCallback();
2175
3030
  this.removeEventListener("wf-option-select", this._handleOptionSelect);
3031
+ this.removeEventListener("wf-other-change", this._handleComposableOtherChange);
2176
3032
  document.removeEventListener("keydown", this._handleKeydown);
2177
3033
  }
2178
- firstUpdated() {
2179
- const layout = this.querySelector("wf-layout");
2180
- const options = Array.from(this.querySelectorAll(":scope > wf-option"));
2181
- options.forEach((option) => layout?.appendChild(option));
3034
+ firstUpdated(changedProperties) {
3035
+ super.firstUpdated(changedProperties);
3036
+ const slottedElements = this._defaultSlot?.assignedElements({ flatten: true }) || [];
3037
+ const foundOther = slottedElements.find(
3038
+ (el) => el.tagName.toLowerCase() === "wf-other"
3039
+ );
3040
+ this._composableOther = foundOther ? foundOther : null;
2182
3041
  this._discoverOptions();
2183
3042
  this.requestUpdate();
2184
3043
  }
3044
+ /**
3045
+ * Check if this component has a composable wf-other child
3046
+ */
3047
+ _hasComposableOther() {
3048
+ return this._composableOther !== null;
3049
+ }
2185
3050
  updated(changedProperties) {
3051
+ super.updated(changedProperties);
2186
3052
  if (changedProperties.has("multi") || changedProperties.has("max")) {
2187
3053
  this._updateOptionStates();
2188
3054
  }
2189
3055
  }
2190
3056
  render() {
3057
+ super.updated(/* @__PURE__ */ new Map());
2191
3058
  this.setAttribute("role", "listbox");
2192
3059
  this.setAttribute("aria-multiselectable", String(this.multi));
2193
3060
  this.setAttribute("aria-required", String(this.required));
2194
3061
  return b`
2195
- <wf-layout mode="grid" columns="${this.columns}" gap="md">
2196
- <!-- wf-option children will be moved here in firstUpdated -->
2197
- </wf-layout>
2198
- ${this.allowOther ? b`
2199
- <div class="wf-other-container">
2200
- <label class="wf-other-label">${this.otherLabel}</label>
2201
- <div class="wf-other-input-wrapper">
2202
- ${this._otherShortcut ? b`<wf-badge shortcut="${this._otherShortcut}"></wf-badge>` : ""}
2203
- <input
2204
- type="text"
2205
- class="wf-other-input"
2206
- .value="${this._otherValue}"
2207
- placeholder="${this.otherPlaceholder}"
2208
- data-testid="wf-other-input"
2209
- @input="${this._handleOtherInput}"
2210
- @keydown="${this._handleOtherKeydown}"
2211
- @focus="${this._handleOtherFocus}"
2212
- />
2213
- </div>
2214
- </div>
2215
- ` : ""}
2216
- <span class="wf-error-message" role="alert" aria-live="polite" data-testid="wf-error">
2217
- ${this._errorMessage}
2218
- </span>
3062
+ <slot @slotchange="${this._handleSlotChange}"></slot>
3063
+ <div class="wf-error-wrapper ${this._errorMessage ? "wf-has-error" : ""}">
3064
+ <span class="wf-error-message" role="alert" aria-live="polite" data-testid="wf-error">
3065
+ ${this._errorMessage || ""}
3066
+ </span>
3067
+ </div>
2219
3068
  `;
2220
3069
  }
2221
- _handleOtherInput(e2) {
2222
- const input = e2.target;
2223
- this._otherValue = input.value;
2224
- if (this._otherValue.trim() && this._selected.size > 0) {
2225
- this._selected.clear();
2226
- this._updateOptionStates();
2227
- }
2228
- this._dispatchChange();
2229
- }
2230
- _handleOtherFocus() {
2231
- }
2232
- _handleOtherKeydown(e2) {
2233
- if (e2.key === "Escape") {
2234
- e2.stopPropagation();
2235
- const input = e2.target;
2236
- input.blur();
2237
- }
3070
+ /**
3071
+ * Handle slot content changes to rediscover options
3072
+ */
3073
+ _handleSlotChange() {
3074
+ const slottedElements = this._defaultSlot?.assignedElements({ flatten: true }) || [];
3075
+ const foundOther = slottedElements.find(
3076
+ (el) => el.tagName.toLowerCase() === "wf-other"
3077
+ );
3078
+ this._composableOther = foundOther ? foundOther : null;
3079
+ this._discoverOptions();
2238
3080
  }
2239
3081
  _discoverOptions() {
2240
- const layout = this.querySelector("wf-layout");
2241
- this._options = layout ? Array.from(layout.querySelectorAll(":scope > wf-option")) : [];
3082
+ const slottedElements = this._defaultSlot?.assignedElements({ flatten: true }) || [];
3083
+ this._options = slottedElements.filter(
3084
+ (el) => el.tagName.toLowerCase() === "wf-option"
3085
+ );
2242
3086
  this._shortcutMap.clear();
2243
3087
  this._options.forEach((option, index) => {
2244
3088
  if (index < 26) {
@@ -2248,8 +3092,9 @@ let WfOptions = class extends i {
2248
3092
  }
2249
3093
  option.setSelected(this._selected.has(option.value));
2250
3094
  });
2251
- if (this.allowOther && this._options.length < 26) {
2252
- this._otherShortcut = String.fromCharCode(65 + this._options.length);
3095
+ if (this._composableOther && this._options.length < 26) {
3096
+ const otherShortcut = String.fromCharCode(65 + this._options.length);
3097
+ this._composableOther.shortcut = otherShortcut;
2253
3098
  }
2254
3099
  }
2255
3100
  _selectValue(value) {
@@ -2258,8 +3103,11 @@ let WfOptions = class extends i {
2258
3103
  } else {
2259
3104
  this._handleSingleSelect(value);
2260
3105
  }
2261
- if (this.allowOther && this._otherValue) {
3106
+ if (this._otherValue) {
2262
3107
  this._otherValue = "";
3108
+ if (this._composableOther) {
3109
+ this._composableOther.clear();
3110
+ }
2263
3111
  }
2264
3112
  this._updateOptionStates();
2265
3113
  this._validateSelection();
@@ -2288,7 +3136,7 @@ let WfOptions = class extends i {
2288
3136
  * Silent validation check (no side effects)
2289
3137
  */
2290
3138
  _checkValidation() {
2291
- const hasOtherValue = this.allowOther && this._otherValue.trim();
3139
+ const hasOtherValue = this._hasComposableOther() && this._otherValue.trim();
2292
3140
  const hasSelection = this._selected.size > 0 || hasOtherValue;
2293
3141
  if (this.required && !hasSelection) {
2294
3142
  return false;
@@ -2312,10 +3160,10 @@ let WfOptions = class extends i {
2312
3160
  return this._checkValidation();
2313
3161
  }
2314
3162
  this._errorMessage = "";
2315
- const hasOtherValue = this.allowOther && this._otherValue.trim();
3163
+ const hasOtherValue = this._hasComposableOther() && this._otherValue.trim();
2316
3164
  const hasSelection = this._selected.size > 0 || hasOtherValue;
2317
3165
  if (this.required && !hasSelection) {
2318
- this._errorMessage = this.allowOther ? "Please select an option or specify in the text field" : "Please select an option";
3166
+ this._errorMessage = this._hasComposableOther() ? "Please select an option or specify in the text field" : "Please select an option";
2319
3167
  return false;
2320
3168
  }
2321
3169
  if (this.multi) {
@@ -2332,22 +3180,17 @@ let WfOptions = class extends i {
2332
3180
  }
2333
3181
  _dispatchChange() {
2334
3182
  const selectedArray = Array.from(this._selected);
2335
- const hasOtherText = this.allowOther && this._otherValue.trim() && this._selected.size === 0;
2336
- let currentValue;
2337
- if (this.otherName && hasOtherText) {
2338
- currentValue = this.multi ? [this.otherFieldValue] : this.otherFieldValue;
2339
- } else {
2340
- currentValue = this.value;
2341
- }
2342
3183
  const detail = {
2343
3184
  name: this.name,
2344
- value: currentValue,
3185
+ value: this.value,
2345
3186
  selected: selectedArray
2346
3187
  };
2347
- if (this.otherName) {
3188
+ if (this._hasComposableOther() && this._otherValue.trim() && this._selected.size === 0) {
3189
+ const otherName = this._composableOther?.name || `${this.name}_other`;
2348
3190
  detail.extraFields = {
2349
- [this.otherName]: hasOtherText ? this._otherValue.trim() : ""
3191
+ [otherName]: this._otherValue
2350
3192
  };
3193
+ detail.value = this._composableOther?.parentValue || "Others";
2351
3194
  }
2352
3195
  this.dispatchEvent(
2353
3196
  new CustomEvent("wf-change", {
@@ -2362,10 +3205,10 @@ let WfOptions = class extends i {
2362
3205
  // ============================================
2363
3206
  /**
2364
3207
  * Get current value (string for single, array for multi)
2365
- * If allowOther is enabled and "Others" text is filled, returns the custom text
3208
+ * If wf-other child is present and has text, returns the custom text
2366
3209
  */
2367
3210
  get value() {
2368
- if (this.allowOther && this._otherValue.trim() && this._selected.size === 0) {
3211
+ if (this._hasComposableOther() && this._otherValue.trim() && this._selected.size === 0) {
2369
3212
  return this.multi ? [this._otherValue] : this._otherValue;
2370
3213
  }
2371
3214
  const selectedArray = Array.from(this._selected);
@@ -2464,6 +3307,9 @@ let WfOptions = class extends i {
2464
3307
  this._otherValue = "";
2465
3308
  this._errorMessage = "";
2466
3309
  this._validationActivated = false;
3310
+ if (this._composableOther) {
3311
+ this._composableOther.clear();
3312
+ }
2467
3313
  this._options.forEach((option) => {
2468
3314
  if (option.hasAttribute("selected")) {
2469
3315
  this._selected.add(option.value);
@@ -2473,65 +3319,146 @@ let WfOptions = class extends i {
2473
3319
  this._dispatchChange();
2474
3320
  }
2475
3321
  };
2476
- __decorateClass$9([
3322
+ WfOptions.styles = [WfLayout.styles, wfOptionsStyles];
3323
+ __decorateClass$a([
3324
+ e("slot:not([name])")
3325
+ ], WfOptions.prototype, "_defaultSlot", 2);
3326
+ __decorateClass$a([
3327
+ n2({ type: String })
3328
+ ], WfOptions.prototype, "mode", 2);
3329
+ __decorateClass$a([
3330
+ n2({ type: String })
3331
+ ], WfOptions.prototype, "gap", 2);
3332
+ __decorateClass$a([
2477
3333
  n2({ type: String })
2478
3334
  ], WfOptions.prototype, "name", 2);
2479
- __decorateClass$9([
3335
+ __decorateClass$a([
2480
3336
  n2({ type: Boolean })
2481
3337
  ], WfOptions.prototype, "multi", 2);
2482
- __decorateClass$9([
3338
+ __decorateClass$a([
2483
3339
  n2({ type: Boolean })
2484
3340
  ], WfOptions.prototype, "required", 2);
2485
- __decorateClass$9([
3341
+ __decorateClass$a([
2486
3342
  n2({ type: Number })
2487
3343
  ], WfOptions.prototype, "min", 2);
2488
- __decorateClass$9([
3344
+ __decorateClass$a([
2489
3345
  n2({ type: Number })
2490
3346
  ], WfOptions.prototype, "max", 2);
2491
- __decorateClass$9([
2492
- n2({ type: Number, reflect: true })
3347
+ __decorateClass$a([
3348
+ n2({ type: String, reflect: true })
2493
3349
  ], WfOptions.prototype, "columns", 2);
2494
- __decorateClass$9([
2495
- n2({ type: Boolean, attribute: "allow-other" })
2496
- ], WfOptions.prototype, "allowOther", 2);
2497
- __decorateClass$9([
2498
- n2({ type: String, attribute: "other-label" })
2499
- ], WfOptions.prototype, "otherLabel", 2);
2500
- __decorateClass$9([
2501
- n2({ type: String, attribute: "other-placeholder" })
2502
- ], WfOptions.prototype, "otherPlaceholder", 2);
2503
- __decorateClass$9([
2504
- n2({ type: Boolean, attribute: "other-required" })
2505
- ], WfOptions.prototype, "otherRequired", 2);
2506
- __decorateClass$9([
2507
- n2({ type: String, attribute: "other-name" })
2508
- ], WfOptions.prototype, "otherName", 2);
2509
- __decorateClass$9([
2510
- n2({ type: String, attribute: "other-value" })
2511
- ], WfOptions.prototype, "otherFieldValue", 2);
2512
- __decorateClass$9([
3350
+ __decorateClass$a([
2513
3351
  r()
2514
3352
  ], WfOptions.prototype, "_selected", 2);
2515
- __decorateClass$9([
3353
+ __decorateClass$a([
2516
3354
  r()
2517
3355
  ], WfOptions.prototype, "_otherValue", 2);
2518
- __decorateClass$9([
3356
+ __decorateClass$a([
2519
3357
  r()
2520
3358
  ], WfOptions.prototype, "_errorMessage", 2);
2521
- __decorateClass$9([
2522
- r()
2523
- ], WfOptions.prototype, "_otherShortcut", 2);
2524
- WfOptions = __decorateClass$9([
3359
+ WfOptions = __decorateClass$a([
2525
3360
  t("wf-options")
2526
3361
  ], WfOptions);
2527
- var __defProp$8 = Object.defineProperty;
3362
+ const wfOptionStyles = i$3`
3363
+ :host {
3364
+ display: block;
3365
+ }
3366
+
3367
+ :host([hidden]) {
3368
+ display: none;
3369
+ }
3370
+
3371
+ .wf-option-card {
3372
+ display: flex;
3373
+ align-items: center;
3374
+ gap: var(--wf-spacing-3);
3375
+ width: 100%;
3376
+ min-height: var(--wf-input-min-height);
3377
+ padding: var(--wf-spacing-3);
3378
+ background: var(--wf-glass-bg);
3379
+ backdrop-filter: blur(var(--wf-glass-blur));
3380
+ -webkit-backdrop-filter: blur(var(--wf-glass-blur));
3381
+ border: 1px solid var(--wf-glass-border);
3382
+ border-radius: var(--wf-radius-md);
3383
+ box-shadow: var(--wf-glass-shadow);
3384
+ cursor: pointer;
3385
+ text-align: left;
3386
+ font-family: inherit;
3387
+ font-size: var(--wf-font-size-base);
3388
+ font-weight: var(--wf-font-weight-input);
3389
+ color: var(--wf-color-text);
3390
+ transition: border-color 150ms ease, background 150ms ease, transform 100ms ease;
3391
+ outline: none;
3392
+ box-sizing: border-box;
3393
+ }
3394
+
3395
+ .wf-option-card:hover:not(:disabled) {
3396
+ border-color: var(--wf-color-primary);
3397
+ background: var(--wf-glass-bg-hover);
3398
+ }
3399
+
3400
+ .wf-option-card:focus-visible {
3401
+ border-color: var(--wf-color-primary);
3402
+ box-shadow: 0 0 0 var(--wf-focus-ring-width) var(--wf-focus-ring-primary);
3403
+ }
3404
+
3405
+ .wf-option-card[aria-selected='true'] {
3406
+ border-color: var(--wf-color-primary);
3407
+ background-color: var(--wf-color-primary-light);
3408
+ }
3409
+
3410
+ .wf-option-card:disabled {
3411
+ opacity: 0.5;
3412
+ cursor: not-allowed;
3413
+ }
3414
+
3415
+ .wf-option-card:active:not(:disabled) {
3416
+ transform: scale(0.98);
3417
+ }
3418
+
3419
+ .wf-option-card.selecting {
3420
+ animation: wf-blink 0.3s ease;
3421
+ }
3422
+
3423
+ @keyframes wf-blink {
3424
+ 0%, 100% {
3425
+ opacity: 1;
3426
+ }
3427
+ 50% {
3428
+ opacity: 0.5;
3429
+ }
3430
+ }
3431
+
3432
+ .wf-option-content {
3433
+ flex: 1;
3434
+ min-width: 0;
3435
+ }
3436
+
3437
+ /* Slotted content styling */
3438
+ ::slotted(strong),
3439
+ ::slotted(h3),
3440
+ ::slotted(h4) {
3441
+ display: block;
3442
+ font-weight: var(--wf-font-weight-heading);
3443
+ margin: 0;
3444
+ }
3445
+
3446
+ ::slotted(span),
3447
+ ::slotted(p) {
3448
+ display: block;
3449
+ font-size: var(--wf-font-size-sm);
3450
+ color: var(--wf-color-text-muted);
3451
+ margin: var(--wf-spacing-1) 0 0 0;
3452
+ }
3453
+ `;
3454
+ var __defProp$9 = Object.defineProperty;
2528
3455
  var __getOwnPropDesc$7 = Object.getOwnPropertyDescriptor;
2529
- var __decorateClass$8 = (decorators, target, key, kind) => {
3456
+ var __decorateClass$9 = (decorators, target, key, kind) => {
2530
3457
  var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$7(target, key) : target;
2531
3458
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
2532
3459
  if (decorator = decorators[i2])
2533
3460
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
2534
- if (kind && result) __defProp$8(target, key, result);
3461
+ if (kind && result) __defProp$9(target, key, result);
2535
3462
  return result;
2536
3463
  };
2537
3464
  let WfOption = class extends i {
@@ -2542,20 +3469,6 @@ let WfOption = class extends i {
2542
3469
  this.disabled = false;
2543
3470
  this.shortcut = "";
2544
3471
  this._selecting = false;
2545
- this._cachedContent = [];
2546
- }
2547
- /**
2548
- * Disable Shadow DOM - render to Light DOM for external styling
2549
- */
2550
- createRenderRoot() {
2551
- return this;
2552
- }
2553
- connectedCallback() {
2554
- if (this._cachedContent.length === 0) {
2555
- this._cachedContent = Array.from(this.childNodes).map((node) => node.cloneNode(true));
2556
- this.textContent = "";
2557
- }
2558
- super.connectedCallback();
2559
3472
  }
2560
3473
  render() {
2561
3474
  return b`
@@ -2572,7 +3485,7 @@ let WfOption = class extends i {
2572
3485
  variant="${this.selected ? "selected" : "default"}"
2573
3486
  ></wf-badge>` : A}
2574
3487
  <div class="wf-option-content">
2575
- ${this._cachedContent}
3488
+ <slot></slot>
2576
3489
  </div>
2577
3490
  </button>
2578
3491
  `;
@@ -2614,7 +3527,7 @@ let WfOption = class extends i {
2614
3527
  * Focus the option button
2615
3528
  */
2616
3529
  focus() {
2617
- const button = this.querySelector("button");
3530
+ const button = this.shadowRoot?.querySelector("button");
2618
3531
  button?.focus();
2619
3532
  }
2620
3533
  /**
@@ -2624,35 +3537,205 @@ let WfOption = class extends i {
2624
3537
  this.selected = selected;
2625
3538
  }
2626
3539
  };
2627
- __decorateClass$8([
3540
+ WfOption.styles = wfOptionStyles;
3541
+ __decorateClass$9([
2628
3542
  n2({ type: String })
2629
3543
  ], WfOption.prototype, "value", 2);
2630
- __decorateClass$8([
3544
+ __decorateClass$9([
2631
3545
  n2({ type: Boolean, reflect: true })
2632
3546
  ], WfOption.prototype, "selected", 2);
2633
- __decorateClass$8([
3547
+ __decorateClass$9([
2634
3548
  n2({ type: Boolean, reflect: true })
2635
3549
  ], WfOption.prototype, "disabled", 2);
2636
- __decorateClass$8([
3550
+ __decorateClass$9([
2637
3551
  n2({ type: String })
2638
3552
  ], WfOption.prototype, "shortcut", 2);
2639
- __decorateClass$8([
3553
+ __decorateClass$9([
2640
3554
  r()
2641
3555
  ], WfOption.prototype, "_selecting", 2);
2642
- WfOption = __decorateClass$8([
3556
+ WfOption = __decorateClass$9([
2643
3557
  t("wf-option")
2644
3558
  ], WfOption);
2645
- var __defProp$7 = Object.defineProperty;
2646
- var __decorateClass$7 = (decorators, target, key, kind) => {
3559
+ const formInputBaseStyles = i$3`
3560
+ :host {
3561
+ display: block;
3562
+ }
3563
+
3564
+ :host([hidden]) {
3565
+ display: none;
3566
+ }
3567
+
3568
+ .wf-field-container {
3569
+ display: flex;
3570
+ flex-direction: column;
3571
+ }
3572
+
3573
+ .wf-label {
3574
+ font-size: var(--wf-font-size-sm);
3575
+ font-weight: var(--wf-font-weight-label);
3576
+ color: var(--wf-color-text);
3577
+ margin-bottom: var(--wf-spacing-2);
3578
+ }
3579
+
3580
+ .wf-label-required::after {
3581
+ content: ' *';
3582
+ color: var(--wf-color-error);
3583
+ }
3584
+
3585
+ /* Error wrapper for animated expand/collapse */
3586
+ .wf-error-wrapper {
3587
+ display: grid;
3588
+ grid-template-rows: 0fr;
3589
+ transition: grid-template-rows 200ms ease-out;
3590
+ }
3591
+
3592
+ .wf-error-wrapper.wf-has-error {
3593
+ grid-template-rows: 1fr;
3594
+ }
3595
+
3596
+ .wf-error-message {
3597
+ overflow: hidden;
3598
+ min-height: 0;
3599
+ font-size: var(--wf-font-size-sm);
3600
+ color: var(--wf-color-error);
3601
+ opacity: 0;
3602
+ transform: translateY(-4px);
3603
+ transition: opacity 200ms ease-out, transform 200ms ease-out;
3604
+ }
3605
+
3606
+ .wf-has-error .wf-error-message {
3607
+ margin-top: var(--wf-spacing-2);
3608
+ opacity: 1;
3609
+ transform: translateY(0);
3610
+ }
3611
+
3612
+ .wf-hint {
3613
+ font-size: var(--wf-font-size-sm);
3614
+ color: var(--wf-color-text-muted);
3615
+ margin-top: var(--wf-spacing-2);
3616
+ }
3617
+
3618
+ .wf-input {
3619
+ width: 100%;
3620
+ min-height: var(--wf-input-min-height);
3621
+ padding: var(--wf-spacing-4);
3622
+ font-size: var(--wf-font-size-base);
3623
+ font-weight: var(--wf-font-weight-input);
3624
+ font-family: inherit;
3625
+ background: var(--wf-glass-bg);
3626
+ backdrop-filter: blur(var(--wf-glass-blur));
3627
+ -webkit-backdrop-filter: blur(var(--wf-glass-blur));
3628
+ border: 1px solid var(--wf-glass-border);
3629
+ border-radius: var(--wf-radius-md);
3630
+ box-shadow: var(--wf-glass-shadow);
3631
+ color: var(--wf-color-text);
3632
+ transition: border-color 150ms ease, box-shadow 150ms ease, background 150ms ease;
3633
+ outline: none;
3634
+ box-sizing: border-box;
3635
+ }
3636
+
3637
+ .wf-input::placeholder {
3638
+ color: var(--wf-color-text-muted);
3639
+ font-weight: var(--wf-font-weight-input);
3640
+ }
3641
+
3642
+ .wf-input:focus {
3643
+ border-color: var(--wf-color-primary);
3644
+ box-shadow: 0 0 0 var(--wf-focus-ring-width) var(--wf-focus-ring-primary);
3645
+ }
3646
+
3647
+ .wf-input:disabled {
3648
+ opacity: 0.5;
3649
+ cursor: not-allowed;
3650
+ }
3651
+
3652
+ .wf-input.wf-input-error {
3653
+ border-color: var(--wf-color-error);
3654
+ }
3655
+
3656
+ .wf-input.wf-input-error:focus {
3657
+ box-shadow: 0 0 0 var(--wf-focus-ring-width) var(--wf-focus-ring-error);
3658
+ }
3659
+
3660
+ /* Textarea-specific styles */
3661
+ .wf-textarea {
3662
+ width: 100%;
3663
+ padding: var(--wf-spacing-4);
3664
+ font-size: var(--wf-font-size-base);
3665
+ font-family: inherit;
3666
+ background: var(--wf-glass-bg);
3667
+ backdrop-filter: blur(var(--wf-glass-blur));
3668
+ -webkit-backdrop-filter: blur(var(--wf-glass-blur));
3669
+ border: 1px solid var(--wf-glass-border);
3670
+ border-radius: var(--wf-radius-lg);
3671
+ box-shadow: var(--wf-glass-shadow);
3672
+ color: var(--wf-color-text);
3673
+ transition: border-color 150ms ease, box-shadow 150ms ease, background 150ms ease;
3674
+ outline: none;
3675
+ box-sizing: border-box;
3676
+ resize: vertical;
3677
+ min-height: var(--wf-textarea-min-height);
3678
+ }
3679
+
3680
+ .wf-textarea::placeholder {
3681
+ color: var(--wf-color-text-muted);
3682
+ }
3683
+
3684
+ .wf-textarea:focus {
3685
+ border-color: var(--wf-color-primary);
3686
+ box-shadow: 0 0 0 var(--wf-focus-ring-width) var(--wf-focus-ring-primary);
3687
+ }
3688
+
3689
+ .wf-textarea:disabled {
3690
+ opacity: 0.5;
3691
+ cursor: not-allowed;
3692
+ }
3693
+
3694
+ .wf-textarea.wf-textarea-error {
3695
+ border-color: var(--wf-color-error);
3696
+ }
3697
+
3698
+ .wf-textarea.wf-textarea-error:focus {
3699
+ box-shadow: 0 0 0 var(--wf-focus-ring-width) var(--wf-focus-ring-error);
3700
+ }
3701
+
3702
+ .wf-char-count {
3703
+ font-size: var(--wf-font-size-sm);
3704
+ color: var(--wf-color-text-muted);
3705
+ text-align: right;
3706
+ }
3707
+
3708
+ .wf-char-count.wf-char-limit {
3709
+ color: var(--wf-color-error);
3710
+ }
3711
+
3712
+ /* wf-field slotted input styles */
3713
+ .wf-input-wrapper {
3714
+ position: relative;
3715
+ }
3716
+
3717
+ /* Number input - hide spinners */
3718
+ .wf-input::-webkit-outer-spin-button,
3719
+ .wf-input::-webkit-inner-spin-button {
3720
+ -webkit-appearance: none;
3721
+ margin: 0;
3722
+ }
3723
+
3724
+ .wf-input[type='number'] {
3725
+ -moz-appearance: textfield;
3726
+ }
3727
+ `;
3728
+ var __defProp$8 = Object.defineProperty;
3729
+ var __decorateClass$8 = (decorators, target, key, kind) => {
2647
3730
  var result = void 0;
2648
3731
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
2649
3732
  if (decorator = decorators[i2])
2650
3733
  result = decorator(target, key, result) || result;
2651
- if (result) __defProp$7(target, key, result);
3734
+ if (result) __defProp$8(target, key, result);
2652
3735
  return result;
2653
3736
  };
2654
3737
  const DEFAULT_DEBOUNCE_MS = 600;
2655
- class FormInputBase extends i {
3738
+ const _FormInputBase = class _FormInputBase extends i {
2656
3739
  constructor() {
2657
3740
  super(...arguments);
2658
3741
  this.name = "";
@@ -2705,12 +3788,6 @@ class FormInputBase extends i {
2705
3788
  );
2706
3789
  };
2707
3790
  }
2708
- /**
2709
- * Disable Shadow DOM - render to Light DOM for external styling
2710
- */
2711
- createRenderRoot() {
2712
- return this;
2713
- }
2714
3791
  // ============================================
2715
3792
  // Lifecycle Methods
2716
3793
  // ============================================
@@ -2743,6 +3820,41 @@ class FormInputBase extends i {
2743
3820
  return "input";
2744
3821
  }
2745
3822
  // ============================================
3823
+ // Shared Render Helpers
3824
+ // ============================================
3825
+ /**
3826
+ * Render the label element
3827
+ */
3828
+ _renderLabel() {
3829
+ if (!this.label) {
3830
+ return A;
3831
+ }
3832
+ return b`<label
3833
+ class="wf-label ${this.required ? "wf-label-required" : ""}"
3834
+ for="${this.name}"
3835
+ data-testid="wf-label"
3836
+ >${this.label}</label>`;
3837
+ }
3838
+ /**
3839
+ * Render the hint text (only shown when no error)
3840
+ */
3841
+ _renderHint() {
3842
+ if (!this.hint || this._errorMessage) {
3843
+ return A;
3844
+ }
3845
+ return b`<span class="wf-hint">${this.hint}</span>`;
3846
+ }
3847
+ /**
3848
+ * Render the error message container with animation support
3849
+ */
3850
+ _renderError() {
3851
+ return b`<div class="wf-error-wrapper ${this._errorMessage ? "wf-has-error" : ""}">
3852
+ <span class="wf-error-message" role="alert" aria-live="polite" data-testid="wf-error">
3853
+ ${this._errorMessage || ""}
3854
+ </span>
3855
+ </div>`;
3856
+ }
3857
+ // ============================================
2746
3858
  // Public API
2747
3859
  // ============================================
2748
3860
  /**
@@ -2819,7 +3931,7 @@ class FormInputBase extends i {
2819
3931
  * Focus the input element
2820
3932
  */
2821
3933
  focus() {
2822
- const element = this.querySelector(this._getFocusableSelector());
3934
+ const element = this.shadowRoot?.querySelector(this._getFocusableSelector());
2823
3935
  element?.focus();
2824
3936
  }
2825
3937
  /**
@@ -2834,23 +3946,25 @@ class FormInputBase extends i {
2834
3946
  this._debounceTimer = null;
2835
3947
  }
2836
3948
  }
2837
- }
2838
- __decorateClass$7([
3949
+ };
3950
+ _FormInputBase.styles = formInputBaseStyles;
3951
+ let FormInputBase = _FormInputBase;
3952
+ __decorateClass$8([
2839
3953
  n2({ type: String })
2840
3954
  ], FormInputBase.prototype, "name");
2841
- __decorateClass$7([
3955
+ __decorateClass$8([
2842
3956
  n2({ type: String })
2843
3957
  ], FormInputBase.prototype, "label");
2844
- __decorateClass$7([
3958
+ __decorateClass$8([
2845
3959
  n2({ type: Boolean })
2846
3960
  ], FormInputBase.prototype, "required");
2847
- __decorateClass$7([
3961
+ __decorateClass$8([
2848
3962
  n2({ type: String })
2849
3963
  ], FormInputBase.prototype, "hint");
2850
- __decorateClass$7([
3964
+ __decorateClass$8([
2851
3965
  r()
2852
3966
  ], FormInputBase.prototype, "_errorMessage");
2853
- __decorateClass$7([
3967
+ __decorateClass$8([
2854
3968
  r()
2855
3969
  ], FormInputBase.prototype, "_value");
2856
3970
  const DEFAULT_BLOCKED_DOMAINS = [
@@ -3088,182 +4202,14 @@ class ValidationController {
3088
4202
  };
3089
4203
  }
3090
4204
  }
3091
- var __defProp$6 = Object.defineProperty;
4205
+ var __defProp$7 = Object.defineProperty;
3092
4206
  var __getOwnPropDesc$6 = Object.getOwnPropertyDescriptor;
3093
- var __decorateClass$6 = (decorators, target, key, kind) => {
4207
+ var __decorateClass$7 = (decorators, target, key, kind) => {
3094
4208
  var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$6(target, key) : target;
3095
4209
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
3096
4210
  if (decorator = decorators[i2])
3097
4211
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
3098
- if (kind && result) __defProp$6(target, key, result);
3099
- return result;
3100
- };
3101
- let WfField = class extends FormInputBase {
3102
- constructor() {
3103
- super(...arguments);
3104
- this._inputElement = null;
3105
- }
3106
- // ============================================
3107
- // Lifecycle Overrides
3108
- // ============================================
3109
- connectedCallback() {
3110
- super.connectedCallback();
3111
- this.addEventListener("input", this._handleInput);
3112
- this.addEventListener("blur", this._handleBlur, true);
3113
- this.addEventListener("focus", this._handleFocus, true);
3114
- }
3115
- disconnectedCallback() {
3116
- super.disconnectedCallback();
3117
- this.removeEventListener("input", this._handleInput);
3118
- this.removeEventListener("blur", this._handleBlur, true);
3119
- this.removeEventListener("focus", this._handleFocus, true);
3120
- }
3121
- firstUpdated() {
3122
- this._discoverInput();
3123
- this._setupValidators();
3124
- }
3125
- // ============================================
3126
- // Abstract Method Implementations
3127
- // ============================================
3128
- _getValidationTriggerProperties() {
3129
- return ["required"];
3130
- }
3131
- /**
3132
- * Field uses faster debounce (300ms) for responsive validation
3133
- */
3134
- _getDebounceMs() {
3135
- return 300;
3136
- }
3137
- _setupValidators() {
3138
- if (!this._inputElement) {
3139
- return;
3140
- }
3141
- this._validators = [];
3142
- if (this.required || this._inputElement.hasAttribute("required")) {
3143
- this._validators.push(ValidationController.required());
3144
- }
3145
- if (this._inputElement.getAttribute("type") === "email") {
3146
- this._validators.push(ValidationController.email());
3147
- }
3148
- if (this._inputElement.hasAttribute("data-work-email")) {
3149
- const blockedDomainsAttr = this._inputElement.getAttribute("data-blocked-domains");
3150
- const blockedDomains = blockedDomainsAttr ? blockedDomainsAttr.split(",").map((d2) => d2.trim()) : void 0;
3151
- this._validators.push(ValidationController.workEmail(blockedDomains));
3152
- }
3153
- const pattern = this._inputElement.getAttribute("pattern");
3154
- if (pattern) {
3155
- const message = this._inputElement.getAttribute("data-pattern-message") || "Invalid format";
3156
- this._validators.push(ValidationController.pattern(new RegExp(pattern), message));
3157
- }
3158
- const minLength = this._inputElement.getAttribute("minlength");
3159
- if (minLength) {
3160
- this._validators.push(ValidationController.minLength(parseInt(minLength, 10)));
3161
- }
3162
- const maxLength = this._inputElement.getAttribute("maxlength");
3163
- if (maxLength) {
3164
- this._validators.push(ValidationController.maxLength(parseInt(maxLength, 10)));
3165
- }
3166
- }
3167
- // ============================================
3168
- // Slot Handling
3169
- // ============================================
3170
- _handleSlotChange() {
3171
- this._discoverInput();
3172
- this._setupValidators();
3173
- }
3174
- _discoverInput() {
3175
- const slot = this.shadowRoot?.querySelector("slot");
3176
- if (!slot) {
3177
- return;
3178
- }
3179
- const elements = slot.assignedElements({ flatten: true });
3180
- for (const el of elements) {
3181
- if (el instanceof HTMLInputElement || el instanceof HTMLTextAreaElement || el instanceof HTMLSelectElement) {
3182
- this._inputElement = el;
3183
- if (!el.id) {
3184
- el.id = this.name;
3185
- }
3186
- if (!el.name) {
3187
- el.name = this.name;
3188
- }
3189
- this._value = el.value;
3190
- break;
3191
- }
3192
- }
3193
- }
3194
- // ============================================
3195
- // Value Override (for slotted elements)
3196
- // ============================================
3197
- /**
3198
- * Get current value from slotted element or internal state
3199
- */
3200
- get value() {
3201
- return this._inputElement?.value ?? this._value;
3202
- }
3203
- /**
3204
- * Set value on both internal state and slotted element
3205
- */
3206
- set value(val) {
3207
- this._value = val;
3208
- if (this._inputElement) {
3209
- this._inputElement.value = String(val ?? "");
3210
- }
3211
- }
3212
- // ============================================
3213
- // Focus and Reset Overrides
3214
- // ============================================
3215
- /**
3216
- * Focus the slotted input element
3217
- */
3218
- focus() {
3219
- this._inputElement?.focus();
3220
- }
3221
- /**
3222
- * Reset field to initial state including slotted element
3223
- */
3224
- reset() {
3225
- super.reset();
3226
- if (this._inputElement) {
3227
- this._inputElement.value = "";
3228
- }
3229
- }
3230
- // ============================================
3231
- // Render
3232
- // ============================================
3233
- render() {
3234
- return b`
3235
- <div class="wf-field-container">
3236
- ${this.label ? b`<label
3237
- class="wf-label ${this.required ? "wf-label-required" : ""}"
3238
- for="${this.name}"
3239
- >
3240
- ${this.label}
3241
- </label>` : ""}
3242
- <div class="wf-input-wrapper">
3243
- <slot @slotchange="${this._handleSlotChange}"></slot>
3244
- </div>
3245
- ${this.hint && !this._errorMessage ? b`<span class="wf-hint">${this.hint}</span>` : ""}
3246
- <span class="wf-error-message" role="alert" aria-live="polite">
3247
- ${this._errorMessage}
3248
- </span>
3249
- </div>
3250
- `;
3251
- }
3252
- };
3253
- __decorateClass$6([
3254
- r()
3255
- ], WfField.prototype, "_inputElement", 2);
3256
- WfField = __decorateClass$6([
3257
- t("wf-field")
3258
- ], WfField);
3259
- var __defProp$5 = Object.defineProperty;
3260
- var __getOwnPropDesc$5 = Object.getOwnPropertyDescriptor;
3261
- var __decorateClass$5 = (decorators, target, key, kind) => {
3262
- var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$5(target, key) : target;
3263
- for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
3264
- if (decorator = decorators[i2])
3265
- result = (kind ? decorator(target, key, result) : decorator(result)) || result;
3266
- if (kind && result) __defProp$5(target, key, result);
4212
+ if (kind && result) __defProp$7(target, key, result);
3267
4213
  return result;
3268
4214
  };
3269
4215
  let WfEmail = class extends FormInputBase {
@@ -3309,13 +4255,7 @@ let WfEmail = class extends FormInputBase {
3309
4255
  render() {
3310
4256
  return b`
3311
4257
  <div class="wf-field-container">
3312
- ${this.label ? b`<label
3313
- class="wf-label ${this.required ? "wf-label-required" : ""}"
3314
- for="${this.name}"
3315
- data-testid="wf-label"
3316
- >
3317
- ${this.label}
3318
- </label>` : ""}
4258
+ ${this._renderLabel()}
3319
4259
  <input
3320
4260
  type="email"
3321
4261
  class="wf-input ${this._errorMessage ? "wf-input-error" : ""}"
@@ -3330,40 +4270,38 @@ let WfEmail = class extends FormInputBase {
3330
4270
  @blur="${this._handleBlur}"
3331
4271
  @focus="${this._handleFocus}"
3332
4272
  />
3333
- ${this.hint && !this._errorMessage ? b`<span class="wf-hint">${this.hint}</span>` : ""}
3334
- <span class="wf-error-message" role="alert" aria-live="polite" data-testid="wf-error">
3335
- ${this._errorMessage}
3336
- </span>
4273
+ ${this._renderHint()}
4274
+ ${this._renderError()}
3337
4275
  </div>
3338
4276
  `;
3339
4277
  }
3340
4278
  };
3341
- __decorateClass$5([
4279
+ __decorateClass$7([
3342
4280
  n2({ type: String })
3343
4281
  ], WfEmail.prototype, "placeholder", 2);
3344
- __decorateClass$5([
4282
+ __decorateClass$7([
3345
4283
  n2({ type: Boolean, attribute: "work-email" })
3346
4284
  ], WfEmail.prototype, "workEmail", 2);
3347
- __decorateClass$5([
4285
+ __decorateClass$7([
3348
4286
  n2({ type: String, attribute: "blocked-domains" })
3349
4287
  ], WfEmail.prototype, "blockedDomains", 2);
3350
- __decorateClass$5([
4288
+ __decorateClass$7([
3351
4289
  n2({ type: String, attribute: "work-email-message" })
3352
4290
  ], WfEmail.prototype, "workEmailMessage", 2);
3353
- __decorateClass$5([
4291
+ __decorateClass$7([
3354
4292
  n2({ type: Boolean })
3355
4293
  ], WfEmail.prototype, "disabled", 2);
3356
- WfEmail = __decorateClass$5([
4294
+ WfEmail = __decorateClass$7([
3357
4295
  t("wf-email")
3358
4296
  ], WfEmail);
3359
- var __defProp$4 = Object.defineProperty;
3360
- var __getOwnPropDesc$4 = Object.getOwnPropertyDescriptor;
3361
- var __decorateClass$4 = (decorators, target, key, kind) => {
3362
- var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$4(target, key) : target;
4297
+ var __defProp$6 = Object.defineProperty;
4298
+ var __getOwnPropDesc$5 = Object.getOwnPropertyDescriptor;
4299
+ var __decorateClass$6 = (decorators, target, key, kind) => {
4300
+ var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$5(target, key) : target;
3363
4301
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
3364
4302
  if (decorator = decorators[i2])
3365
4303
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
3366
- if (kind && result) __defProp$4(target, key, result);
4304
+ if (kind && result) __defProp$6(target, key, result);
3367
4305
  return result;
3368
4306
  };
3369
4307
  let WfInput = class extends FormInputBase {
@@ -3404,13 +4342,7 @@ let WfInput = class extends FormInputBase {
3404
4342
  render() {
3405
4343
  return b`
3406
4344
  <div class="wf-field-container">
3407
- ${this.label ? b`<label
3408
- class="wf-label ${this.required ? "wf-label-required" : ""}"
3409
- for="${this.name}"
3410
- data-testid="wf-label"
3411
- >
3412
- ${this.label}
3413
- </label>` : ""}
4345
+ ${this._renderLabel()}
3414
4346
  <input
3415
4347
  type="${this.type}"
3416
4348
  class="wf-input ${this._errorMessage ? "wf-input-error" : ""}"
@@ -3426,49 +4358,47 @@ let WfInput = class extends FormInputBase {
3426
4358
  @blur="${this._handleBlur}"
3427
4359
  @focus="${this._handleFocus}"
3428
4360
  />
3429
- ${this.hint && !this._errorMessage ? b`<span class="wf-hint">${this.hint}</span>` : ""}
3430
- <span class="wf-error-message" role="alert" aria-live="polite" data-testid="wf-error">
3431
- ${this._errorMessage}
3432
- </span>
4361
+ ${this._renderHint()}
4362
+ ${this._renderError()}
3433
4363
  </div>
3434
4364
  `;
3435
4365
  }
3436
4366
  };
3437
- __decorateClass$4([
4367
+ __decorateClass$6([
3438
4368
  n2({ type: String })
3439
4369
  ], WfInput.prototype, "placeholder", 2);
3440
- __decorateClass$4([
4370
+ __decorateClass$6([
3441
4371
  n2({ type: String })
3442
4372
  ], WfInput.prototype, "type", 2);
3443
- __decorateClass$4([
4373
+ __decorateClass$6([
3444
4374
  n2({ type: Number })
3445
4375
  ], WfInput.prototype, "minlength", 2);
3446
- __decorateClass$4([
4376
+ __decorateClass$6([
3447
4377
  n2({ type: Number })
3448
4378
  ], WfInput.prototype, "maxlength", 2);
3449
- __decorateClass$4([
4379
+ __decorateClass$6([
3450
4380
  n2({ type: String })
3451
4381
  ], WfInput.prototype, "pattern", 2);
3452
- __decorateClass$4([
4382
+ __decorateClass$6([
3453
4383
  n2({ type: String, attribute: "pattern-message" })
3454
4384
  ], WfInput.prototype, "patternMessage", 2);
3455
- __decorateClass$4([
4385
+ __decorateClass$6([
3456
4386
  n2({ type: Boolean })
3457
4387
  ], WfInput.prototype, "disabled", 2);
3458
- __decorateClass$4([
4388
+ __decorateClass$6([
3459
4389
  n2({ type: String })
3460
4390
  ], WfInput.prototype, "autocomplete", 2);
3461
- WfInput = __decorateClass$4([
4391
+ WfInput = __decorateClass$6([
3462
4392
  t("wf-input")
3463
4393
  ], WfInput);
3464
- var __defProp$3 = Object.defineProperty;
3465
- var __getOwnPropDesc$3 = Object.getOwnPropertyDescriptor;
3466
- var __decorateClass$3 = (decorators, target, key, kind) => {
3467
- var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$3(target, key) : target;
4394
+ var __defProp$5 = Object.defineProperty;
4395
+ var __getOwnPropDesc$4 = Object.getOwnPropertyDescriptor;
4396
+ var __decorateClass$5 = (decorators, target, key, kind) => {
4397
+ var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$4(target, key) : target;
3468
4398
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
3469
4399
  if (decorator = decorators[i2])
3470
4400
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
3471
- if (kind && result) __defProp$3(target, key, result);
4401
+ if (kind && result) __defProp$5(target, key, result);
3472
4402
  return result;
3473
4403
  };
3474
4404
  let WfNumber = class extends WfInput {
@@ -3509,13 +4439,7 @@ let WfNumber = class extends WfInput {
3509
4439
  render() {
3510
4440
  return b`
3511
4441
  <div class="wf-field-container">
3512
- ${this.label ? b`<label
3513
- class="wf-label ${this.required ? "wf-label-required" : ""}"
3514
- for="${this.name}"
3515
- data-testid="wf-label"
3516
- >
3517
- ${this.label}
3518
- </label>` : ""}
4442
+ ${this._renderLabel()}
3519
4443
  <input
3520
4444
  type="number"
3521
4445
  class="wf-input ${this._errorMessage ? "wf-input-error" : ""}"
@@ -3534,10 +4458,8 @@ let WfNumber = class extends WfInput {
3534
4458
  @blur="${this._handleBlur}"
3535
4459
  @focus="${this._handleFocus}"
3536
4460
  />
3537
- ${this.hint && !this._errorMessage ? b`<span class="wf-hint">${this.hint}</span>` : ""}
3538
- <span class="wf-error-message" role="alert" aria-live="polite" data-testid="wf-error">
3539
- ${this._errorMessage}
3540
- </span>
4461
+ ${this._renderHint()}
4462
+ ${this._renderError()}
3541
4463
  </div>
3542
4464
  `;
3543
4465
  }
@@ -3554,26 +4476,26 @@ let WfNumber = class extends WfInput {
3554
4476
  this._value = String(val);
3555
4477
  }
3556
4478
  };
3557
- __decorateClass$3([
4479
+ __decorateClass$5([
3558
4480
  n2({ type: Number })
3559
4481
  ], WfNumber.prototype, "min", 2);
3560
- __decorateClass$3([
4482
+ __decorateClass$5([
3561
4483
  n2({ type: Number })
3562
4484
  ], WfNumber.prototype, "max", 2);
3563
- __decorateClass$3([
4485
+ __decorateClass$5([
3564
4486
  n2({ type: Number })
3565
4487
  ], WfNumber.prototype, "step", 2);
3566
- WfNumber = __decorateClass$3([
4488
+ WfNumber = __decorateClass$5([
3567
4489
  t("wf-number")
3568
4490
  ], WfNumber);
3569
- var __defProp$2 = Object.defineProperty;
3570
- var __getOwnPropDesc$2 = Object.getOwnPropertyDescriptor;
3571
- var __decorateClass$2 = (decorators, target, key, kind) => {
3572
- var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$2(target, key) : target;
4491
+ var __defProp$4 = Object.defineProperty;
4492
+ var __getOwnPropDesc$3 = Object.getOwnPropertyDescriptor;
4493
+ var __decorateClass$4 = (decorators, target, key, kind) => {
4494
+ var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$3(target, key) : target;
3573
4495
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
3574
4496
  if (decorator = decorators[i2])
3575
4497
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
3576
- if (kind && result) __defProp$2(target, key, result);
4498
+ if (kind && result) __defProp$4(target, key, result);
3577
4499
  return result;
3578
4500
  };
3579
4501
  let WfTextarea = class extends FormInputBase {
@@ -3618,13 +4540,7 @@ let WfTextarea = class extends FormInputBase {
3618
4540
  const isAtLimit = this.maxlength !== void 0 && charCount >= this.maxlength;
3619
4541
  return b`
3620
4542
  <div class="wf-field-container">
3621
- ${this.label ? b`<label
3622
- class="wf-label ${this.required ? "wf-label-required" : ""}"
3623
- for="${this.name}"
3624
- data-testid="wf-label"
3625
- >
3626
- ${this.label}
3627
- </label>` : ""}
4543
+ ${this._renderLabel()}
3628
4544
  <textarea
3629
4545
  class="wf-textarea ${this._errorMessage ? "wf-textarea-error" : ""}"
3630
4546
  id="${this.name}"
@@ -3644,33 +4560,31 @@ let WfTextarea = class extends FormInputBase {
3644
4560
  ${this.showCount && this.maxlength ? b`<span class="wf-char-count ${isAtLimit ? "wf-char-limit" : ""}" data-testid="wf-counter">
3645
4561
  ${charCount}/${this.maxlength}
3646
4562
  </span>` : ""}
3647
- ${this.hint && !this._errorMessage ? b`<span class="wf-hint">${this.hint}</span>` : ""}
3648
- <span class="wf-error-message" role="alert" aria-live="polite" data-testid="wf-error">
3649
- ${this._errorMessage}
3650
- </span>
4563
+ ${this._renderHint()}
4564
+ ${this._renderError()}
3651
4565
  </div>
3652
4566
  `;
3653
4567
  }
3654
4568
  };
3655
- __decorateClass$2([
4569
+ __decorateClass$4([
3656
4570
  n2({ type: String })
3657
4571
  ], WfTextarea.prototype, "placeholder", 2);
3658
- __decorateClass$2([
4572
+ __decorateClass$4([
3659
4573
  n2({ type: Number })
3660
4574
  ], WfTextarea.prototype, "rows", 2);
3661
- __decorateClass$2([
4575
+ __decorateClass$4([
3662
4576
  n2({ type: Number })
3663
4577
  ], WfTextarea.prototype, "minlength", 2);
3664
- __decorateClass$2([
4578
+ __decorateClass$4([
3665
4579
  n2({ type: Number })
3666
4580
  ], WfTextarea.prototype, "maxlength", 2);
3667
- __decorateClass$2([
4581
+ __decorateClass$4([
3668
4582
  n2({ type: Boolean })
3669
4583
  ], WfTextarea.prototype, "disabled", 2);
3670
- __decorateClass$2([
4584
+ __decorateClass$4([
3671
4585
  n2({ type: Boolean, attribute: "show-count" })
3672
4586
  ], WfTextarea.prototype, "showCount", 2);
3673
- WfTextarea = __decorateClass$2([
4587
+ WfTextarea = __decorateClass$4([
3674
4588
  t("wf-textarea")
3675
4589
  ], WfTextarea);
3676
4590
  function init(config) {
@@ -3875,14 +4789,44 @@ function init(config) {
3875
4789
  return instance;
3876
4790
  }
3877
4791
  const init_default = { init };
3878
- var __defProp$1 = Object.defineProperty;
3879
- var __getOwnPropDesc$1 = Object.getOwnPropertyDescriptor;
3880
- var __decorateClass$1 = (decorators, target, key, kind) => {
3881
- var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$1(target, key) : target;
4792
+ const wfProgressStyles = [
4793
+ hostTokens,
4794
+ i$3`
4795
+ :host {
4796
+ display: block;
4797
+ }
4798
+
4799
+ :host([hidden]) {
4800
+ display: none;
4801
+ }
4802
+
4803
+ .wf-progress {
4804
+ display: flex;
4805
+ gap: var(--wf-spacing-2);
4806
+ }
4807
+
4808
+ .wf-progress-segment {
4809
+ width: 100%;
4810
+ height: var(--wf-progress-height);
4811
+ background-color: var(--wf-color-progress-inactive);
4812
+ border-radius: var(--wf-radius-full);
4813
+ transition: background-color 300ms ease;
4814
+ }
4815
+
4816
+ .wf-progress-segment.completed,
4817
+ .wf-progress-segment.active {
4818
+ background-color: var(--wf-color-progress-active);
4819
+ }
4820
+ `
4821
+ ];
4822
+ var __defProp$3 = Object.defineProperty;
4823
+ var __getOwnPropDesc$2 = Object.getOwnPropertyDescriptor;
4824
+ var __decorateClass$3 = (decorators, target, key, kind) => {
4825
+ var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$2(target, key) : target;
3882
4826
  for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
3883
4827
  if (decorator = decorators[i2])
3884
4828
  result = (kind ? decorator(target, key, result) : decorator(result)) || result;
3885
- if (kind && result) __defProp$1(target, key, result);
4829
+ if (kind && result) __defProp$3(target, key, result);
3886
4830
  return result;
3887
4831
  };
3888
4832
  let WfProgress = class extends i {
@@ -3897,12 +4841,6 @@ let WfProgress = class extends i {
3897
4841
  this._boundHandleSuccess = this._handleSuccess.bind(this);
3898
4842
  this._boundHandleStepsDiscovered = this._handleStepsDiscovered.bind(this);
3899
4843
  }
3900
- /**
3901
- * Disable Shadow DOM - render to Light DOM for external styling
3902
- */
3903
- createRenderRoot() {
3904
- return this;
3905
- }
3906
4844
  connectedCallback() {
3907
4845
  super.connectedCallback();
3908
4846
  document.addEventListener("wf:steps-discovered", this._boundHandleStepsDiscovered);
@@ -3976,6 +4914,10 @@ let WfProgress = class extends i {
3976
4914
  segments.push(b`
3977
4915
  <div
3978
4916
  class="wf-progress-segment ${completed ? "completed" : ""} ${active ? "active" : ""}"
4917
+ data-testid="wf-progress-segment"
4918
+ data-step="${i2}"
4919
+ data-completed="${completed}"
4920
+ data-active="${active}"
3979
4921
  role="progressbar"
3980
4922
  aria-valuenow="${this._currentStep}"
3981
4923
  aria-valuemin="1"
@@ -3983,24 +4925,266 @@ let WfProgress = class extends i {
3983
4925
  ></div>
3984
4926
  `);
3985
4927
  }
3986
- return b`<div class="wf-progress" role="group" aria-label="Form progress">${segments}</div>`;
4928
+ return b`<div class="wf-progress" data-testid="wf-progress-bar" role="group" aria-label="Form progress">${segments}</div>`;
3987
4929
  }
3988
4930
  };
3989
- __decorateClass$1([
4931
+ WfProgress.styles = wfProgressStyles;
4932
+ __decorateClass$3([
3990
4933
  n2({ type: String })
3991
4934
  ], WfProgress.prototype, "for", 2);
3992
- __decorateClass$1([
4935
+ __decorateClass$3([
3993
4936
  r()
3994
4937
  ], WfProgress.prototype, "_currentStep", 2);
3995
- __decorateClass$1([
4938
+ __decorateClass$3([
3996
4939
  r()
3997
4940
  ], WfProgress.prototype, "_totalSteps", 2);
3998
- __decorateClass$1([
4941
+ __decorateClass$3([
3999
4942
  r()
4000
4943
  ], WfProgress.prototype, "_isComplete", 2);
4001
- WfProgress = __decorateClass$1([
4944
+ WfProgress = __decorateClass$3([
4002
4945
  t("wf-progress")
4003
4946
  ], WfProgress);
4947
+ var __defProp$2 = Object.defineProperty;
4948
+ var __decorateClass$2 = (decorators, target, key, kind) => {
4949
+ var result = void 0;
4950
+ for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
4951
+ if (decorator = decorators[i2])
4952
+ result = decorator(target, key, result) || result;
4953
+ if (result) __defProp$2(target, key, result);
4954
+ return result;
4955
+ };
4956
+ class NavigationButtonBase extends i {
4957
+ constructor() {
4958
+ super(...arguments);
4959
+ this._isFirstStep = true;
4960
+ this._isLastStep = false;
4961
+ this._isSubmitting = false;
4962
+ this._handleNavState = (e2) => {
4963
+ this._isFirstStep = e2.detail.isFirstStep;
4964
+ this._isLastStep = e2.detail.isLastStep;
4965
+ this._isSubmitting = e2.detail.isSubmitting;
4966
+ };
4967
+ }
4968
+ // ============================================
4969
+ // Lifecycle
4970
+ // ============================================
4971
+ connectedCallback() {
4972
+ super.connectedCallback();
4973
+ this._findWizardForm()?.addEventListener("wf:nav-state", this._handleNavState);
4974
+ this._requestNavState();
4975
+ }
4976
+ disconnectedCallback() {
4977
+ super.disconnectedCallback();
4978
+ this._findWizardForm()?.removeEventListener("wf:nav-state", this._handleNavState);
4979
+ }
4980
+ // ============================================
4981
+ // Helpers
4982
+ // ============================================
4983
+ _findWizardForm() {
4984
+ return this.closest("wizard-form");
4985
+ }
4986
+ _requestNavState() {
4987
+ this.dispatchEvent(
4988
+ new CustomEvent("wf:nav-state-request", {
4989
+ bubbles: true,
4990
+ composed: true
4991
+ })
4992
+ );
4993
+ }
4994
+ /**
4995
+ * Dispatch the navigation event
4996
+ */
4997
+ _dispatchNavEvent() {
4998
+ this.dispatchEvent(
4999
+ new CustomEvent(this._getEventName(), {
5000
+ bubbles: true,
5001
+ composed: true
5002
+ })
5003
+ );
5004
+ }
5005
+ }
5006
+ __decorateClass$2([
5007
+ r()
5008
+ ], NavigationButtonBase.prototype, "_isFirstStep");
5009
+ __decorateClass$2([
5010
+ r()
5011
+ ], NavigationButtonBase.prototype, "_isLastStep");
5012
+ __decorateClass$2([
5013
+ r()
5014
+ ], NavigationButtonBase.prototype, "_isSubmitting");
5015
+ const wfNextBtnStyles = [
5016
+ sharedAnimations,
5017
+ buttonBaseStyles,
5018
+ i$3`
5019
+ :host {
5020
+ display: block;
5021
+ width: 100%;
5022
+ }
5023
+
5024
+ :host([hidden]) {
5025
+ display: none;
5026
+ }
5027
+
5028
+ .wf-btn-next {
5029
+ width: 100%;
5030
+ flex: 1;
5031
+ background-color: var(--wf-color-primary);
5032
+ border: 1px solid var(--wf-color-primary-border);
5033
+ color: white;
5034
+ position: relative;
5035
+ }
5036
+
5037
+ .wf-btn-next:hover:not(:disabled) {
5038
+ filter: brightness(1.1);
5039
+ }
5040
+
5041
+ .wf-btn-shortcut {
5042
+ display: inline-flex;
5043
+ align-items: center;
5044
+ gap: var(--wf-spacing-05);
5045
+ }
5046
+
5047
+ .wf-loading {
5048
+ display: inline-block;
5049
+ width: var(--wf-spinner-size);
5050
+ height: var(--wf-spinner-size);
5051
+ border: 2px solid rgba(0, 0, 0, 0.1);
5052
+ border-radius: 50%;
5053
+ border-top-color: white;
5054
+ animation: wf-spin 0.8s linear infinite;
5055
+ }
5056
+
5057
+ /* Inline button styles (for use inside wf-other) */
5058
+ :host([inline]) {
5059
+ display: inline-block;
5060
+ width: auto;
5061
+ }
5062
+
5063
+ :host([inline]) .wf-btn {
5064
+ min-height: var(--wf-input-min-height);
5065
+ width: auto;
5066
+ padding: var(--wf-spacing-3) var(--wf-spacing-5);
5067
+ }
5068
+ `
5069
+ ];
5070
+ var __defProp$1 = Object.defineProperty;
5071
+ var __getOwnPropDesc$1 = Object.getOwnPropertyDescriptor;
5072
+ var __decorateClass$1 = (decorators, target, key, kind) => {
5073
+ var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$1(target, key) : target;
5074
+ for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
5075
+ if (decorator = decorators[i2])
5076
+ result = (kind ? decorator(target, key, result) : decorator(result)) || result;
5077
+ if (kind && result) __defProp$1(target, key, result);
5078
+ return result;
5079
+ };
5080
+ let WfNextBtn = class extends NavigationButtonBase {
5081
+ constructor() {
5082
+ super(...arguments);
5083
+ this.showShortcut = true;
5084
+ this.inline = false;
5085
+ this.disabled = false;
5086
+ this._handleClick = () => {
5087
+ if (this.disabled || this._isSubmitting) {
5088
+ return;
5089
+ }
5090
+ this._dispatchNavEvent();
5091
+ };
5092
+ }
5093
+ // ============================================
5094
+ // Abstract Implementation
5095
+ // ============================================
5096
+ _getEventName() {
5097
+ return "wf:nav-next";
5098
+ }
5099
+ // ============================================
5100
+ // Helpers
5101
+ // ============================================
5102
+ _getButtonLabel() {
5103
+ if (this.label) {
5104
+ return this.label;
5105
+ }
5106
+ const isSubmit = !this.inline && (this.action === "submit" || this.action !== "next" && this._isLastStep);
5107
+ return isSubmit ? "Submit" : "Continue";
5108
+ }
5109
+ _isSubmitAction() {
5110
+ return !this.inline && (this.action === "submit" || this.action !== "next" && this._isLastStep);
5111
+ }
5112
+ // ============================================
5113
+ // Render
5114
+ // ============================================
5115
+ render() {
5116
+ const buttonLabel = this._getButtonLabel();
5117
+ const isDisabled = this.disabled || this._isSubmitting;
5118
+ return b`
5119
+ <button
5120
+ type="button"
5121
+ class="wf-btn wf-btn-next"
5122
+ ?disabled="${isDisabled}"
5123
+ @click="${this._handleClick}"
5124
+ data-testid="wf-next-btn"
5125
+ >
5126
+ ${this._isSubmitting ? b`<span class="wf-loading"></span>` : b`
5127
+ ${buttonLabel}
5128
+ ${this.showShortcut ? b`
5129
+ <span class="wf-btn-shortcut ${this.inline ? "wf-btn-shortcut-inline" : ""}">
5130
+ <wf-badge variant="button" shortcut="Enter ↵"></wf-badge>
5131
+ </span>
5132
+ ` : A}
5133
+ `}
5134
+ </button>
5135
+ `;
5136
+ }
5137
+ };
5138
+ WfNextBtn.styles = wfNextBtnStyles;
5139
+ __decorateClass$1([
5140
+ n2({ type: String })
5141
+ ], WfNextBtn.prototype, "label", 2);
5142
+ __decorateClass$1([
5143
+ n2({ type: String })
5144
+ ], WfNextBtn.prototype, "action", 2);
5145
+ __decorateClass$1([
5146
+ n2({ type: Boolean, attribute: "show-shortcut" })
5147
+ ], WfNextBtn.prototype, "showShortcut", 2);
5148
+ __decorateClass$1([
5149
+ n2({ type: Boolean })
5150
+ ], WfNextBtn.prototype, "inline", 2);
5151
+ __decorateClass$1([
5152
+ n2({ type: Boolean })
5153
+ ], WfNextBtn.prototype, "disabled", 2);
5154
+ WfNextBtn = __decorateClass$1([
5155
+ t("wf-next-btn")
5156
+ ], WfNextBtn);
5157
+ const wfBackBtnStyles = [
5158
+ buttonBaseStyles,
5159
+ i$3`
5160
+ :host {
5161
+ display: inline-block;
5162
+ }
5163
+
5164
+ :host([hidden]) {
5165
+ display: none;
5166
+ }
5167
+
5168
+ .wf-btn-back {
5169
+ background: var(--wf-glass-bg);
5170
+ backdrop-filter: blur(var(--wf-glass-blur));
5171
+ -webkit-backdrop-filter: blur(var(--wf-glass-blur));
5172
+ border: 1px solid var(--wf-glass-border);
5173
+ box-shadow: var(--wf-glass-shadow);
5174
+ color: var(--wf-color-text);
5175
+ }
5176
+
5177
+ .wf-btn-back:hover:not(:disabled) {
5178
+ background: var(--wf-glass-bg-hover);
5179
+ }
5180
+
5181
+ .wf-btn-shortcut {
5182
+ display: inline-flex;
5183
+ align-items: center;
5184
+ gap: var(--wf-spacing-05);
5185
+ }
5186
+ `
5187
+ ];
4004
5188
  var __defProp = Object.defineProperty;
4005
5189
  var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4006
5190
  var __decorateClass = (decorators, target, key, kind) => {
@@ -4011,117 +5195,86 @@ var __decorateClass = (decorators, target, key, kind) => {
4011
5195
  if (kind && result) __defProp(target, key, result);
4012
5196
  return result;
4013
5197
  };
4014
- let WfThankYou = class extends i {
5198
+ let WfBackBtn = class extends NavigationButtonBase {
4015
5199
  constructor() {
4016
5200
  super(...arguments);
4017
- this.title = "Thank you!";
4018
- this._cachedIconContent = [];
4019
- this._cachedFooterContent = [];
4020
- this._cachedDefaultContent = [];
4021
- this.subtitle = "We've received your request.";
4022
- this.hideIcon = false;
4023
- }
4024
- /**
4025
- * Disable Shadow DOM - render to Light DOM for external styling
4026
- */
4027
- createRenderRoot() {
4028
- return this;
4029
- }
4030
- connectedCallback() {
4031
- if (this._cachedIconContent.length === 0 && this._cachedFooterContent.length === 0 && this._cachedDefaultContent.length === 0) {
4032
- const iconSlot = this.querySelector('[slot="icon"]');
4033
- const footerSlot = this.querySelector('[slot="footer"]');
4034
- if (iconSlot) {
4035
- this._cachedIconContent = [iconSlot.cloneNode(true)];
4036
- }
4037
- if (footerSlot) {
4038
- this._cachedFooterContent = [footerSlot.cloneNode(true)];
5201
+ this.label = "Back";
5202
+ this.showShortcut = true;
5203
+ this.disabled = false;
5204
+ this.hideOnFirst = true;
5205
+ this._handleClick = () => {
5206
+ if (this.disabled) {
5207
+ return;
4039
5208
  }
4040
- Array.from(this.childNodes).forEach((node) => {
4041
- if (node.nodeType === Node.ELEMENT_NODE) {
4042
- const el = node;
4043
- if (!el.hasAttribute("slot")) {
4044
- this._cachedDefaultContent.push(node.cloneNode(true));
4045
- }
4046
- } else if (node.nodeType === Node.TEXT_NODE && node.textContent?.trim()) {
4047
- this._cachedDefaultContent.push(node.cloneNode(true));
4048
- }
4049
- });
4050
- this.textContent = "";
4051
- }
4052
- super.connectedCallback();
5209
+ this._dispatchNavEvent();
5210
+ };
5211
+ }
5212
+ // ============================================
5213
+ // Abstract Implementation
5214
+ // ============================================
5215
+ _getEventName() {
5216
+ return "wf:nav-back";
4053
5217
  }
5218
+ // ============================================
5219
+ // Render
5220
+ // ============================================
4054
5221
  render() {
5222
+ if (this.hideOnFirst && this._isFirstStep) {
5223
+ return A;
5224
+ }
4055
5225
  return b`
4056
- ${!this.hideIcon ? b`
4057
- <div class="wf-thank-you-icon">
4058
- ${this._cachedIconContent.length > 0 ? this._cachedIconContent : b`<svg
4059
- xmlns="http://www.w3.org/2000/svg"
4060
- fill="none"
4061
- viewBox="0 0 24 24"
4062
- stroke="currentColor"
4063
- >
4064
- <path
4065
- stroke-linecap="round"
4066
- stroke-linejoin="round"
4067
- stroke-width="2"
4068
- d="M5 13l4 4L19 7"
4069
- />
4070
- </svg>`}
4071
- </div>
4072
- ` : ""}
4073
- <h2 class="wf-thank-you-title">${this.title}</h2>
4074
- <p class="wf-thank-you-subtitle">${this.subtitle}</p>
4075
- ${this._cachedDefaultContent}
4076
- ${this._cachedFooterContent.length > 0 ? b`<div class="wf-thank-you-footer">${this._cachedFooterContent}</div>` : ""}
5226
+ <button
5227
+ type="button"
5228
+ class="wf-btn wf-btn-back"
5229
+ ?disabled="${this.disabled}"
5230
+ @click="${this._handleClick}"
5231
+ data-testid="wf-back-btn"
5232
+ >
5233
+ ${this.showShortcut ? b`
5234
+ <span class="wf-btn-shortcut">
5235
+ <wf-badge variant="button-secondary">Esc</wf-badge>
5236
+ </span>
5237
+ ` : A}
5238
+ ${this.label}
5239
+ </button>
4077
5240
  `;
4078
5241
  }
4079
5242
  };
5243
+ WfBackBtn.styles = wfBackBtnStyles;
4080
5244
  __decorateClass([
4081
5245
  n2({ type: String })
4082
- ], WfThankYou.prototype, "title", 2);
5246
+ ], WfBackBtn.prototype, "label", 2);
4083
5247
  __decorateClass([
4084
- n2({ type: String })
4085
- ], WfThankYou.prototype, "subtitle", 2);
5248
+ n2({ type: Boolean, attribute: "show-shortcut" })
5249
+ ], WfBackBtn.prototype, "showShortcut", 2);
4086
5250
  __decorateClass([
4087
- n2({ type: Boolean, attribute: "hide-icon" })
4088
- ], WfThankYou.prototype, "hideIcon", 2);
4089
- WfThankYou = __decorateClass([
4090
- t("wf-thank-you")
4091
- ], WfThankYou);
4092
- const GLOBAL_STYLES = `wizard-form{--wf-color-primary:#8040f0;--wf-color-primary-border:#602cbb;--wf-color-primary-light:#8040f014;--wf-color-surface:#f3f3f5;--wf-color-surface-hover:#e9e9eb;--wf-color-border:#d4d4d4;--wf-color-text:#0a0a0a;--wf-color-text-secondary:#404040;--wf-color-text-muted:#646464;--wf-color-error:#dc3545;--wf-color-badge-bg:#fcfcfc;--wf-color-badge-border:#d4d4d4;--wf-color-badge-text:#5f5f5f;--wf-color-progress-active:#0000001a;--wf-color-progress-inactive:#0000000d;--wf-spacing-1:4px;--wf-spacing-2:8px;--wf-spacing-3:12px;--wf-spacing-4:16px;--wf-spacing-5:20px;--wf-spacing-6:24px;--wf-spacing-8:32px;--wf-radius-sm:4px;--wf-radius-md:8px;--wf-radius-lg:8px;--wf-radius-full:99px;--wf-font-size-xs:.75rem;--wf-font-size-sm:.875rem;--wf-font-size-base:1rem;--wf-font-size-lg:1.25rem;--wf-font-size-xl:1.5rem;--wf-font-size-2xl:2rem;--wf-font-size-3xl:2.5rem;--wf-input-min-height:56px;--wf-glass-bg:#ffffffb3;--wf-glass-bg-hover:#ffffffd9;--wf-glass-border:#0000001a;--wf-glass-blur:20px;--wf-glass-shadow:0 4px 6px #0000000d;display:block}wizard-form[theme=dark]{--wf-color-surface:#2d2d2d;--wf-color-surface-hover:#3d3d3d;--wf-color-border:#4d4d4d;--wf-color-text:#f8f9fa;--wf-color-text-secondary:#d0d0d0;--wf-color-text-muted:#adb5bd;--wf-color-badge-bg:#3d3d3d;--wf-color-badge-border:#4d4d4d;--wf-color-badge-text:#adb5bd;--wf-color-progress-active:#c8c8c899;--wf-color-progress-inactive:#64646499;--wf-glass-bg:#2d2d2db3;--wf-glass-bg-hover:#3c3c3ccc;--wf-glass-border:#ffffff1a}@media (prefers-color-scheme:dark){wizard-form[theme=auto]{--wf-color-surface:#2d2d2d;--wf-color-surface-hover:#3d3d3d;--wf-color-border:#4d4d4d;--wf-color-text:#f8f9fa;--wf-color-text-secondary:#d0d0d0;--wf-color-text-muted:#adb5bd;--wf-color-badge-bg:#3d3d3d;--wf-color-badge-border:#4d4d4d;--wf-color-badge-text:#adb5bd;--wf-color-progress-active:#c8c8c899;--wf-color-progress-inactive:#64646499;--wf-glass-bg:#2d2d2db3;--wf-glass-bg-hover:#3c3c3ccc;--wf-glass-border:#ffffff1a}}wizard-form .wf-container{margin:0 auto}wizard-form .wf-progress{gap:var(--wf-spacing-4,16px);margin-top:var(--wf-spacing-6,24px);display:flex}wizard-form .wf-progress-segment{background-color:var(--wf-color-progress-inactive,#0000001a);border-radius:var(--wf-radius-full,99px);width:32px;height:8px;transition:background-color .3s}wizard-form .wf-progress-segment.completed,wizard-form .wf-progress-segment.active{background-color:var(--wf-color-progress-active,#0000004d)}wizard-form .wf-steps-container{min-height:200px}wizard-form .wf-navigation{justify-content:space-between;gap:var(--wf-spacing-4,16px);margin-top:var(--wf-spacing-6,24px);display:flex}wizard-form .wf-btn{justify-content:center;align-items:center;gap:var(--wf-spacing-2,8px);padding:var(--wf-spacing-3,12px)var(--wf-spacing-4,16px);min-height:48px;font-size:var(--wf-font-size-base,1rem);border-radius:var(--wf-radius-md,8px);cursor:pointer;border:1px solid #0000;outline:none;font-family:inherit;font-weight:600;transition:all .15s;display:inline-flex}wizard-form .wf-btn:focus-visible{box-shadow:0 0 0 3px #8040f04d}wizard-form .wf-btn-back{background:var(--wf-glass-bg,#ffffffb3);-webkit-backdrop-filter:blur(var(--wf-glass-blur,20px));border:1px solid var(--wf-glass-border,#0000001a);box-shadow:var(--wf-glass-shadow,0 4px 6px #0000000d);color:var(--wf-color-text,#0a0a0a)}wizard-form .wf-btn-back:hover:not(:disabled){background:var(--wf-glass-bg-hover,#ffffffd9)}wizard-form .wf-btn-next{background-color:var(--wf-color-primary,#8040f0);border:1px solid var(--wf-color-primary-border,#602cbb);color:#fff;flex:1;margin-left:auto;position:relative}wizard-form .wf-btn-next:hover:not(:disabled){filter:brightness(1.1)}wizard-form .wf-btn:disabled{opacity:.5;cursor:not-allowed}wizard-form .wf-btn-shortcut{right:var(--wf-spacing-4,16px);align-items:center;gap:2px;display:inline-flex;position:absolute}wizard-form .wf-btn-back .wf-btn-shortcut{position:static}wizard-form .wf-success-screen{text-align:center;padding:var(--wf-spacing-6,24px)}wizard-form .wf-loading{border:2px solid #0000001a;border-top-color:#fff;border-radius:50%;width:20px;height:20px;animation:.8s linear infinite wf-spin;display:inline-block}@keyframes wf-spin{to{transform:rotate(360deg)}}wizard-form .wf-form-error{padding:var(--wf-spacing-4,16px);margin-bottom:var(--wf-spacing-4,16px);border:1px solid var(--wf-color-error,#dc3545);border-radius:var(--wf-radius-md,8px);color:var(--wf-color-error,#dc3545);font-size:var(--wf-font-size-base,1rem);background-color:#dc35451a}wf-success{display:block}wf-success h1,wf-success h2,wf-success h3{margin:0 0 var(--wf-spacing-4,16px)0;color:var(--wf-color-text,#212529);font-weight:600}wf-success p{color:var(--wf-color-text-muted,#6c757d);margin:0}wf-step{width:100%;display:none}wf-step[active]{animation:.3s forwards wf-stepFadeIn;display:block}wf-step[direction=forward][active]{animation:.3s forwards wf-stepSlideInRight}wf-step[direction=backward][active]{animation:.3s forwards wf-stepSlideInLeft}wf-step[leaving]{animation:.2s forwards wf-stepFadeOut;display:block}@keyframes wf-stepFadeIn{0%{opacity:0;transform:translateY(10px)}to{opacity:1;transform:translateY(0)}}@keyframes wf-stepFadeOut{0%{opacity:1;transform:translateY(0)}to{opacity:0;transform:translateY(-10px)}}@keyframes wf-stepSlideInRight{0%{opacity:0;transform:translate(30px)}to{opacity:1;transform:translate(0)}}@keyframes wf-stepSlideInLeft{0%{opacity:0;transform:translate(-30px)}to{opacity:1;transform:translate(0)}}wf-step .wf-step-content{gap:var(--wf-spacing-4,16px);flex-direction:column;display:flex}wf-step h1,wf-step h2,wf-step h3{color:var(--wf-color-text,#212529);margin:0;font-weight:600}wf-step h2{font-size:var(--wf-font-size-3xl,2rem)}wf-step p{color:var(--wf-color-text-muted,#6c757d);font-size:var(--wf-font-size-xl,1.375rem);margin:0}wf-options{display:block}wf-options[hidden]{display:none}wf-options .wf-options-container{gap:var(--wf-spacing-4,16px);grid-template-columns:repeat(2,1fr);display:grid}wf-options[columns="1"] .wf-options-container{grid-template-columns:1fr}@media (width<=600px){wf-options .wf-options-container{grid-template-columns:1fr}}wf-options .wf-error-message{margin-top:var(--wf-spacing-2,8px);font-size:var(--wf-font-size-sm,.875rem);color:var(--wf-color-error,#dc3545);min-height:20px;display:block}wf-options .wf-other-container{margin-top:var(--wf-spacing-4,16px)}wf-options .wf-other-label{margin-bottom:var(--wf-spacing-2,8px);font-size:var(--wf-font-size-sm,.875rem);color:var(--wf-color-text,#0a0a0a);font-weight:500;display:block}wf-options .wf-other-label span{color:var(--wf-color-text-muted,#646464);font-weight:400}wf-options .wf-other-input-wrapper{align-items:center;gap:var(--wf-spacing-3,12px);min-height:var(--wf-input-min-height,56px);background:var(--wf-glass-bg,#ffffffb3);-webkit-backdrop-filter:blur(var(--wf-glass-blur,20px));border:1px solid var(--wf-glass-border,#0000001a);border-radius:var(--wf-radius-md,8px);box-shadow:var(--wf-glass-shadow,0 4px 6px #0000000d);padding-left:var(--wf-spacing-4,16px);transition:border-color .15s,box-shadow .15s,background .15s;display:flex}wf-options .wf-other-input-wrapper:focus-within{border-color:var(--wf-color-primary,#8040f0);box-shadow:0 0 0 3px #8040f01a}wf-options .wf-other-input{min-height:calc(var(--wf-input-min-height,56px) - 2px);padding:var(--wf-spacing-4,16px);font-size:var(--wf-font-size-base,1rem);color:var(--wf-color-text,#0a0a0a);box-sizing:border-box;background:0 0;border:none;outline:none;flex:1;padding-left:0;font-weight:500}wf-options .wf-other-input::placeholder{color:var(--wf-color-text-muted,#646464);font-weight:500}wf-option{display:block}wf-option[hidden]{display:none}wf-option .wf-option-card{align-items:center;gap:var(--wf-spacing-3,12px);width:100%;min-height:var(--wf-input-min-height,56px);padding:var(--wf-spacing-3,12px);background:var(--wf-glass-bg,#ffffffb3);-webkit-backdrop-filter:blur(var(--wf-glass-blur,20px));border:1px solid var(--wf-glass-border,#0000001a);border-radius:var(--wf-radius-md,8px);box-shadow:var(--wf-glass-shadow,0 4px 6px #0000000d);cursor:pointer;text-align:left;font-family:inherit;font-size:var(--wf-font-size-base,1rem);color:var(--wf-color-text,#0a0a0a);box-sizing:border-box;outline:none;font-weight:500;transition:border-color .15s,background .15s,transform .1s;display:flex}wf-option .wf-option-card:hover:not(:disabled){border-color:var(--wf-color-primary,#8040f0);background:var(--wf-glass-bg-hover,#ffffffd9)}wf-option .wf-option-card:focus-visible{border-color:var(--wf-color-primary,#8040f0);box-shadow:0 0 0 3px #8040f033}wf-option .wf-option-card[aria-selected=true]{border-color:var(--wf-color-primary,#8040f0);background-color:var(--wf-color-primary-light,#8040f01a)}wf-option .wf-option-card:disabled{opacity:.5;cursor:not-allowed}wf-option .wf-option-card:active:not(:disabled){transform:scale(.98)}wf-option .wf-option-card.selecting{animation:.3s wf-blink}@keyframes wf-blink{0%,to{opacity:1}50%{opacity:.5}}wf-option .wf-option-content{flex:1;min-width:0}wf-option .wf-option-content strong,wf-option .wf-option-content h3,wf-option .wf-option-content h4{margin:0;font-weight:600;display:block}wf-option .wf-option-content span,wf-option .wf-option-content p{font-size:var(--wf-font-size-sm,.875rem);color:var(--wf-color-text-muted,#646464);margin:4px 0 0;display:block}wf-progress{display:block}wf-progress[hidden]{display:none}wf-progress .wf-progress{gap:var(--wf-spacing-4,16px);display:flex}wf-progress .wf-progress-segment{background-color:var(--wf-color-progress-inactive,#0000000d);border-radius:var(--wf-radius-full,99px);width:32px;height:8px;transition:background-color .3s}wf-progress .wf-progress-segment.completed,wf-progress .wf-progress-segment.active{background-color:var(--wf-color-progress-active,#0000001a)}wf-badge{display:inline-flex}wf-badge[hidden]{display:none}wf-badge .wf-badge{box-sizing:border-box;min-width:24px;height:24px;padding:var(--wf-spacing-1,4px)var(--wf-spacing-2,8px);font-size:var(--wf-font-size-xs,.75rem);text-transform:uppercase;flex-shrink:0;justify-content:center;align-items:center;font-family:inherit;font-weight:500;line-height:1;display:inline-flex}wf-badge .wf-badge--default{background-color:var(--wf-color-badge-bg,#fcfcfc);border:1px solid var(--wf-color-badge-border,#d4d4d4);border-radius:var(--wf-radius-sm,4px);color:var(--wf-color-badge-text,#5f5f5f)}wf-badge .wf-badge--selected{background-color:var(--wf-color-primary,#8040f0);border:1px solid var(--wf-color-primary,#8040f0);border-radius:var(--wf-radius-sm,4px);color:#fff}wf-badge .wf-badge--button{border-radius:var(--wf-radius-sm,4px);color:#ffffffa6;background-color:#0000;border:none}wf-badge .wf-badge--button-secondary{border-radius:var(--wf-radius-sm,4px);color:var(--wf-color-text-muted,#5f5f5f);background-color:#0000;border:none}wf-layout{box-sizing:border-box;display:block}wf-layout[hidden]{display:none}wf-layout.wf-layout--width-full{width:100%}wf-layout.wf-layout--width-auto{width:auto}wf-layout.wf-layout--width-fit{width:fit-content}wf-thank-you{text-align:center;padding:var(--wf-spacing-8,48px)var(--wf-spacing-4,24px);display:block}wf-thank-you[hidden]{display:none}wf-thank-you .wf-thank-you-icon{width:72px;height:72px;margin:0 auto var(--wf-spacing-4,24px);background:linear-gradient(135deg,#10b981 0%,#059669 100%);border-radius:50%;justify-content:center;align-items:center;display:flex;box-shadow:0 10px 25px -5px #10b98166}wf-thank-you .wf-thank-you-icon svg{color:#fff;width:36px;height:36px}wf-thank-you .wf-thank-you-title{color:var(--wf-color-text,#1e293b);margin:0 0 12px;font-size:28px;font-weight:700}wf-thank-you .wf-thank-you-subtitle{color:var(--wf-color-text-muted,#64748b);margin:0 0 24px;font-size:16px;line-height:1.6}wf-thank-you [slot=footer]{margin-top:var(--wf-spacing-4,24px)}wf-input,wf-email,wf-textarea,wf-field,wf-number{display:block}wf-input[hidden],wf-email[hidden],wf-textarea[hidden],wf-field[hidden],wf-number[hidden]{display:none}.wf-field-container{gap:var(--wf-spacing-2,8px);flex-direction:column;display:flex}.wf-label{font-size:var(--wf-font-size-sm,.875rem);color:var(--wf-color-text,#0a0a0a);font-weight:500}.wf-label-required:after{content:" *";color:var(--wf-color-error,#dc3545)}.wf-error-message{font-size:var(--wf-font-size-sm,.875rem);color:var(--wf-color-error,#dc3545)}.wf-hint{font-size:var(--wf-font-size-sm,.875rem);color:var(--wf-color-text-muted,#646464)}.wf-input{width:100%;min-height:var(--wf-input-min-height,56px);padding:var(--wf-spacing-4,16px);font-size:var(--wf-font-size-base,1rem);background:var(--wf-glass-bg,#ffffffb3);-webkit-backdrop-filter:blur(var(--wf-glass-blur,20px));border:1px solid var(--wf-glass-border,#0000001a);border-radius:var(--wf-radius-md,8px);box-shadow:var(--wf-glass-shadow,0 4px 6px #0000000d);color:var(--wf-color-text,#0a0a0a);box-sizing:border-box;outline:none;font-family:inherit;font-weight:400;transition:border-color .15s,box-shadow .15s,background .15s}.wf-input::placeholder{color:var(--wf-color-text-muted,#646464);font-weight:500}.wf-input:focus{border-color:var(--wf-color-primary,#8040f0);box-shadow:0 0 0 3px #8040f033}.wf-input:disabled{opacity:.5;cursor:not-allowed}.wf-input.wf-input-error{border-color:var(--wf-color-error,#dc3545)}.wf-input.wf-input-error:focus{box-shadow:0 0 0 3px #dc354533}.wf-textarea{width:100%;padding:var(--wf-spacing-4,16px);font-size:var(--wf-font-size-base,1rem);background:var(--wf-glass-bg,#ffffffb3);-webkit-backdrop-filter:blur(var(--wf-glass-blur,20px));border:1px solid var(--wf-glass-border,#0000001a);border-radius:var(--wf-radius-lg,12px);box-shadow:var(--wf-glass-shadow,0 4px 6px #0000000d);color:var(--wf-color-text,#212529);box-sizing:border-box;resize:vertical;outline:none;min-height:100px;font-family:inherit;transition:border-color .15s,box-shadow .15s,background .15s}.wf-textarea::placeholder{color:var(--wf-color-text-muted,#6c757d)}.wf-textarea:focus{border-color:var(--wf-color-primary,#8b5cf6);box-shadow:0 0 0 3px #8b5cf633}.wf-textarea:disabled{opacity:.5;cursor:not-allowed}.wf-textarea.wf-textarea-error{border-color:var(--wf-color-error,#dc3545)}.wf-textarea.wf-textarea-error:focus{box-shadow:0 0 0 3px #dc354533}.wf-char-count{font-size:var(--wf-font-size-sm,.875rem);color:var(--wf-color-text-muted,#6c757d);text-align:right}.wf-char-count.wf-char-limit{color:var(--wf-color-error,#dc3545)}wf-field .wf-input-wrapper{position:relative}wf-field .wf-input-wrapper input,wf-field .wf-input-wrapper textarea,wf-field .wf-input-wrapper select{width:100%;padding:var(--wf-spacing-4,16px);font-size:var(--wf-font-size-base,1rem);background-color:var(--wf-color-surface,#f8f9fa);border:2px solid var(--wf-color-border,#dee2e6);border-radius:var(--wf-radius-lg,12px);color:var(--wf-color-text,#212529);box-sizing:border-box;outline:none;font-family:inherit;transition:border-color .15s,box-shadow .15s}wf-field .wf-input-wrapper input::placeholder,wf-field .wf-input-wrapper textarea::placeholder{color:var(--wf-color-text-muted,#6c757d)}wf-field .wf-input-wrapper input:focus,wf-field .wf-input-wrapper textarea:focus,wf-field .wf-input-wrapper select:focus{border-color:var(--wf-color-primary,#8b5cf6);box-shadow:0 0 0 3px #8b5cf633}wf-field .wf-input-wrapper input:disabled,wf-field .wf-input-wrapper textarea:disabled,wf-field .wf-input-wrapper select:disabled{opacity:.5;cursor:not-allowed}wf-number .wf-input::-webkit-outer-spin-button,wf-number .wf-input::-webkit-inner-spin-button{-webkit-appearance:none;margin:0}wf-number .wf-input[type=number]{-moz-appearance:textfield}`;
4093
- function injectGlobalStyles() {
4094
- if (typeof document === "undefined") {
4095
- return;
4096
- }
4097
- const STYLE_ID = "wf-global-styles";
4098
- if (document.getElementById(STYLE_ID)) {
4099
- return;
4100
- }
4101
- const style = document.createElement("style");
4102
- style.id = STYLE_ID;
4103
- style.textContent = GLOBAL_STYLES;
4104
- document.head.appendChild(style);
4105
- }
4106
- injectGlobalStyles();
5251
+ n2({ type: Boolean })
5252
+ ], WfBackBtn.prototype, "disabled", 2);
5253
+ __decorateClass([
5254
+ n2({ type: Boolean, attribute: "hide-on-first" })
5255
+ ], WfBackBtn.prototype, "hideOnFirst", 2);
5256
+ WfBackBtn = __decorateClass([
5257
+ t("wf-back-btn")
5258
+ ], WfBackBtn);
4107
5259
  export {
4108
5260
  DEFAULT_BLOCKED_DOMAINS,
4109
5261
  FormStateController,
4110
5262
  KeyboardController,
4111
5263
  ValidationController,
5264
+ WfBackBtn,
4112
5265
  WfBadge,
4113
5266
  WfEmail,
4114
- WfField,
4115
5267
  WfInput,
4116
5268
  WfLayout,
5269
+ WfNextBtn,
4117
5270
  WfNumber,
4118
5271
  WfOption,
4119
5272
  WfOptions,
5273
+ WfOther,
4120
5274
  WfProgress,
4121
5275
  WfStep,
4122
5276
  WfSuccess,
4123
5277
  WfTextarea,
4124
- WfThankYou,
4125
5278
  WizardForm,
4126
5279
  createHubSpotAdapter,
4127
5280
  createRevenueHeroAdapter,