@sebgroup/green-core 1.0.0-beta.8 → 1.0.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.
package/index.js CHANGED
@@ -37,7 +37,7 @@ import { property as property5 } from "lit/decorators.js";
37
37
  import { unsafeHTML } from "lit/directives/unsafe-html.js";
38
38
  import { when as when2 } from "lit/directives/when.js";
39
39
  import { ifDefined } from "lit/directives/if-defined.js";
40
- import { createRef as createRef2, ref as ref2 } from "lit/directives/ref.js";
40
+ import { createRef as createRef3, ref as ref3 } from "lit/directives/ref.js";
41
41
  import { msg, str, updateWhenLocaleChanges } from "@lit/localize";
42
42
  import "reflect-metadata";
43
43
 
@@ -119,10 +119,31 @@ function observeLightDOM() {
119
119
  };
120
120
  }
121
121
 
122
+ // libs/core/src/utils/decorators/watch-media-query.ts
123
+ function watchMediaQuery(q) {
124
+ return (proto, _propertyKey, descriptor) => {
125
+ const mediaQuery = window.matchMedia(q);
126
+ const connectedCallback = proto.connectedCallback;
127
+ const disconnectedCallback = proto.disconnectedCallback;
128
+ proto.connectedCallback = function() {
129
+ connectedCallback?.call(this);
130
+ const listener = (e) => {
131
+ descriptor.value?.call(this, e.matches);
132
+ };
133
+ mediaQuery.addEventListener("change", listener);
134
+ this.disconnectedCallback = function() {
135
+ disconnectedCallback?.call(this);
136
+ mediaQuery.removeEventListener("change", listener);
137
+ };
138
+ descriptor.value?.call(this, mediaQuery.matches);
139
+ };
140
+ };
141
+ }
142
+
122
143
  // libs/core/src/utils/helpers/custom-element-scoping.ts
123
144
  import { html as litHtml } from "lit";
124
145
  import { customElement } from "lit/decorators.js";
125
- var VER_SUFFIX = "-00499f";
146
+ var VER_SUFFIX = "-b7215a";
126
147
  var elementLookupTable = /* @__PURE__ */ new Map();
127
148
  var gdsCustomElement = (tagName) => {
128
149
  if (globalThis.GDS_DISABLE_VERSIONED_ELEMENTS) {
@@ -130,6 +151,8 @@ var gdsCustomElement = (tagName) => {
130
151
  }
131
152
  const versionedTagName = tagName + VER_SUFFIX;
132
153
  elementLookupTable.set(tagName, versionedTagName);
154
+ if (customElements.get(versionedTagName))
155
+ return (_classOrDescriptor) => false;
133
156
  return customElement(versionedTagName);
134
157
  };
135
158
  var templateCache = /* @__PURE__ */ new WeakMap();
@@ -173,15 +196,17 @@ import { property as property2 } from "lit/decorators.js";
173
196
  import { createRef, ref } from "lit/directives/ref.js";
174
197
 
175
198
  // libs/core/src/utils/helpers/transitional-styles.ts
176
- var TransitionalStyles = class {
199
+ var TransitionalStyles = class _TransitionalStyles {
177
200
  constructor() {
178
201
  this.sheets = /* @__PURE__ */ new Map();
179
202
  this.elements = /* @__PURE__ */ new Map();
180
203
  }
181
204
  static get instance() {
182
- if (!globalThis.__gdsTransitionalStyles)
183
- globalThis.__gdsTransitionalStyles = new TransitionalStyles();
184
- return globalThis.__gdsTransitionalStyles;
205
+ if (!globalThis.__gdsTransitionalStyles?.[VER_SUFFIX])
206
+ globalThis.__gdsTransitionalStyles = {
207
+ [VER_SUFFIX]: new _TransitionalStyles()
208
+ };
209
+ return globalThis.__gdsTransitionalStyles[VER_SUFFIX];
185
210
  }
186
211
  apply(element, styleKey) {
187
212
  const sheet = this.sheets.get(styleKey);
@@ -381,6 +406,7 @@ var GdsListbox = class extends LitElement2 {
381
406
  constructor() {
382
407
  super();
383
408
  this.multiple = false;
409
+ this.compareWith = (a, b) => a === b;
384
410
  __privateAdd(this, _slotRef, createRef());
385
411
  __privateAdd(this, _handleSelect, (e) => {
386
412
  const option = e.target;
@@ -478,7 +504,7 @@ var GdsListbox = class extends LitElement2 {
478
504
  }
479
505
  set selection(values) {
480
506
  this.options.forEach((el) => {
481
- el.selected = values.includes(el.value) || values.includes(el);
507
+ el.selected = values.some((v) => this.compareWith(v, el.value));
482
508
  });
483
509
  }
484
510
  connectedCallback() {
@@ -520,6 +546,9 @@ __decorateClass([
520
546
  }
521
547
  })
522
548
  ], GdsListbox.prototype, "multiple", 2);
549
+ __decorateClass([
550
+ property2()
551
+ ], GdsListbox.prototype, "compareWith", 2);
523
552
  __decorateClass([
524
553
  watch("multiple")
525
554
  ], GdsListbox.prototype, "_rerenderOptions", 1);
@@ -530,8 +559,166 @@ GdsListbox = __decorateClass([
530
559
  // libs/core/src/primitives/popover/popover.ts
531
560
  import { LitElement as LitElement3, html as html3, unsafeCSS as unsafeCSS3 } from "lit";
532
561
  import { property as property3 } from "lit/decorators.js";
562
+ import { createRef as createRef2, ref as ref2 } from "lit/directives/ref.js";
533
563
  import { computePosition, autoUpdate, offset, flip } from "@floating-ui/dom";
534
564
 
565
+ // libs/core/src/primitives/popover/topLayerOverTransforms.middleware.ts
566
+ var topLayerOverTransforms = () => ({
567
+ name: "topLayer",
568
+ async fn(middlewareArguments) {
569
+ const {
570
+ x,
571
+ y,
572
+ elements: { reference, floating }
573
+ } = middlewareArguments;
574
+ let onTopLayer = false;
575
+ let topLayerIsFloating = false;
576
+ const diffCoords = {
577
+ x: 0,
578
+ y: 0
579
+ };
580
+ try {
581
+ onTopLayer = onTopLayer || floating.matches(":open");
582
+ } catch (e) {
583
+ }
584
+ try {
585
+ onTopLayer = onTopLayer || floating.matches(":modal");
586
+ } catch (e) {
587
+ }
588
+ topLayerIsFloating = onTopLayer;
589
+ if (!onTopLayer) {
590
+ const dialogAncestorQueryEvent = new Event("floating-ui-dialog-test", {
591
+ composed: true,
592
+ bubbles: true
593
+ });
594
+ floating.addEventListener(
595
+ "floating-ui-dialog-test",
596
+ (event) => {
597
+ event.composedPath().forEach((el) => {
598
+ if (el === floating || el.localName !== "dialog")
599
+ return;
600
+ try {
601
+ onTopLayer = onTopLayer || el.matches(":modal");
602
+ if (onTopLayer) {
603
+ }
604
+ } catch (e) {
605
+ }
606
+ });
607
+ },
608
+ { once: true }
609
+ );
610
+ floating.dispatchEvent(dialogAncestorQueryEvent);
611
+ }
612
+ let overTransforms = false;
613
+ const containingBlock = getContainingBlock(reference);
614
+ if (containingBlock !== null && !isWindow(containingBlock)) {
615
+ overTransforms = true;
616
+ }
617
+ if (onTopLayer && overTransforms) {
618
+ const rect = containingBlock.getBoundingClientRect();
619
+ diffCoords.x = rect.x;
620
+ diffCoords.y = rect.y;
621
+ }
622
+ if (onTopLayer && topLayerIsFloating) {
623
+ return {
624
+ x: x + diffCoords.x,
625
+ y: y + diffCoords.y,
626
+ data: diffCoords
627
+ };
628
+ }
629
+ if (onTopLayer) {
630
+ return {
631
+ x,
632
+ y,
633
+ data: diffCoords
634
+ };
635
+ }
636
+ return {
637
+ x: x - diffCoords.x,
638
+ y: y - diffCoords.y,
639
+ data: diffCoords
640
+ };
641
+ }
642
+ });
643
+ function getContainingBlock(element) {
644
+ let currentNode = getParentNode(element);
645
+ if (isShadowRoot(currentNode)) {
646
+ currentNode = currentNode.host;
647
+ }
648
+ while (isHTMLElement(currentNode) && !isLastTraversableNode(currentNode)) {
649
+ if (isContainingBlock(currentNode)) {
650
+ return currentNode;
651
+ } else {
652
+ const parent = currentNode.assignedSlot ? currentNode.assignedSlot : currentNode.parentNode;
653
+ currentNode = isShadowRoot(parent) ? parent.host : parent;
654
+ }
655
+ }
656
+ return null;
657
+ }
658
+ function isLastTraversableNode(node) {
659
+ return ["html", "body", "#document"].includes(getNodeName(node));
660
+ }
661
+ function isContainingBlock(element) {
662
+ const isFirefox = /firefox/i.test(getUAString());
663
+ if (element.tagName === "dialog") {
664
+ return true;
665
+ }
666
+ const css5 = getComputedStyle(element);
667
+ return css5.transform !== "none" || css5.perspective !== "none" || css5.contain === "paint" || ["transform", "perspective"].includes(css5.willChange) || isFirefox && css5.willChange === "filter" || isFirefox && (css5.filter ? css5.filter !== "none" : false);
668
+ }
669
+ function getUAString() {
670
+ const uaData = navigator.userAgentData;
671
+ if (uaData?.brands) {
672
+ return uaData.brands.map((item) => `${item.brand}/${item.version}`).join(" ");
673
+ }
674
+ return navigator.userAgent;
675
+ }
676
+ function getParentNode(node) {
677
+ if (getNodeName(node) === "html") {
678
+ return node;
679
+ }
680
+ return (
681
+ // this is a quicker (but less type safe) way to save quite some bytes from the bundle
682
+ node.assignedSlot || // step into the shadow DOM of the parent of a slotted node
683
+ node.parentNode || // DOM Element detected
684
+ (isShadowRoot(node) ? node.host : null) || // ShadowRoot detected
685
+ getDocumentElement(node)
686
+ );
687
+ }
688
+ function getNodeName(node) {
689
+ return isWindow(node) ? "" : node ? (node.nodeName || "").toLowerCase() : "";
690
+ }
691
+ function getDocumentElement(node) {
692
+ return ((isNode(node) ? node.ownerDocument : node.document) || window.document).documentElement;
693
+ }
694
+ function isNode(value) {
695
+ return value instanceof getWindow(value).Node;
696
+ }
697
+ function isWindow(value) {
698
+ return value && value.document && value.location && value.alert && value.setInterval;
699
+ }
700
+ function getWindow(node) {
701
+ if (node == null) {
702
+ return window;
703
+ }
704
+ if (!isWindow(node)) {
705
+ const ownerDocument = node.ownerDocument;
706
+ return ownerDocument ? ownerDocument.defaultView || window : window;
707
+ }
708
+ return node;
709
+ }
710
+ function isShadowRoot(node) {
711
+ if (typeof ShadowRoot === "undefined") {
712
+ return false;
713
+ }
714
+ const OwnElement = getWindow(node).ShadowRoot;
715
+ const testNode = node;
716
+ return node instanceof OwnElement || testNode instanceof ShadowRoot;
717
+ }
718
+ function isHTMLElement(value) {
719
+ return value instanceof getWindow(value).HTMLElement;
720
+ }
721
+
535
722
  // libs/core/src/primitives/popover/popover.styles.ts
536
723
  import { css as css3 } from "lit";
537
724
  var style3 = css3`
@@ -544,15 +731,23 @@ var style3 = css3`
544
731
  var popover_styles_default = style3;
545
732
 
546
733
  // libs/core/src/primitives/popover/popover.ts
547
- var _autoPositionCleanup, _registerTriggerEvents, registerTriggerEvents_fn, _unregisterTriggerEvents, unregisterTriggerEvents_fn, _triggerKeyDownListener, _setOpen, setOpen_fn;
734
+ var _dialogElementRef, _handleCloseButton, _registerTriggerEvents, registerTriggerEvents_fn, _unregisterTriggerEvents, unregisterTriggerEvents_fn, _autoPositionCleanup, _registerAutoPositioning, registerAutoPositioning_fn, _triggerKeyDownListener, _focusFirstSlottedChild, _clickOutsideListener;
548
735
  var GdsPopover = class extends LitElement3 {
549
736
  constructor() {
550
737
  super(...arguments);
551
738
  __privateAdd(this, _registerTriggerEvents);
552
739
  __privateAdd(this, _unregisterTriggerEvents);
553
- __privateAdd(this, _setOpen);
740
+ __privateAdd(this, _registerAutoPositioning);
554
741
  this.open = false;
555
742
  this.trigger = void 0;
743
+ this.label = void 0;
744
+ __privateAdd(this, _dialogElementRef, createRef2());
745
+ __privateAdd(this, _handleCloseButton, (e) => {
746
+ e.stopPropagation();
747
+ e.preventDefault();
748
+ this.open = false;
749
+ setTimeout(() => this.trigger?.focus(), 250);
750
+ });
556
751
  __privateAdd(this, _autoPositionCleanup, void 0);
557
752
  /**
558
753
  * ArrowDown on the trigger element will trigger the popover by default, and escape will close it.
@@ -560,14 +755,29 @@ var GdsPopover = class extends LitElement3 {
560
755
  __privateAdd(this, _triggerKeyDownListener, (e) => {
561
756
  if (e.key === "ArrowDown") {
562
757
  e.preventDefault();
563
- __privateMethod(this, _setOpen, setOpen_fn).call(this, true);
564
- const firstSlottedChild = this.shadowRoot?.querySelector("slot")?.assignedElements()[0];
565
- this.updateComplete.then(() => {
566
- firstSlottedChild?.focus();
567
- });
758
+ this.open = true;
568
759
  }
569
760
  if (e.key === "Escape") {
570
- __privateMethod(this, _setOpen, setOpen_fn).call(this, false);
761
+ this.open = false;
762
+ }
763
+ });
764
+ /**
765
+ * Move focus to the first slotted child.
766
+ */
767
+ __privateAdd(this, _focusFirstSlottedChild, () => {
768
+ const firstSlottedChild = this.shadowRoot?.querySelector("slot")?.assignedElements()[0];
769
+ this.updateComplete.then(() => {
770
+ firstSlottedChild?.focus();
771
+ });
772
+ });
773
+ __privateAdd(this, _clickOutsideListener, (e) => {
774
+ const dialog = __privateGet(this, _dialogElementRef).value;
775
+ if (dialog && this.open) {
776
+ const rect = dialog.getBoundingClientRect();
777
+ const isInDialog = rect.top <= e.clientY && e.clientY <= rect.top + rect.height && rect.left <= e.clientX && e.clientX <= rect.left + rect.width;
778
+ if (!isInDialog) {
779
+ this.open = false;
780
+ }
571
781
  }
572
782
  });
573
783
  }
@@ -578,10 +788,11 @@ var GdsPopover = class extends LitElement3 {
578
788
  super.connectedCallback();
579
789
  TransitionalStyles.instance.apply(this, "gds-popover");
580
790
  __privateMethod(this, _registerTriggerEvents, registerTriggerEvents_fn).call(this);
581
- this._updateHidden();
791
+ this._handleOpenChange();
582
792
  this.addEventListener("keydown", (e) => {
583
793
  if (e.key === "Escape") {
584
- __privateMethod(this, _setOpen, setOpen_fn).call(this, false);
794
+ this.open = false;
795
+ e.stopImmediatePropagation();
585
796
  }
586
797
  });
587
798
  }
@@ -590,31 +801,68 @@ var GdsPopover = class extends LitElement3 {
590
801
  __privateMethod(this, _unregisterTriggerEvents, unregisterTriggerEvents_fn).call(this);
591
802
  }
592
803
  render() {
593
- return html3` <slot></slot> `;
804
+ return html3`<dialog ${ref2(__privateGet(this, _dialogElementRef))}>
805
+ <header>
806
+ <h2>${this.label}</h2>
807
+ <button class="close" @click=${__privateGet(this, _handleCloseButton)}>
808
+ <i></i>
809
+ </button>
810
+ </header>
811
+ <slot></slot>
812
+ </dialog>`;
594
813
  }
595
- _updateHidden() {
814
+ _handleOpenChange() {
596
815
  this.setAttribute("aria-hidden", String(!this.open));
597
816
  this.hidden = !this.open;
817
+ this.updateComplete.then(() => {
818
+ if (this.open) {
819
+ __privateGet(this, _dialogElementRef).value?.showModal();
820
+ __privateGet(this, _focusFirstSlottedChild).call(this);
821
+ setTimeout(
822
+ () => __privateGet(this, _dialogElementRef).value?.addEventListener(
823
+ "click",
824
+ __privateGet(this, _clickOutsideListener)
825
+ ),
826
+ 0
827
+ );
828
+ } else {
829
+ __privateGet(this, _dialogElementRef).value?.close();
830
+ __privateGet(this, _dialogElementRef).value?.removeEventListener(
831
+ "click",
832
+ __privateGet(this, _clickOutsideListener)
833
+ );
834
+ }
835
+ });
836
+ this.dispatchEvent(
837
+ new CustomEvent("gds-ui-state", {
838
+ detail: { open: this.open },
839
+ bubbles: true,
840
+ composed: false
841
+ })
842
+ );
843
+ }
844
+ _handleMobileLayout(matches) {
845
+ var _a;
846
+ if (matches) {
847
+ (_a = __privateGet(this, _autoPositionCleanup)) == null ? void 0 : _a.call(this);
848
+ __privateGet(this, _dialogElementRef).value?.style.removeProperty("left");
849
+ __privateGet(this, _dialogElementRef).value?.style.removeProperty("top");
850
+ this.updateComplete.then(() => {
851
+ if (this.open)
852
+ __privateGet(this, _dialogElementRef).value?.showModal();
853
+ });
854
+ } else {
855
+ this.updateComplete.then(() => {
856
+ __privateMethod(this, _registerAutoPositioning, registerAutoPositioning_fn).call(this);
857
+ });
858
+ }
598
859
  }
599
860
  };
600
- _autoPositionCleanup = new WeakMap();
861
+ _dialogElementRef = new WeakMap();
862
+ _handleCloseButton = new WeakMap();
601
863
  _registerTriggerEvents = new WeakSet();
602
864
  registerTriggerEvents_fn = function() {
603
- if (!this.trigger)
604
- return;
605
- this.trigger.addEventListener("keydown", __privateGet(this, _triggerKeyDownListener));
606
- const referenceEl = this.trigger;
607
- __privateSet(this, _autoPositionCleanup, autoUpdate(referenceEl, this, () => {
608
- computePosition(referenceEl, this, {
609
- placement: "bottom-start",
610
- middleware: [offset(8), flip()]
611
- }).then(({ x, y }) => {
612
- Object.assign(this.style, {
613
- left: `${x}px`,
614
- top: `${y}px`
615
- });
616
- });
617
- }));
865
+ this.trigger?.addEventListener("keydown", __privateGet(this, _triggerKeyDownListener));
618
866
  };
619
867
  _unregisterTriggerEvents = new WeakSet();
620
868
  unregisterTriggerEvents_fn = function() {
@@ -622,18 +870,30 @@ unregisterTriggerEvents_fn = function() {
622
870
  this.trigger?.removeEventListener("keydown", __privateGet(this, _triggerKeyDownListener));
623
871
  (_a = __privateGet(this, _autoPositionCleanup)) == null ? void 0 : _a.call(this);
624
872
  };
625
- _triggerKeyDownListener = new WeakMap();
626
- _setOpen = new WeakSet();
627
- setOpen_fn = function(open) {
628
- this.open = open;
629
- this.dispatchEvent(
630
- new CustomEvent("gds-ui-state", {
631
- detail: { open },
632
- bubbles: true,
633
- composed: false
634
- })
635
- );
873
+ _autoPositionCleanup = new WeakMap();
874
+ _registerAutoPositioning = new WeakSet();
875
+ registerAutoPositioning_fn = function() {
876
+ const referenceEl = this.trigger;
877
+ const floatingEl = __privateGet(this, _dialogElementRef).value;
878
+ if (!referenceEl || !floatingEl)
879
+ return;
880
+ __privateSet(this, _autoPositionCleanup, autoUpdate(referenceEl, floatingEl, () => {
881
+ computePosition(referenceEl, floatingEl, {
882
+ placement: "bottom-start",
883
+ middleware: [offset(8), flip(), topLayerOverTransforms()],
884
+ strategy: "fixed"
885
+ }).then(
886
+ ({ x, y }) => Object.assign(floatingEl.style, {
887
+ left: `${x}px`,
888
+ top: `${y}px`,
889
+ minWidth: `${referenceEl.offsetWidth}px`
890
+ })
891
+ );
892
+ }));
636
893
  };
894
+ _triggerKeyDownListener = new WeakMap();
895
+ _focusFirstSlottedChild = new WeakMap();
896
+ _clickOutsideListener = new WeakMap();
637
897
  GdsPopover.styles = unsafeCSS3(popover_styles_default);
638
898
  __decorateClass([
639
899
  property3({ type: Boolean, reflect: true })
@@ -641,12 +901,18 @@ __decorateClass([
641
901
  __decorateClass([
642
902
  property3()
643
903
  ], GdsPopover.prototype, "trigger", 2);
904
+ __decorateClass([
905
+ property3()
906
+ ], GdsPopover.prototype, "label", 2);
644
907
  __decorateClass([
645
908
  watch("trigger")
646
909
  ], GdsPopover.prototype, "_handleTriggerChanged", 1);
647
910
  __decorateClass([
648
911
  watch("open")
649
- ], GdsPopover.prototype, "_updateHidden", 1);
912
+ ], GdsPopover.prototype, "_handleOpenChange", 1);
913
+ __decorateClass([
914
+ watchMediaQuery("(max-width: 576px)")
915
+ ], GdsPopover.prototype, "_handleMobileLayout", 1);
650
916
  GdsPopover = __decorateClass([
651
917
  gdsCustomElement("gds-popover")
652
918
  ], GdsPopover);
@@ -654,52 +920,54 @@ GdsPopover = __decorateClass([
654
920
  // libs/core/src/components/form-control.ts
655
921
  import { LitElement as LitElement4 } from "lit";
656
922
  import { property as property4 } from "lit/decorators.js";
657
- var _internals, _handleFormReset;
658
923
  var GdsFormControlElement = class extends LitElement4 {
659
924
  constructor() {
660
925
  super();
661
- __privateAdd(this, _internals, void 0);
662
926
  this.invalid = false;
663
927
  this.name = "";
664
928
  /**
665
929
  * Event handler for the form reset event.
666
930
  */
667
- __privateAdd(this, _handleFormReset, () => {
931
+ this.#handleFormReset = () => {
668
932
  this.value = void 0;
669
- });
670
- __privateSet(this, _internals, this.attachInternals());
933
+ };
934
+ this.#internals = this.attachInternals();
935
+ }
936
+ #internals;
937
+ static {
938
+ this.formAssociated = true;
671
939
  }
672
940
  get form() {
673
- return __privateGet(this, _internals).form;
941
+ return this.#internals.form;
674
942
  }
675
943
  get type() {
676
944
  return getUnscopedTagName(this.localName) || "gds-form-control";
677
945
  }
678
946
  get validity() {
679
- return __privateGet(this, _internals).validity;
947
+ return this.#internals.validity;
680
948
  }
681
949
  get validationMessage() {
682
- return __privateGet(this, _internals).validationMessage;
950
+ return this.#internals.validationMessage;
683
951
  }
684
952
  get willValidate() {
685
- return __privateGet(this, _internals).willValidate;
953
+ return this.#internals.willValidate;
686
954
  }
687
955
  checkValidity() {
688
- return __privateGet(this, _internals).checkValidity();
956
+ return this.#internals.checkValidity();
689
957
  }
690
958
  reportValidity() {
691
- return __privateGet(this, _internals).reportValidity();
959
+ return this.#internals.reportValidity();
692
960
  }
693
961
  connectedCallback() {
694
962
  super.connectedCallback();
695
- __privateGet(this, _internals).form?.addEventListener("reset", __privateGet(this, _handleFormReset));
963
+ this.#internals.form?.addEventListener("reset", this.#handleFormReset);
696
964
  }
697
965
  disconnectedCallback() {
698
966
  super.disconnectedCallback();
699
- __privateGet(this, _internals).form?.removeEventListener("reset", __privateGet(this, _handleFormReset));
967
+ this.#internals.form?.removeEventListener("reset", this.#handleFormReset);
700
968
  }
701
969
  __handleValidityChange() {
702
- __privateGet(this, _internals).setValidity(
970
+ this.#internals.setValidity(
703
971
  {
704
972
  badInput: false,
705
973
  customError: this.invalid,
@@ -716,12 +984,10 @@ var GdsFormControlElement = class extends LitElement4 {
716
984
  );
717
985
  }
718
986
  __handleValueChange() {
719
- __privateGet(this, _internals).setFormValue(this.value);
987
+ this.#internals.setFormValue(this.value);
720
988
  }
989
+ #handleFormReset;
721
990
  };
722
- _internals = new WeakMap();
723
- _handleFormReset = new WeakMap();
724
- GdsFormControlElement.formAssociated = true;
725
991
  __decorateClass([
726
992
  property4({
727
993
  type: Boolean,
@@ -763,7 +1029,7 @@ var style4 = css4`
763
1029
  var dropdown_styles_default = style4;
764
1030
 
765
1031
  // libs/core/src/components/dropdown/dropdown.ts
766
- var _listboxRef, _triggerRef, _searchInputRef, _optionElements, _listboxId, _triggerId, _handleSearchFieldKeyUp, _handleSearchFieldKeyDown, _handleOptionFocusChange, _registerPopoverTrigger, registerPopoverTrigger_fn, _handleSelectionChange, handleSelectionChange_fn, _registerAutoCloseListener, registerAutoCloseListener_fn, _unregisterAutoCloseListener, unregisterAutoCloseListener_fn, _autoCloseListener;
1032
+ var _listboxRef, _triggerRef, _searchInputRef, _optionElements, _listboxId, _triggerId, _handleSearchFieldKeyUp, _handleSearchFieldKeyDown, _handleListboxKeyDown, _handleOptionFocusChange, _registerPopoverTrigger, registerPopoverTrigger_fn, _handleSelectionChange, handleSelectionChange_fn, _registerAutoCloseListener, registerAutoCloseListener_fn, _unregisterAutoCloseListener, unregisterAutoCloseListener_fn, _blurCloseListener, _tabCloseListener;
767
1033
  var GdsDropdown = class extends GdsFormControlElement {
768
1034
  constructor() {
769
1035
  super();
@@ -785,10 +1051,12 @@ var GdsDropdown = class extends GdsFormControlElement {
785
1051
  this.open = false;
786
1052
  this.searchable = false;
787
1053
  this.multiple = false;
1054
+ this.compareWith = (a, b) => a === b;
1055
+ this.searchFilter = (q, o) => o.innerHTML.toLowerCase().includes(q.toLowerCase());
788
1056
  // Private members
789
- __privateAdd(this, _listboxRef, createRef2());
790
- __privateAdd(this, _triggerRef, createRef2());
791
- __privateAdd(this, _searchInputRef, createRef2());
1057
+ __privateAdd(this, _listboxRef, createRef3());
1058
+ __privateAdd(this, _triggerRef, createRef3());
1059
+ __privateAdd(this, _searchInputRef, createRef3());
792
1060
  __privateAdd(this, _optionElements, void 0);
793
1061
  __privateAdd(this, _listboxId, randomId());
794
1062
  __privateAdd(this, _triggerId, randomId());
@@ -798,41 +1066,58 @@ var GdsDropdown = class extends GdsFormControlElement {
798
1066
  * @param e The keyboard event.
799
1067
  */
800
1068
  __privateAdd(this, _handleSearchFieldKeyUp, (e) => {
801
- const input = e.target;
1069
+ const input = __privateGet(this, _searchInputRef).value;
802
1070
  const options = Array.from(__privateGet(this, _optionElements));
803
1071
  options.forEach((o) => o.hidden = false);
804
1072
  if (!input.value)
805
1073
  return;
806
1074
  const filteredOptions = options.filter(
807
- (o) => !o.innerHTML.toLowerCase().includes(input.value.toLowerCase())
1075
+ (o) => !this.searchFilter(input.value, o)
808
1076
  );
809
1077
  filteredOptions.forEach((o) => o.hidden = true);
810
1078
  });
811
1079
  /**
812
- * Check for ArrowDown in the search field.
1080
+ * Check for ArrowDown or Tab in the search field.
813
1081
  * If found, focus should be moved to the listbox.
814
1082
  */
815
1083
  __privateAdd(this, _handleSearchFieldKeyDown, (e) => {
816
- if (e.key === "ArrowDown") {
1084
+ if (e.key === "ArrowDown" || e.key === "Tab") {
1085
+ e.preventDefault();
817
1086
  __privateGet(this, _listboxRef).value?.focus();
818
1087
  return;
819
1088
  }
820
1089
  });
1090
+ /**
1091
+ * Check for Tab in the listbox.
1092
+ * If found, focus should be moved to the search field.
1093
+ */
1094
+ __privateAdd(this, _handleListboxKeyDown, (e) => {
1095
+ if (e.key === "Tab" && this.searchable) {
1096
+ e.preventDefault();
1097
+ __privateGet(this, _searchInputRef).value?.focus();
1098
+ return;
1099
+ }
1100
+ });
821
1101
  __privateAdd(this, _handleOptionFocusChange, (e) => {
822
1102
  const triggerButton = __privateGet(this, _triggerRef).value;
823
1103
  if (triggerButton)
824
1104
  triggerButton.ariaActiveDescendantElement = e.target;
825
1105
  });
826
1106
  /**
827
- * A listener to close the dropdown when clicking outside of it,
828
- * or when any other element recieves a keyup event.
1107
+ * A listener to close the dropdown when any other element is focused.
829
1108
  */
830
- __privateAdd(this, _autoCloseListener, (e) => {
831
- const isClickOutside = e instanceof MouseEvent && e.target instanceof Node && !this.contains(e.target);
1109
+ __privateAdd(this, _blurCloseListener, (e) => {
832
1110
  const isFocusOutside = e instanceof FocusEvent && e.relatedTarget && !this.contains(e.relatedTarget);
833
- if (isClickOutside || isFocusOutside)
1111
+ if (isFocusOutside)
834
1112
  this.open = false;
835
1113
  });
1114
+ __privateAdd(this, _tabCloseListener, (e) => {
1115
+ if (e.key === "Tab" && !this.searchable) {
1116
+ e.preventDefault();
1117
+ this.open = false;
1118
+ __privateGet(this, _triggerRef).value?.focus();
1119
+ }
1120
+ });
836
1121
  constrainSlots(this);
837
1122
  updateWhenLocaleChanges(this);
838
1123
  __privateSet(this, _optionElements, this.getElementsByTagName(
@@ -897,7 +1182,7 @@ var GdsDropdown = class extends GdsFormControlElement {
897
1182
  aria-owns="${__privateGet(this, _listboxId)}"
898
1183
  aria-controls="${__privateGet(this, _listboxId)}"
899
1184
  aria-expanded="${this.open}"
900
- ${ref2(__privateGet(this, _triggerRef))}
1185
+ ${ref3(__privateGet(this, _triggerRef))}
901
1186
  >
902
1187
  <slot name="trigger">
903
1188
  <span>${unsafeHTML(this.displayValue)}</span>
@@ -907,9 +1192,10 @@ var GdsDropdown = class extends GdsFormControlElement {
907
1192
  <span class="form-info"><slot name="message"></slot></span>
908
1193
 
909
1194
  <gds-popover
1195
+ .label=${this.label}
910
1196
  .open=${this.open}
911
1197
  @gds-ui-state=${(e) => this.open = e.detail.open}
912
- ${ref2(__privateMethod(this, _registerPopoverTrigger, registerPopoverTrigger_fn))}
1198
+ ${ref3(__privateMethod(this, _registerPopoverTrigger, registerPopoverTrigger_fn))}
913
1199
  >
914
1200
  ${when2(
915
1201
  this.searchable,
@@ -917,7 +1203,7 @@ var GdsDropdown = class extends GdsFormControlElement {
917
1203
  type="text"
918
1204
  aria-label="${msg("Filter available options")}"
919
1205
  placeholder="${msg("Search")}"
920
- ${ref2(__privateGet(this, _searchInputRef))}
1206
+ ${ref3(__privateGet(this, _searchInputRef))}
921
1207
  @keydown=${__privateGet(this, _handleSearchFieldKeyDown)}
922
1208
  @keyup=${__privateGet(this, _handleSearchFieldKeyUp)}
923
1209
  />`
@@ -926,9 +1212,11 @@ var GdsDropdown = class extends GdsFormControlElement {
926
1212
  <gds-listbox
927
1213
  id="${__privateGet(this, _listboxId)}"
928
1214
  .multiple="${ifDefined(this.multiple)}"
929
- ${ref2(__privateGet(this, _listboxRef))}
1215
+ .compareWith="${this.compareWith}"
1216
+ ${ref3(__privateGet(this, _listboxRef))}
930
1217
  @change="${__privateMethod(this, _handleSelectionChange, handleSelectionChange_fn)}"
931
1218
  @gds-focus="${__privateGet(this, _handleOptionFocusChange)}"
1219
+ @keydown=${__privateGet(this, _handleListboxKeyDown)}
932
1220
  >
933
1221
  <slot gds-allow="gds-option"></slot>
934
1222
  </gds-listbox>
@@ -937,6 +1225,7 @@ var GdsDropdown = class extends GdsFormControlElement {
937
1225
  }
938
1226
  _handleLightDOMChange() {
939
1227
  this.requestUpdate();
1228
+ this._handleValueChange();
940
1229
  if (this.multiple)
941
1230
  return;
942
1231
  if (!this.value) {
@@ -960,12 +1249,12 @@ var GdsDropdown = class extends GdsFormControlElement {
960
1249
  }
961
1250
  _onOpenChange() {
962
1251
  const open = this.open;
1252
+ Array.from(__privateGet(this, _optionElements)).forEach((o) => o.hidden = !open);
963
1253
  if (open)
964
1254
  __privateMethod(this, _registerAutoCloseListener, registerAutoCloseListener_fn).call(this);
965
1255
  else {
966
1256
  __privateMethod(this, _unregisterAutoCloseListener, unregisterAutoCloseListener_fn).call(this);
967
1257
  __privateGet(this, _searchInputRef).value && (__privateGet(this, _searchInputRef).value.value = "");
968
- Array.from(__privateGet(this, _optionElements)).forEach((o) => o.hidden = false);
969
1258
  }
970
1259
  this.dispatchEvent(
971
1260
  new CustomEvent("gds-ui-state", {
@@ -984,6 +1273,7 @@ _listboxId = new WeakMap();
984
1273
  _triggerId = new WeakMap();
985
1274
  _handleSearchFieldKeyUp = new WeakMap();
986
1275
  _handleSearchFieldKeyDown = new WeakMap();
1276
+ _handleListboxKeyDown = new WeakMap();
987
1277
  _handleOptionFocusChange = new WeakMap();
988
1278
  _registerPopoverTrigger = new WeakSet();
989
1279
  registerPopoverTrigger_fn = function(el) {
@@ -1014,17 +1304,18 @@ handleSelectionChange_fn = function() {
1014
1304
  };
1015
1305
  _registerAutoCloseListener = new WeakSet();
1016
1306
  registerAutoCloseListener_fn = function() {
1017
- window.addEventListener("click", __privateGet(this, _autoCloseListener));
1018
- this.addEventListener("blur", __privateGet(this, _autoCloseListener));
1019
- this.addEventListener("gds-blur", __privateGet(this, _autoCloseListener));
1307
+ this.addEventListener("blur", __privateGet(this, _blurCloseListener));
1308
+ this.addEventListener("gds-blur", __privateGet(this, _blurCloseListener));
1309
+ this.addEventListener("keydown", __privateGet(this, _tabCloseListener));
1020
1310
  };
1021
1311
  _unregisterAutoCloseListener = new WeakSet();
1022
1312
  unregisterAutoCloseListener_fn = function() {
1023
- window.removeEventListener("click", __privateGet(this, _autoCloseListener));
1024
- this.removeEventListener("blur", __privateGet(this, _autoCloseListener));
1025
- this.removeEventListener("gds-blur", __privateGet(this, _autoCloseListener));
1313
+ this.removeEventListener("blur", __privateGet(this, _blurCloseListener));
1314
+ this.removeEventListener("gds-blur", __privateGet(this, _blurCloseListener));
1315
+ this.removeEventListener("keydown", __privateGet(this, _tabCloseListener));
1026
1316
  };
1027
- _autoCloseListener = new WeakMap();
1317
+ _blurCloseListener = new WeakMap();
1318
+ _tabCloseListener = new WeakMap();
1028
1319
  GdsDropdown.styles = dropdown_styles_default;
1029
1320
  GdsDropdown.shadowRootOptions = {
1030
1321
  mode: "open",
@@ -1042,6 +1333,12 @@ __decorateClass([
1042
1333
  __decorateClass([
1043
1334
  property5({ type: Boolean, reflect: true })
1044
1335
  ], GdsDropdown.prototype, "multiple", 2);
1336
+ __decorateClass([
1337
+ property5()
1338
+ ], GdsDropdown.prototype, "compareWith", 2);
1339
+ __decorateClass([
1340
+ property5()
1341
+ ], GdsDropdown.prototype, "searchFilter", 2);
1045
1342
  __decorateClass([
1046
1343
  observeLightDOM()
1047
1344
  ], GdsDropdown.prototype, "_handleLightDOMChange", 1);
@@ -1057,6 +1354,7 @@ GdsDropdown = __decorateClass([
1057
1354
  export {
1058
1355
  GdsDropdown,
1059
1356
  GdsOption,
1357
+ VER_SUFFIX,
1060
1358
  gdsCustomElement,
1061
1359
  getScopedTagName,
1062
1360
  getUnscopedTagName,