@patternfly/pfe-core 2.1.0 → 2.3.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.
@@ -32,8 +32,8 @@ export class RovingTabindexController {
32
32
  * next item after active item in array of focusable items
33
33
  */
34
34
  get nextItem() {
35
- return (__classPrivateFieldGet(this, _RovingTabindexController_instances, "a", _RovingTabindexController_activeIndex_get) < __classPrivateFieldGet(this, _RovingTabindexController_instances, "a", _RovingTabindexController_focusableItems_get).length - 1 ? __classPrivateFieldGet(this, _RovingTabindexController_instances, "a", _RovingTabindexController_focusableItems_get)[__classPrivateFieldGet(this, _RovingTabindexController_instances, "a", _RovingTabindexController_activeIndex_get) + 1]
36
- : this.firstItem);
35
+ return (__classPrivateFieldGet(this, _RovingTabindexController_instances, "a", _RovingTabindexController_activeIndex_get) >= __classPrivateFieldGet(this, _RovingTabindexController_instances, "a", _RovingTabindexController_focusableItems_get).length - 1 ? this.firstItem
36
+ : __classPrivateFieldGet(this, _RovingTabindexController_instances, "a", _RovingTabindexController_focusableItems_get)[__classPrivateFieldGet(this, _RovingTabindexController_instances, "a", _RovingTabindexController_activeIndex_get) + 1]);
37
37
  }
38
38
  /**
39
39
  * previous item after active item in array of focusable items
@@ -43,8 +43,8 @@ export class RovingTabindexController {
43
43
  : this.lastItem);
44
44
  }
45
45
  constructor(host) {
46
- this.host = host;
47
46
  _RovingTabindexController_instances.add(this);
47
+ this.host = host;
48
48
  /** active focusable element */
49
49
  _RovingTabindexController_activeItem.set(this, void 0);
50
50
  /** closest ancestor containing items */
@@ -136,6 +136,7 @@ export class RovingTabindexController {
136
136
  focusOnItem(item) {
137
137
  this.updateActiveItem(item || this.firstItem);
138
138
  __classPrivateFieldGet(this, _RovingTabindexController_activeItem, "f")?.focus();
139
+ this.host.requestUpdate();
139
140
  }
140
141
  /**
141
142
  * Focuses next focusable item
@@ -166,13 +167,13 @@ export class RovingTabindexController {
166
167
  }
167
168
  }
168
169
  /**
169
- * adds event listners to items container
170
+ * adds event listeners to items container
170
171
  */
171
172
  hostConnected() {
172
173
  __classPrivateFieldGet(this, _RovingTabindexController_itemsContainer, "f")?.addEventListener('keydown', __classPrivateFieldGet(this, _RovingTabindexController_onKeydown, "f"));
173
174
  }
174
175
  /**
175
- * removes event listners from items container
176
+ * removes event listeners from items container
176
177
  */
177
178
  hostDisconnected() {
178
179
  __classPrivateFieldGet(this, _RovingTabindexController_itemsContainer, "f")?.removeEventListener('keydown', __classPrivateFieldGet(this, _RovingTabindexController_onKeydown, "f"));
@@ -1 +1 @@
1
- {"version":3,"file":"roving-tabindex-controller.js","sourceRoot":"","sources":["roving-tabindex-controller.ts"],"names":[],"mappings":"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","sourcesContent":["import type { ReactiveController, ReactiveControllerHost } from 'lit';\n\nconst isFocusableElement = (el: Element): el is HTMLElement =>\n !!el &&\n !el.hasAttribute('disabled') &&\n !el.ariaHidden &&\n !el.hasAttribute('hidden');\n\n/**\n * Implements roving tabindex, as described in WAI-ARIA practices, [Managing Focus Within\n * Components Using a Roving\n * tabindex](https://www.w3.org/WAI/ARIA/apg/practices/keyboard-interface/#kbd_roving_tabindex)\n */\nexport class RovingTabindexController implements ReactiveController {\n /** active focusable element */\n #activeItem?: HTMLElement;\n\n /** closest ancestor containing items */\n #itemsContainer?: HTMLElement;\n\n /** array of all focusable elements */\n #items: HTMLElement[] = [];\n\n /**\n * finds focusable items from a group of items\n */\n get #focusableItems(): HTMLElement[] {\n return this.#items.filter(isFocusableElement);\n }\n\n /**\n * index of active item in array of focusable items\n */\n get #activeIndex(): number {\n return !!this.#focusableItems && !!this.activeItem ? this.#focusableItems.indexOf(this.activeItem) : -1;\n }\n\n /**\n * index of active item in array of items\n */\n get #itemIndex(): number {\n return this.activeItem ? this.#items.indexOf(this.activeItem) : -1;\n }\n\n /**\n * active item of array of items\n */\n get activeItem(): HTMLElement | undefined {\n return this.#activeItem;\n }\n\n /**\n * first item in array of focusable items\n */\n get firstItem(): HTMLElement | undefined {\n return this.#focusableItems[0];\n }\n\n /**\n * last item in array of focusable items\n */\n get lastItem(): HTMLElement | undefined {\n return this.#focusableItems.at(-1);\n }\n\n /**\n * next item after active item in array of focusable items\n */\n get nextItem(): HTMLElement | undefined {\n return (\n this.#activeIndex < this.#focusableItems.length - 1 ? this.#focusableItems[this.#activeIndex + 1]\n : this.firstItem\n );\n }\n\n /**\n * previous item after active item in array of focusable items\n */\n get prevItem(): HTMLElement | undefined {\n return (\n this.#activeIndex > 0 ? this.#focusableItems[this.#activeIndex - 1]\n : this.lastItem\n );\n }\n\n constructor(public host: ReactiveControllerHost & HTMLElement) {\n this.host.addController(this);\n }\n\n /**\n * handles keyboard navigation\n */\n #onKeydown = (event: KeyboardEvent) => {\n if (event.ctrlKey || event.altKey || event.metaKey || this.#focusableItems.length < 1) {\n return;\n }\n\n const item = this.activeItem;\n let shouldPreventDefault = false;\n const horizontalOnly =\n !item ? false\n : item.tagName === 'SELECT' ||\n item.getAttribute('role') === 'spinbutton';\n\n\n switch (event.key) {\n case 'ArrowLeft':\n this.focusOnItem(this.prevItem);\n shouldPreventDefault = true;\n break;\n case 'ArrowRight':\n this.focusOnItem(this.nextItem);\n shouldPreventDefault = true;\n break;\n case 'ArrowUp':\n if (horizontalOnly) {\n return;\n }\n this.focusOnItem(this.prevItem);\n shouldPreventDefault = true;\n break;\n case 'ArrowDown':\n if (horizontalOnly) {\n return;\n }\n this.focusOnItem(this.nextItem);\n shouldPreventDefault = true;\n break;\n case 'Home':\n this.focusOnItem(this.firstItem);\n shouldPreventDefault = true;\n break;\n case 'PageUp':\n if (horizontalOnly) {\n return;\n }\n this.focusOnItem(this.firstItem);\n shouldPreventDefault = true;\n break;\n case 'End':\n this.focusOnItem(this.lastItem);\n shouldPreventDefault = true;\n break;\n case 'PageDown':\n if (horizontalOnly) {\n return;\n }\n this.focusOnItem(this.lastItem);\n shouldPreventDefault = true;\n break;\n default:\n break;\n }\n\n if (shouldPreventDefault) {\n event.stopPropagation();\n event.preventDefault();\n }\n };\n\n /**\n * sets tabindex of item based on whether or not it is active\n */\n updateActiveItem(item?: HTMLElement):void {\n if (item) {\n if (!!this.#activeItem && item !== this.#activeItem) {\n this.#activeItem.tabIndex = -1;\n }\n item.tabIndex = 0;\n this.#activeItem = item;\n }\n }\n\n /**\n * focuses on an item and sets it as active\n */\n focusOnItem(item?: HTMLElement):void {\n this.updateActiveItem(item || this.firstItem);\n this.#activeItem?.focus();\n }\n\n /**\n * Focuses next focusable item\n */\n updateItems(items: HTMLElement[]) {\n const sequence = [...items.slice(this.#itemIndex), ...items.slice(0, this.#itemIndex)];\n const first = sequence.find(item => this.#focusableItems.includes(item));\n this.focusOnItem(first || this.firstItem);\n }\n\n /**\n * from array of HTML items, and sets active items\n */\n initItems(items: HTMLElement[], itemsContainer: HTMLElement = this.host) {\n this.#items = items ?? [];\n const focusableItems = this.#focusableItems;\n const [focusableItem] = focusableItems;\n this.#activeItem = focusableItem;\n for (const item of focusableItems) {\n item.tabIndex = this.#activeItem === item ? 0 : -1;\n }\n /**\n * removes listener on previous contained and applies it to new container\n */\n if (!this.#itemsContainer || itemsContainer !== this.#itemsContainer) {\n this.#itemsContainer?.removeEventListener('keydown', this.#onKeydown);\n this.#itemsContainer = itemsContainer;\n this.hostConnected();\n }\n }\n\n /**\n * adds event listners to items container\n */\n hostConnected() {\n this.#itemsContainer?.addEventListener('keydown', this.#onKeydown);\n }\n\n /**\n * removes event listners from items container\n */\n hostDisconnected() {\n this.#itemsContainer?.removeEventListener('keydown', this.#onKeydown);\n }\n}\n"]}
1
+ {"version":3,"file":"roving-tabindex-controller.js","sourceRoot":"","sources":["roving-tabindex-controller.ts"],"names":[],"mappings":";;AAEA,MAAM,kBAAkB,GAAG,CAAC,EAAW,EAAqB,EAAE,CAC5D,CAAC,CAAC,EAAE;IACJ,CAAC,EAAE,CAAC,YAAY,CAAC,UAAU,CAAC;IAC5B,CAAC,EAAE,CAAC,UAAU;IACd,CAAC,EAAE,CAAC,YAAY,CAAC,QAAQ,CAAC,CAAC;AAE7B;;;;GAIG;AACH,MAAM,OAAO,wBAAwB;IAiCnC;;OAEG;IACH,IAAI,UAAU;QACZ,OAAO,uBAAA,IAAI,4CAAY,CAAC;IAC1B,CAAC;IAED;;OAEG;IACH,IAAI,SAAS;QACX,OAAO,uBAAA,IAAI,yFAAgB,CAAC,CAAC,CAAC,CAAC;IACjC,CAAC;IAED;;OAEG;IACH,IAAI,QAAQ;QACV,OAAO,uBAAA,IAAI,yFAAgB,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;IACrC,CAAC;IAED;;OAEG;IACH,IAAI,QAAQ;QACV,OAAO,CACH,uBAAA,IAAI,sFAAa,IAAI,uBAAA,IAAI,yFAAgB,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,SAAS;YACvE,CAAC,CAAC,uBAAA,IAAI,yFAAgB,CAAC,uBAAA,IAAI,sFAAa,GAAG,CAAC,CAAC,CAC9C,CAAC;IACJ,CAAC;IAED;;OAEG;IACH,IAAI,QAAQ;QACV,OAAO,CACH,uBAAA,IAAI,sFAAa,GAAG,CAAC,CAAC,CAAC,CAAC,uBAAA,IAAI,yFAAgB,CAAC,uBAAA,IAAI,sFAAa,GAAG,CAAC,CAAC;YACrE,CAAC,CAAC,IAAI,CAAC,QAAQ,CAChB,CAAC;IACJ,CAAC;IAED,YAAmB,IAA0C;;QAA1C,SAAI,GAAJ,IAAI,CAAsC;QAvE7D,+BAA+B;QAC/B,uDAAuB;QAEvB,wCAAwC;QACxC,2DAA8B;QAE9B,sCAAsC;QACtC,0CAAqB,EAAE,EAAC;QAoExB;;WAEG;QACH,8CAAa,CAAC,KAAoB,EAAE,EAAE;YACpC,IAAI,KAAK,CAAC,OAAO,IAAI,KAAK,CAAC,MAAM,IAAI,KAAK,CAAC,OAAO,IAAI,uBAAA,IAAI,yFAAgB,CAAC,MAAM,GAAG,CAAC,EAAE;gBACrF,OAAO;aACR;YAED,MAAM,IAAI,GAAG,IAAI,CAAC,UAAU,CAAC;YAC7B,IAAI,oBAAoB,GAAG,KAAK,CAAC;YACjC,MAAM,cAAc,GAChB,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK;gBACf,CAAC,CAAC,IAAI,CAAC,OAAO,KAAK,QAAQ;oBACzB,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,KAAK,YAAY,CAAC;YAG/C,QAAQ,KAAK,CAAC,GAAG,EAAE;gBACjB,KAAK,WAAW;oBACd,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;oBAChC,oBAAoB,GAAG,IAAI,CAAC;oBAC5B,MAAM;gBACR,KAAK,YAAY;oBACf,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;oBAChC,oBAAoB,GAAG,IAAI,CAAC;oBAC5B,MAAM;gBACR,KAAK,SAAS;oBACZ,IAAI,cAAc,EAAE;wBAClB,OAAO;qBACR;oBACD,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;oBAChC,oBAAoB,GAAG,IAAI,CAAC;oBAC5B,MAAM;gBACR,KAAK,WAAW;oBACd,IAAI,cAAc,EAAE;wBAClB,OAAO;qBACR;oBACD,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;oBAChC,oBAAoB,GAAG,IAAI,CAAC;oBAC5B,MAAM;gBACR,KAAK,MAAM;oBACT,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;oBACjC,oBAAoB,GAAG,IAAI,CAAC;oBAC5B,MAAM;gBACR,KAAK,QAAQ;oBACX,IAAI,cAAc,EAAE;wBAClB,OAAO;qBACR;oBACD,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;oBACjC,oBAAoB,GAAG,IAAI,CAAC;oBAC5B,MAAM;gBACR,KAAK,KAAK;oBACR,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;oBAChC,oBAAoB,GAAG,IAAI,CAAC;oBAC5B,MAAM;gBACR,KAAK,UAAU;oBACb,IAAI,cAAc,EAAE;wBAClB,OAAO;qBACR;oBACD,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;oBAChC,oBAAoB,GAAG,IAAI,CAAC;oBAC5B,MAAM;gBACR;oBACE,MAAM;aACT;YAED,IAAI,oBAAoB,EAAE;gBACxB,KAAK,CAAC,eAAe,EAAE,CAAC;gBACxB,KAAK,CAAC,cAAc,EAAE,CAAC;aACxB;QACH,CAAC,EAAC;QAxEA,IAAI,CAAC,IAAI,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC;IAChC,CAAC;IAyED;;OAEG;IACH,gBAAgB,CAAC,IAAe;QAC9B,IAAI,IAAI,EAAE;YACR,IAAI,CAAC,CAAC,uBAAA,IAAI,4CAAY,IAAI,IAAI,KAAK,uBAAA,IAAI,4CAAY,EAAE;gBACnD,uBAAA,IAAI,4CAAY,CAAC,QAAQ,GAAG,CAAC,CAAC,CAAC;aAChC;YACD,IAAI,CAAC,QAAQ,GAAG,CAAC,CAAC;YAClB,uBAAA,IAAI,wCAAe,IAAI,MAAA,CAAC;SACzB;IACH,CAAC;IAED;;OAEG;IACH,WAAW,CAAC,IAAe;QACzB,IAAI,CAAC,gBAAgB,CAAC,IAAI,IAAI,IAAI,CAAC,SAAS,CAAC,CAAC;QAC9C,uBAAA,IAAI,4CAAY,EAAE,KAAK,EAAE,CAAC;QAC1B,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,CAAC;IAC5B,CAAC;IAED;;OAEG;IACH,WAAW,CAAC,KAAiB;QAC3B,MAAM,QAAQ,GAAG,CAAC,GAAG,KAAK,CAAC,KAAK,CAAC,uBAAA,IAAI,oFAAW,CAAC,EAAE,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,uBAAA,IAAI,oFAAW,CAAC,CAAC,CAAC;QACvF,MAAM,KAAK,GAAG,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,uBAAA,IAAI,yFAAgB,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC;QACzE,IAAI,CAAC,WAAW,CAAC,KAAK,IAAI,IAAI,CAAC,SAAS,CAAC,CAAC;IAC5C,CAAC;IAED;;OAEG;IACH,SAAS,CAAC,KAAiB,EAAE,iBAA8B,IAAI,CAAC,IAAI;QAClE,uBAAA,IAAI,mCAAU,KAAK,IAAI,EAAE,MAAA,CAAC;QAC1B,MAAM,cAAc,GAAG,uBAAA,IAAI,yFAAgB,CAAC;QAC5C,MAAM,CAAC,aAAa,CAAC,GAAG,cAAc,CAAC;QACvC,uBAAA,IAAI,wCAAe,aAAa,MAAA,CAAC;QACjC,KAAK,MAAM,IAAI,IAAI,cAAc,EAAE;YACjC,IAAI,CAAC,QAAQ,GAAG,uBAAA,IAAI,4CAAY,KAAK,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;SACpD;QACD;;WAEG;QACH,IAAI,CAAC,uBAAA,IAAI,gDAAgB,IAAI,cAAc,KAAK,uBAAA,IAAI,gDAAgB,EAAE;YACpE,uBAAA,IAAI,gDAAgB,EAAE,mBAAmB,CAAC,SAAS,EAAE,uBAAA,IAAI,2CAAW,CAAC,CAAC;YACtE,uBAAA,IAAI,4CAAmB,cAAc,MAAA,CAAC;YACtC,IAAI,CAAC,aAAa,EAAE,CAAC;SACtB;IACH,CAAC;IAED;;OAEG;IACH,aAAa;QACX,uBAAA,IAAI,gDAAgB,EAAE,gBAAgB,CAAC,SAAS,EAAE,uBAAA,IAAI,2CAAW,CAAC,CAAC;IACrE,CAAC;IAED;;OAEG;IACH,gBAAgB;QACd,uBAAA,IAAI,gDAAgB,EAAE,mBAAmB,CAAC,SAAS,EAAE,uBAAA,IAAI,2CAAW,CAAC,CAAC;IACxE,CAAC;CACF;;IAtMG,OAAO,uBAAA,IAAI,uCAAO,CAAC,MAAM,CAAC,kBAAkB,CAAC,CAAC;AAChD,CAAC;IAMC,OAAO,CAAC,CAAC,uBAAA,IAAI,yFAAgB,IAAI,CAAC,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,uBAAA,IAAI,yFAAgB,CAAC,OAAO,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;AAC1G,CAAC;IAMC,OAAO,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,uBAAA,IAAI,uCAAO,CAAC,OAAO,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;AACrE,CAAC","sourcesContent":["import type { ReactiveController, ReactiveControllerHost } from 'lit';\n\nconst isFocusableElement = (el: Element): el is HTMLElement =>\n !!el &&\n !el.hasAttribute('disabled') &&\n !el.ariaHidden &&\n !el.hasAttribute('hidden');\n\n/**\n * Implements roving tabindex, as described in WAI-ARIA practices, [Managing Focus Within\n * Components Using a Roving\n * tabindex](https://www.w3.org/WAI/ARIA/apg/practices/keyboard-interface/#kbd_roving_tabindex)\n */\nexport class RovingTabindexController<\n ItemType extends HTMLElement = HTMLElement,\n> implements ReactiveController {\n /** active focusable element */\n #activeItem?: ItemType;\n\n /** closest ancestor containing items */\n #itemsContainer?: HTMLElement;\n\n /** array of all focusable elements */\n #items: ItemType[] = [];\n\n /**\n * finds focusable items from a group of items\n */\n get #focusableItems(): ItemType[] {\n return this.#items.filter(isFocusableElement);\n }\n\n /**\n * index of active item in array of focusable items\n */\n get #activeIndex(): number {\n return !!this.#focusableItems && !!this.activeItem ? this.#focusableItems.indexOf(this.activeItem) : -1;\n }\n\n /**\n * index of active item in array of items\n */\n get #itemIndex(): number {\n return this.activeItem ? this.#items.indexOf(this.activeItem) : -1;\n }\n\n /**\n * active item of array of items\n */\n get activeItem(): ItemType | undefined {\n return this.#activeItem;\n }\n\n /**\n * first item in array of focusable items\n */\n get firstItem(): ItemType | undefined {\n return this.#focusableItems[0];\n }\n\n /**\n * last item in array of focusable items\n */\n get lastItem(): ItemType | undefined {\n return this.#focusableItems.at(-1);\n }\n\n /**\n * next item after active item in array of focusable items\n */\n get nextItem(): ItemType | undefined {\n return (\n this.#activeIndex >= this.#focusableItems.length - 1 ? this.firstItem\n : this.#focusableItems[this.#activeIndex + 1]\n );\n }\n\n /**\n * previous item after active item in array of focusable items\n */\n get prevItem(): ItemType | undefined {\n return (\n this.#activeIndex > 0 ? this.#focusableItems[this.#activeIndex - 1]\n : this.lastItem\n );\n }\n\n constructor(public host: ReactiveControllerHost & HTMLElement) {\n this.host.addController(this);\n }\n\n /**\n * handles keyboard navigation\n */\n #onKeydown = (event: KeyboardEvent) => {\n if (event.ctrlKey || event.altKey || event.metaKey || this.#focusableItems.length < 1) {\n return;\n }\n\n const item = this.activeItem;\n let shouldPreventDefault = false;\n const horizontalOnly =\n !item ? false\n : item.tagName === 'SELECT' ||\n item.getAttribute('role') === 'spinbutton';\n\n\n switch (event.key) {\n case 'ArrowLeft':\n this.focusOnItem(this.prevItem);\n shouldPreventDefault = true;\n break;\n case 'ArrowRight':\n this.focusOnItem(this.nextItem);\n shouldPreventDefault = true;\n break;\n case 'ArrowUp':\n if (horizontalOnly) {\n return;\n }\n this.focusOnItem(this.prevItem);\n shouldPreventDefault = true;\n break;\n case 'ArrowDown':\n if (horizontalOnly) {\n return;\n }\n this.focusOnItem(this.nextItem);\n shouldPreventDefault = true;\n break;\n case 'Home':\n this.focusOnItem(this.firstItem);\n shouldPreventDefault = true;\n break;\n case 'PageUp':\n if (horizontalOnly) {\n return;\n }\n this.focusOnItem(this.firstItem);\n shouldPreventDefault = true;\n break;\n case 'End':\n this.focusOnItem(this.lastItem);\n shouldPreventDefault = true;\n break;\n case 'PageDown':\n if (horizontalOnly) {\n return;\n }\n this.focusOnItem(this.lastItem);\n shouldPreventDefault = true;\n break;\n default:\n break;\n }\n\n if (shouldPreventDefault) {\n event.stopPropagation();\n event.preventDefault();\n }\n };\n\n /**\n * sets tabindex of item based on whether or not it is active\n */\n updateActiveItem(item?: ItemType): void {\n if (item) {\n if (!!this.#activeItem && item !== this.#activeItem) {\n this.#activeItem.tabIndex = -1;\n }\n item.tabIndex = 0;\n this.#activeItem = item;\n }\n }\n\n /**\n * focuses on an item and sets it as active\n */\n focusOnItem(item?: ItemType): void {\n this.updateActiveItem(item || this.firstItem);\n this.#activeItem?.focus();\n this.host.requestUpdate();\n }\n\n /**\n * Focuses next focusable item\n */\n updateItems(items: ItemType[]) {\n const sequence = [...items.slice(this.#itemIndex), ...items.slice(0, this.#itemIndex)];\n const first = sequence.find(item => this.#focusableItems.includes(item));\n this.focusOnItem(first || this.firstItem);\n }\n\n /**\n * from array of HTML items, and sets active items\n */\n initItems(items: ItemType[], itemsContainer: HTMLElement = this.host) {\n this.#items = items ?? [];\n const focusableItems = this.#focusableItems;\n const [focusableItem] = focusableItems;\n this.#activeItem = focusableItem;\n for (const item of focusableItems) {\n item.tabIndex = this.#activeItem === item ? 0 : -1;\n }\n /**\n * removes listener on previous contained and applies it to new container\n */\n if (!this.#itemsContainer || itemsContainer !== this.#itemsContainer) {\n this.#itemsContainer?.removeEventListener('keydown', this.#onKeydown);\n this.#itemsContainer = itemsContainer;\n this.hostConnected();\n }\n }\n\n /**\n * adds event listeners to items container\n */\n hostConnected() {\n this.#itemsContainer?.addEventListener('keydown', this.#onKeydown);\n }\n\n /**\n * removes event listeners from items container\n */\n hostDisconnected() {\n this.#itemsContainer?.removeEventListener('keydown', this.#onKeydown);\n }\n}\n"]}
@@ -26,8 +26,8 @@ export class ScrollSpyController {
26
26
  __classPrivateFieldGet(this, _ScrollSpyController_instances, "m", _ScrollSpyController_initIo).call(this);
27
27
  }
28
28
  constructor(host, options) {
29
- this.host = host;
30
29
  _ScrollSpyController_instances.add(this);
30
+ this.host = host;
31
31
  _ScrollSpyController_tagNames.set(this, void 0);
32
32
  _ScrollSpyController_activeAttribute.set(this, void 0);
33
33
  _ScrollSpyController_io.set(this, void 0);
@@ -1 +1 @@
1
- {"version":3,"file":"scroll-spy-controller.js","sourceRoot":"","sources":["scroll-spy-controller.ts"],"names":[],"mappings":"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","sourcesContent":["import type { ReactiveController, ReactiveControllerHost } from 'lit';\n\nexport interface ScrollSpyControllerOptions extends IntersectionObserverInit {\n /**\n * Tag names of legal link children.\n * Legal children must have an `href` property/attribute pair, like `<a>`.\n */\n tagNames: string[];\n\n /**\n * Attribute to set on the active link element.\n * @default 'active'\n */\n activeAttribute?: string;\n\n /**\n * The root node to query content for\n * @default the host's root node\n */\n rootNode?: Node;\n /**\n * function to call on link children to get their URL hash (i.e. id to scroll to)\n * @default el => el.getAttribute('href');\n */\n getHash?: (el: Element) => string|null;\n}\n\nexport class ScrollSpyController implements ReactiveController {\n #tagNames: string[];\n #activeAttribute: string;\n\n #io?: IntersectionObserver;\n\n /** Which link's targets have already scrolled past? */\n #passedLinks = new Set<Element>();\n\n /** Ignore intersections? */\n #force = false;\n\n /** Has the intersection observer found an element? */\n #intersected = false;\n\n #root: ScrollSpyControllerOptions['root'];\n #rootMargin?: string;\n #threshold: number|number[];\n\n #rootNode: Node;\n #getHash: (el: Element) => string|null;\n\n get #linkChildren(): Element[] {\n return Array.from(this.host.querySelectorAll(this.#tagNames.join(',')))\n .filter(this.#getHash);\n }\n\n get root() {\n return this.#root;\n }\n\n set root(v) {\n this.#root = v;\n this.#io?.disconnect();\n this.#initIo();\n }\n\n get rootMargin() {\n return this.#rootMargin;\n }\n\n set rootMargin(v) {\n this.#rootMargin = v;\n this.#io?.disconnect();\n this.#initIo();\n }\n\n get threshold() {\n return this.#threshold;\n }\n\n set threshold(v) {\n this.#threshold = v;\n this.#io?.disconnect();\n this.#initIo();\n }\n\n constructor(\n private host: ReactiveControllerHost & HTMLElement,\n options: ScrollSpyControllerOptions,\n ) {\n host.addController(this);\n this.#tagNames = options.tagNames;\n this.#root = options.root;\n this.#rootMargin = options.rootMargin;\n this.#activeAttribute = options.activeAttribute ?? 'active';\n this.#threshold = options.threshold ?? 0.85;\n this.#rootNode = options.rootNode ?? host.getRootNode();\n this.#getHash = options?.getHash ?? ((el: Element) => el.getAttribute('href'));\n }\n\n hostConnected() {\n this.#initIo();\n }\n\n #initIo() {\n const rootNode = this.#rootNode;\n if (rootNode instanceof Document || rootNode instanceof ShadowRoot) {\n const { rootMargin, threshold, root } = this;\n this.#io = new IntersectionObserver(r => this.#onIo(r), { root, rootMargin, threshold });\n this.#linkChildren\n .map(x => this.#getHash(x))\n .filter((x): x is string => !!x)\n .map(x => rootNode.getElementById(x.replace('#', '')))\n .filter((x): x is HTMLElement => !!x)\n .forEach(target => this.#io?.observe(target));\n }\n }\n\n #markPassed(link: Element, force: boolean) {\n if (force) {\n this.#passedLinks.add(link);\n } else {\n this.#passedLinks.delete(link);\n }\n }\n\n #setActive(link?: EventTarget|null) {\n for (const child of this.#linkChildren) {\n child.toggleAttribute(this.#activeAttribute, child === link);\n }\n }\n\n async #nextIntersection() {\n this.#intersected = false;\n // safeguard the loop\n setTimeout(() => this.#intersected = false, 3000);\n while (!this.#intersected) {\n await new Promise(requestAnimationFrame);\n }\n }\n\n async #onIo(entries: IntersectionObserverEntry[]) {\n if (!this.#force) {\n for (const { target, boundingClientRect, intersectionRect } of entries) {\n const selector = `:is(${this.#tagNames.join(',')})[href=\"#${target.id}\"]`;\n const link = this.host.querySelector(selector);\n if (link) {\n this.#markPassed(link, boundingClientRect.top < intersectionRect.top);\n }\n }\n const link = [...this.#passedLinks];\n const last = link.at(-1);\n this.#setActive(last ?? this.#linkChildren.at(0));\n }\n this.#intersected = true;\n }\n\n /** Explicitly set the active item */\n public async setActive(link: EventTarget|null) {\n this.#force = true;\n this.#setActive(link);\n let sawActive = false;\n for (const child of this.#linkChildren) {\n this.#markPassed(child, !sawActive);\n if (child === link) {\n sawActive = true;\n }\n }\n await this.#nextIntersection();\n this.#force = false;\n }\n}\n"]}
1
+ {"version":3,"file":"scroll-spy-controller.js","sourceRoot":"","sources":["scroll-spy-controller.ts"],"names":[],"mappings":"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","sourcesContent":["import type { ReactiveController, ReactiveControllerHost } from 'lit';\n\nexport interface ScrollSpyControllerOptions extends IntersectionObserverInit {\n /**\n * Tag names of legal link children.\n * Legal children must have an `href` property/attribute pair, like `<a>`.\n */\n tagNames: string[];\n\n /**\n * Attribute to set on the active link element.\n * @default 'active'\n */\n activeAttribute?: string;\n\n /**\n * The root node to query content for\n * @default the host's root node\n */\n rootNode?: Node;\n /**\n * function to call on link children to get their URL hash (i.e. id to scroll to)\n * @default el => el.getAttribute('href');\n */\n getHash?: (el: Element) => string | null;\n}\n\nexport class ScrollSpyController implements ReactiveController {\n #tagNames: string[];\n #activeAttribute: string;\n\n #io?: IntersectionObserver;\n\n /** Which link's targets have already scrolled past? */\n #passedLinks = new Set<Element>();\n\n /** Ignore intersections? */\n #force = false;\n\n /** Has the intersection observer found an element? */\n #intersected = false;\n\n #root: ScrollSpyControllerOptions['root'];\n #rootMargin?: string;\n #threshold: number | number[];\n\n #rootNode: Node;\n #getHash: (el: Element) => string | null;\n\n get #linkChildren(): Element[] {\n return Array.from(this.host.querySelectorAll(this.#tagNames.join(',')))\n .filter(this.#getHash);\n }\n\n get root() {\n return this.#root;\n }\n\n set root(v) {\n this.#root = v;\n this.#io?.disconnect();\n this.#initIo();\n }\n\n get rootMargin() {\n return this.#rootMargin;\n }\n\n set rootMargin(v) {\n this.#rootMargin = v;\n this.#io?.disconnect();\n this.#initIo();\n }\n\n get threshold() {\n return this.#threshold;\n }\n\n set threshold(v) {\n this.#threshold = v;\n this.#io?.disconnect();\n this.#initIo();\n }\n\n constructor(\n private host: ReactiveControllerHost & HTMLElement,\n options: ScrollSpyControllerOptions,\n ) {\n host.addController(this);\n this.#tagNames = options.tagNames;\n this.#root = options.root;\n this.#rootMargin = options.rootMargin;\n this.#activeAttribute = options.activeAttribute ?? 'active';\n this.#threshold = options.threshold ?? 0.85;\n this.#rootNode = options.rootNode ?? host.getRootNode();\n this.#getHash = options?.getHash ?? ((el: Element) => el.getAttribute('href'));\n }\n\n hostConnected() {\n this.#initIo();\n }\n\n #initIo() {\n const rootNode = this.#rootNode;\n if (rootNode instanceof Document || rootNode instanceof ShadowRoot) {\n const { rootMargin, threshold, root } = this;\n this.#io = new IntersectionObserver(r => this.#onIo(r), { root, rootMargin, threshold });\n this.#linkChildren\n .map(x => this.#getHash(x))\n .filter((x): x is string => !!x)\n .map(x => rootNode.getElementById(x.replace('#', '')))\n .filter((x): x is HTMLElement => !!x)\n .forEach(target => this.#io?.observe(target));\n }\n }\n\n #markPassed(link: Element, force: boolean) {\n if (force) {\n this.#passedLinks.add(link);\n } else {\n this.#passedLinks.delete(link);\n }\n }\n\n #setActive(link?: EventTarget | null) {\n for (const child of this.#linkChildren) {\n child.toggleAttribute(this.#activeAttribute, child === link);\n }\n }\n\n async #nextIntersection() {\n this.#intersected = false;\n // safeguard the loop\n setTimeout(() => this.#intersected = false, 3000);\n while (!this.#intersected) {\n await new Promise(requestAnimationFrame);\n }\n }\n\n async #onIo(entries: IntersectionObserverEntry[]) {\n if (!this.#force) {\n for (const { target, boundingClientRect, intersectionRect } of entries) {\n const selector = `:is(${this.#tagNames.join(',')})[href=\"#${target.id}\"]`;\n const link = this.host.querySelector(selector);\n if (link) {\n this.#markPassed(link, boundingClientRect.top < intersectionRect.top);\n }\n }\n const link = [...this.#passedLinks];\n const last = link.at(-1);\n this.#setActive(last ?? this.#linkChildren.at(0));\n }\n this.#intersected = true;\n }\n\n /** Explicitly set the active item */\n public async setActive(link: EventTarget | null) {\n this.#force = true;\n this.#setActive(link);\n let sawActive = false;\n for (const child of this.#linkChildren) {\n this.#markPassed(child, !sawActive);\n if (child === link) {\n sawActive = true;\n }\n }\n await this.#nextIntersection();\n this.#force = false;\n }\n}\n"]}
@@ -10,7 +10,7 @@ function isObjectConfigSpread(config) {
10
10
  */
11
11
  const isSlot = (n) => (child) => n === SlotController.anonymous ? !child.hasAttribute('slot')
12
12
  : child.getAttribute('slot') === n;
13
- export class SlotController {
13
+ class SlotController {
14
14
  constructor(host, ...config) {
15
15
  this.host = host;
16
16
  this.nodes = new Map();
@@ -145,4 +145,5 @@ __decorate([
145
145
  __decorate([
146
146
  bound
147
147
  ], SlotController.prototype, "init", null);
148
+ export { SlotController };
148
149
  //# sourceMappingURL=slot-controller.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"slot-controller.js","sourceRoot":"","sources":["slot-controller.ts"],"names":[],"mappings":"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","sourcesContent":["import type { ReactiveController, ReactiveElement } from 'lit';\n\nimport { bound } from '../decorators/bound.js';\nimport { Logger } from './logger.js';\n\ninterface AnonymousSlot {\n hasContent: boolean;\n elements: Element[];\n slot: HTMLSlotElement|null;\n}\n\ninterface NamedSlot extends AnonymousSlot {\n name: string;\n initialized: true;\n}\n\nexport type Slot = NamedSlot|AnonymousSlot;\n\nexport interface SlotsConfig {\n slots: (string|null)[];\n /**\n * Object mapping new slot name keys to deprecated slot name values\n * @example `pf-modal--header` is deprecated in favour of `header`\n * ```js\n * new SlotController(this, {\n * slots: ['header'],\n * deprecations: {\n * 'header': 'pf-modal--header'\n * }\n * })\n * ```\n */\n deprecations?: Record<string, string>;\n}\n\nfunction isObjectConfigSpread(config: ([SlotsConfig]|(string|null)[])): config is [SlotsConfig] {\n return config.length === 1 && typeof config[0] === 'object' && config[0] !== null;\n}\n\n/**\n * If it's a named slot, return its children,\n * for the default slot, look for direct children not assigned to a slot\n */\nconst isSlot =\n <T extends Element = Element>(n: string|typeof SlotController.anonymous) =>\n (child: Element): child is T =>\n n === SlotController.anonymous ? !child.hasAttribute('slot')\n : child.getAttribute('slot') === n;\n\nexport class SlotController implements ReactiveController {\n public static anonymous = Symbol('anonymous slot');\n\n private nodes = new Map<string|typeof SlotController.anonymous, Slot>();\n\n private logger: Logger;\n\n private firstUpdated = false;\n\n private mo = new MutationObserver(this.onMutation);\n\n private slotNames: (string|null)[];\n\n private deprecations: Record<string, string> = {};\n\n constructor(public host: ReactiveElement, ...config: ([SlotsConfig]|(string|null)[])) {\n this.logger = new Logger(this.host);\n\n if (isObjectConfigSpread(config)) {\n const [{ slots, deprecations }] = config;\n this.slotNames = slots;\n this.deprecations = deprecations ?? {};\n } else if (config.length >= 1) {\n this.slotNames = config;\n this.deprecations = {};\n } else {\n this.slotNames = [null];\n }\n\n\n host.addController(this);\n }\n\n hostConnected() {\n this.host.addEventListener('slotchange', this.onSlotChange as EventListener);\n this.firstUpdated = false;\n this.mo.observe(this.host, { childList: true });\n this.init();\n }\n\n hostUpdated() {\n if (!this.firstUpdated) {\n this.slotNames.forEach(this.initSlot);\n this.firstUpdated = true;\n }\n }\n\n hostDisconnected() {\n this.mo.disconnect();\n }\n\n /**\n * Returns a boolean statement of whether or not any of those slots exists in the light DOM.\n *\n * @param {String|Array} name The slot name.\n * @example this.hasSlotted(\"header\");\n */\n hasSlotted(...names: string[]): boolean {\n if (!names.length) {\n this.logger.warn(`Please provide at least one slot name for which to search.`);\n return false;\n } else {\n return names.some(x =>\n this.nodes.get(x)?.hasContent ?? false);\n }\n }\n\n /**\n * Given a slot name or slot names, returns elements assigned to the requested slots as an array.\n * If no value is provided, it returns all children not assigned to a slot (without a slot attribute).\n *\n * @example Get header-slotted elements\n * ```js\n * this.getSlotted('header')\n * ```\n *\n * @example Get header- and footer-slotted elements\n * ```js\n * this.getSlotted('header', 'footer')\n * ```\n *\n * @example Get default-slotted elements\n * ```js\n * this.getSlotted();\n * ```\n */\n getSlotted<T extends Element = Element>(...slotNames: string[]): T[] {\n if (!slotNames.length) {\n return (this.nodes.get(SlotController.anonymous)?.elements ?? []) as T[];\n } else {\n return slotNames.flatMap(slotName =>\n this.nodes.get(slotName)?.elements ?? []) as T[];\n }\n }\n\n @bound private onSlotChange(event: Event & { target: HTMLSlotElement }) {\n const slotName = event.target.name;\n this.initSlot(slotName);\n this.host.requestUpdate();\n }\n\n @bound private async onMutation(records: MutationRecord[]) {\n const changed = [];\n for (const { addedNodes, removedNodes } of records) {\n for (const node of [...addedNodes, ...removedNodes]) {\n if (node instanceof HTMLElement && node.slot) {\n this.initSlot(node.slot);\n changed.push(node.slot);\n }\n }\n }\n if (changed.length) {\n this.host.requestUpdate();\n }\n }\n\n private getChildrenForSlot<T extends Element = Element>(name: string|typeof SlotController.anonymous): T[] {\n const children = Array.from(this.host.children) as T[];\n return children.filter(isSlot(name));\n }\n\n @bound private initSlot(slotName: string|null) {\n const name = slotName || SlotController.anonymous;\n const elements = this.nodes.get(name)?.slot?.assignedElements?.() ?? this.getChildrenForSlot(name);\n const selector = slotName ? `slot[name=\"${slotName}\"]` : 'slot:not([name])';\n const slot = this.host.shadowRoot?.querySelector?.<HTMLSlotElement>(selector) ?? null;\n const hasContent = !!elements.length;\n this.nodes.set(name, { elements, name: slotName ?? '', hasContent, slot });\n this.logger.log(slotName, hasContent);\n }\n\n /**\n * Maps the defined slots into an object that is easier to query\n */\n @bound private init() {\n this.nodes.clear();\n // Loop over the properties provided by the schema\n this.slotNames.forEach(this.initSlot);\n Object.values(this.deprecations).forEach(this.initSlot);\n this.host.requestUpdate();\n }\n}\n"]}
1
+ {"version":3,"file":"slot-controller.js","sourceRoot":"","sources":["slot-controller.ts"],"names":[],"mappings":"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","sourcesContent":["import type { ReactiveController, ReactiveElement } from 'lit';\n\nimport { bound } from '../decorators/bound.js';\nimport { Logger } from './logger.js';\n\ninterface AnonymousSlot {\n hasContent: boolean;\n elements: Element[];\n slot: HTMLSlotElement | null;\n}\n\ninterface NamedSlot extends AnonymousSlot {\n name: string;\n initialized: true;\n}\n\nexport type Slot = NamedSlot | AnonymousSlot;\n\nexport interface SlotsConfig {\n slots: (string | null)[];\n /**\n * Object mapping new slot name keys to deprecated slot name values\n * @example `pf-modal--header` is deprecated in favour of `header`\n * ```js\n * new SlotController(this, {\n * slots: ['header'],\n * deprecations: {\n * 'header': 'pf-modal--header'\n * }\n * })\n * ```\n */\n deprecations?: Record<string, string>;\n}\n\nfunction isObjectConfigSpread(config: ([SlotsConfig] | (string | null)[])): config is [SlotsConfig] {\n return config.length === 1 && typeof config[0] === 'object' && config[0] !== null;\n}\n\n/**\n * If it's a named slot, return its children,\n * for the default slot, look for direct children not assigned to a slot\n */\nconst isSlot =\n <T extends Element = Element>(n: string | typeof SlotController.anonymous) =>\n (child: Element): child is T =>\n n === SlotController.anonymous ? !child.hasAttribute('slot')\n : child.getAttribute('slot') === n;\n\nexport class SlotController implements ReactiveController {\n public static anonymous = Symbol('anonymous slot');\n\n private nodes = new Map<string | typeof SlotController.anonymous, Slot>();\n\n private logger: Logger;\n\n private firstUpdated = false;\n\n private mo = new MutationObserver(this.onMutation);\n\n private slotNames: (string | null)[];\n\n private deprecations: Record<string, string> = {};\n\n constructor(public host: ReactiveElement, ...config: ([SlotsConfig] | (string | null)[])) {\n this.logger = new Logger(this.host);\n\n if (isObjectConfigSpread(config)) {\n const [{ slots, deprecations }] = config;\n this.slotNames = slots;\n this.deprecations = deprecations ?? {};\n } else if (config.length >= 1) {\n this.slotNames = config;\n this.deprecations = {};\n } else {\n this.slotNames = [null];\n }\n\n\n host.addController(this);\n }\n\n hostConnected() {\n this.host.addEventListener('slotchange', this.onSlotChange as EventListener);\n this.firstUpdated = false;\n this.mo.observe(this.host, { childList: true });\n this.init();\n }\n\n hostUpdated() {\n if (!this.firstUpdated) {\n this.slotNames.forEach(this.initSlot);\n this.firstUpdated = true;\n }\n }\n\n hostDisconnected() {\n this.mo.disconnect();\n }\n\n /**\n * Returns a boolean statement of whether or not any of those slots exists in the light DOM.\n *\n * @param {String|Array} name The slot name.\n * @example this.hasSlotted(\"header\");\n */\n hasSlotted(...names: string[]): boolean {\n if (!names.length) {\n this.logger.warn(`Please provide at least one slot name for which to search.`);\n return false;\n } else {\n return names.some(x =>\n this.nodes.get(x)?.hasContent ?? false);\n }\n }\n\n /**\n * Given a slot name or slot names, returns elements assigned to the requested slots as an array.\n * If no value is provided, it returns all children not assigned to a slot (without a slot attribute).\n *\n * @example Get header-slotted elements\n * ```js\n * this.getSlotted('header')\n * ```\n *\n * @example Get header- and footer-slotted elements\n * ```js\n * this.getSlotted('header', 'footer')\n * ```\n *\n * @example Get default-slotted elements\n * ```js\n * this.getSlotted();\n * ```\n */\n getSlotted<T extends Element = Element>(...slotNames: string[]): T[] {\n if (!slotNames.length) {\n return (this.nodes.get(SlotController.anonymous)?.elements ?? []) as T[];\n } else {\n return slotNames.flatMap(slotName =>\n this.nodes.get(slotName)?.elements ?? []) as T[];\n }\n }\n\n @bound private onSlotChange(event: Event & { target: HTMLSlotElement }) {\n const slotName = event.target.name;\n this.initSlot(slotName);\n this.host.requestUpdate();\n }\n\n @bound private async onMutation(records: MutationRecord[]) {\n const changed = [];\n for (const { addedNodes, removedNodes } of records) {\n for (const node of [...addedNodes, ...removedNodes]) {\n if (node instanceof HTMLElement && node.slot) {\n this.initSlot(node.slot);\n changed.push(node.slot);\n }\n }\n }\n if (changed.length) {\n this.host.requestUpdate();\n }\n }\n\n private getChildrenForSlot<T extends Element = Element>(name: string | typeof SlotController.anonymous): T[] {\n const children = Array.from(this.host.children) as T[];\n return children.filter(isSlot(name));\n }\n\n @bound private initSlot(slotName: string | null) {\n const name = slotName || SlotController.anonymous;\n const elements = this.nodes.get(name)?.slot?.assignedElements?.() ?? this.getChildrenForSlot(name);\n const selector = slotName ? `slot[name=\"${slotName}\"]` : 'slot:not([name])';\n const slot = this.host.shadowRoot?.querySelector?.<HTMLSlotElement>(selector) ?? null;\n const hasContent = !!elements.length;\n this.nodes.set(name, { elements, name: slotName ?? '', hasContent, slot });\n this.logger.log(slotName, hasContent);\n }\n\n /**\n * Maps the defined slots into an object that is easier to query\n */\n @bound private init() {\n this.nodes.clear();\n // Loop over the properties provided by the schema\n this.slotNames.forEach(this.initSlot);\n Object.values(this.deprecations).forEach(this.initSlot);\n this.host.requestUpdate();\n }\n}\n"]}
package/core.d.ts CHANGED
@@ -19,7 +19,12 @@ export declare function trackPerformance(preference?: boolean | typeof noPref):
19
19
  * A LitElement property converter which represents a list of numbers as a comma separated string
20
20
  * @see https://lit.dev/docs/components/properties/#conversion-converter
21
21
  */
22
- export declare const NumberListConverter: ComplexAttributeConverter<null | number[]>;
22
+ export declare const NumberListConverter: ComplexAttributeConverter<number[] | null, unknown>;
23
+ /**
24
+ * A LitElement property converter which represents a list of strings as a comma separated string
25
+ * @see https://lit.dev/docs/components/properties/#conversion-converter
26
+ */
27
+ export declare const StringListConverter: ComplexAttributeConverter<string[] | null, unknown>;
23
28
  /**
24
29
  * A composed, bubbling event for UI interactions
25
30
  * e.g. when an accordion panel opens.
package/core.js CHANGED
@@ -14,23 +14,31 @@ export function trackPerformance(preference = noPref) {
14
14
  }
15
15
  return window.PfeConfig.trackPerformance;
16
16
  }
17
+ function makeConverter(f) {
18
+ return {
19
+ fromAttribute(value) {
20
+ if (typeof value !== 'string') {
21
+ return null;
22
+ }
23
+ else {
24
+ return value.split(',').map(f);
25
+ }
26
+ },
27
+ toAttribute(value) {
28
+ return value.join(',');
29
+ },
30
+ };
31
+ }
17
32
  /**
18
33
  * A LitElement property converter which represents a list of numbers as a comma separated string
19
34
  * @see https://lit.dev/docs/components/properties/#conversion-converter
20
35
  */
21
- export const NumberListConverter = {
22
- fromAttribute(value) {
23
- if (typeof value !== 'string') {
24
- return null;
25
- }
26
- else {
27
- return value.split(',').map(x => x.trim()).map(x => parseInt(x, 10));
28
- }
29
- },
30
- toAttribute(value) {
31
- return value.join(',');
32
- },
33
- };
36
+ export const NumberListConverter = makeConverter(x => parseInt(x?.trim(), 10));
37
+ /**
38
+ * A LitElement property converter which represents a list of strings as a comma separated string
39
+ * @see https://lit.dev/docs/components/properties/#conversion-converter
40
+ */
41
+ export const StringListConverter = makeConverter(x => x.trim());
34
42
  /**
35
43
  * A composed, bubbling event for UI interactions
36
44
  * e.g. when an accordion panel opens.
package/core.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"core.js","sourceRoot":"","sources":["core.ts"],"names":[],"mappings":"AAYA,MAAM,MAAM,GAAG,MAAM,EAAE,CAAC;AAExB,qCAAqC;AACrC,SAAS,OAAO,CAAC,IAAY;IAC3B,OAAO,QAAQ,CAAC,IAAI,CAAC,aAAa,CAAkB,cAAc,IAAI,IAAI,CAAC,EAAE,OAAO,CAAC;AACvF,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,gBAAgB,CAAC,aAAsC,MAAM;IAC3E,IAAI,UAAU,KAAK,MAAM,EAAE;QACzB,MAAM,CAAC,SAAS,CAAC,gBAAgB,GAAG,CAAC,CAAC,UAAU,CAAC;KAClD;IACD,OAAO,MAAM,CAAC,SAAS,CAAC,gBAAgB,CAAC;AAC3C,CAAC;AAED;;;GAGG;AACH,MAAM,CAAC,MAAM,mBAAmB,GAA6C;IAC3E,aAAa,CAAC,KAAa;QACzB,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE;YAC7B,OAAO,IAAI,CAAC;SACb;aAAM;YACL,OAAO,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,QAAQ,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;SACtE;IACH,CAAC;IACD,WAAW,CAAC,KAAe;QACzB,OAAO,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;IACzB,CAAC;CACF,CAAC;AAEF;;;GAGG;AACH,MAAM,OAAO,aAAc,SAAQ,KAAK;IACtC,YAAY,IAAY,EAAE,IAAgB;QACxC,KAAK,CAAC,IAAI,EAAE;YACV,OAAO,EAAE,IAAI;YACb,QAAQ,EAAE,IAAI;YACd,GAAG,IAAI;SACR,CAAC,CAAC;IACL,CAAC;CACF;AAWD,MAAM,gBAAgB,GAAG,QAAQ,CAAC,IAAI,CAAC,YAAY,CAAC,gBAAgB,CAAC,CAAC;AAEtE,wCAAwC;AACxC,MAAM,CAAC,SAAS,GAAG,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,SAAS,IAAI,EAAE,EAAE;IACvD,gBAAgB,EAAE,MAAM,CAAC,SAAS,EAAE,gBAAgB,IAAI,OAAO,CAAC,sBAAsB,CAAC,KAAK,MAAM;IAClG,qEAAqE;IACrE,0EAA0E;IAC1E,4BAA4B;IAC5B,UAAU,EAAE,MAAM,CAAC,SAAS,EAAE,UAAU,IAAI,CACxC,gBAAgB,CAAC,CAAC,CAAC,CAAC,gBAAgB;QACtC,CAAC,CAAC,OAAO,CAAC,gBAAgB,CAAC,KAAK,MAAM,CACvC;IACD,IAAI,GAAG;QACL,OAAO,CAAC,CAAC,YAAY,CAAC,MAAM,CAAC;IAC/B,CAAC;IACD,IAAI,GAAG,CAAC,CAAU;QAChB,IAAI,CAAC,EAAE;YACL,YAAY,CAAC,OAAO,CAAC,QAAQ,EAAE,GAAG,IAAI,EAAE,CAAC,CAAC;SAC3C;aAAM;YACL,YAAY,CAAC,UAAU,CAAC,QAAQ,CAAC,CAAC;SACnC;IACH,CAAC;CACF,CAAC,CAAC","sourcesContent":["import type { ComplexAttributeConverter } from 'lit';\n\n/** PatternFly Elements global config object */\nexport interface PfeConfig {\n /** Set to false to disable client-side page load performance tracking */\n trackPerformance?: boolean;\n /** Set to false to disable various debug logs */\n log?: boolean;\n /** Set to false to disable automatically removing `unresolved` attr from body */\n autoReveal?: boolean;\n}\n\nconst noPref = Symbol();\n\n/** Retrieve an HTML metadata item */\nfunction getMeta(name: string): string|undefined {\n return document.head.querySelector<HTMLMetaElement>(`meta[name=\"${name}\"]`)?.content;\n}\n\n/**\n * A boolean value that indicates if the performance should be tracked.\n * For use in a JS file or script tag; can also be added in the constructor of a component during development.\n * @example trackPerformance(true);\n */\nexport function trackPerformance(preference: boolean | typeof noPref = noPref) {\n if (preference !== noPref) {\n window.PfeConfig.trackPerformance = !!preference;\n }\n return window.PfeConfig.trackPerformance;\n}\n\n/**\n * A LitElement property converter which represents a list of numbers as a comma separated string\n * @see https://lit.dev/docs/components/properties/#conversion-converter\n */\nexport const NumberListConverter: ComplexAttributeConverter<null|number[]> = {\n fromAttribute(value: string) {\n if (typeof value !== 'string') {\n return null;\n } else {\n return value.split(',').map(x => x.trim()).map(x => parseInt(x, 10));\n }\n },\n toAttribute(value: number[]) {\n return value.join(',');\n },\n};\n\n/**\n * A composed, bubbling event for UI interactions\n * e.g. when an accordion panel opens.\n */\nexport class ComposedEvent extends Event {\n constructor(type: string, init?: EventInit) {\n super(type, {\n bubbles: true,\n composed: true,\n ...init\n });\n }\n}\n\n// 👇 SIDE EFFECTS 👇\n\ndeclare global {\n interface Window {\n /** Global configuration settings for PatternFly Elements */\n PfeConfig: PfeConfig;\n }\n}\n\nconst bodyNoAutoReveal = document.body.hasAttribute('no-auto-reveal');\n\n/** Global patternfly elements config */\nwindow.PfeConfig = Object.assign(window.PfeConfig ?? {}, {\n trackPerformance: window.PfeConfig?.trackPerformance ?? getMeta('pf-track-performance') === 'true',\n // if the body tag has `no-auto-reveal` attribute, reveal immediately\n // if `<meta name=\"pf-auto-reveal\">` exists, and it's `content` is 'true',\n // then auto-reveal the body\n autoReveal: window.PfeConfig?.autoReveal ?? (\n bodyNoAutoReveal ? !bodyNoAutoReveal\n : getMeta('pf-auto-reveal') === 'true'\n ),\n get log() {\n return !!localStorage.pfeLog;\n },\n set log(v: boolean) {\n if (v) {\n localStorage.setItem('pfeLog', `${true}`);\n } else {\n localStorage.removeItem('pfeLog');\n }\n },\n});\n"]}
1
+ {"version":3,"file":"core.js","sourceRoot":"","sources":["core.ts"],"names":[],"mappings":"AAYA,MAAM,MAAM,GAAG,MAAM,EAAE,CAAC;AAExB,qCAAqC;AACrC,SAAS,OAAO,CAAC,IAAY;IAC3B,OAAO,QAAQ,CAAC,IAAI,CAAC,aAAa,CAAkB,cAAc,IAAI,IAAI,CAAC,EAAE,OAAO,CAAC;AACvF,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,gBAAgB,CAAC,aAAsC,MAAM;IAC3E,IAAI,UAAU,KAAK,MAAM,EAAE;QACzB,MAAM,CAAC,SAAS,CAAC,gBAAgB,GAAG,CAAC,CAAC,UAAU,CAAC;KAClD;IACD,OAAO,MAAM,CAAC,SAAS,CAAC,gBAAgB,CAAC;AAC3C,CAAC;AAED,SAAS,aAAa,CAAI,CAAmC;IAC3D,OAAO;QACL,aAAa,CAAC,KAAa;YACzB,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE;gBAC7B,OAAO,IAAI,CAAC;aACb;iBAAM;gBACL,OAAO,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC;aAChC;QACH,CAAC;QACD,WAAW,CAAC,KAAU;YACpB,OAAO,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;QACzB,CAAC;KACF,CAAC;AACJ,CAAC;AAED;;;GAGG;AACH,MAAM,CAAC,MAAM,mBAAmB,GAC9B,aAAa,CAAC,CAAC,CAAC,EAAE,CAAC,QAAQ,CAAC,CAAC,EAAE,IAAI,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC;AAE9C;;;GAGG;AACH,MAAM,CAAC,MAAM,mBAAmB,GAC9B,aAAa,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC;AAE/B;;;GAGG;AACH,MAAM,OAAO,aAAc,SAAQ,KAAK;IACtC,YAAY,IAAY,EAAE,IAAgB;QACxC,KAAK,CAAC,IAAI,EAAE;YACV,OAAO,EAAE,IAAI;YACb,QAAQ,EAAE,IAAI;YACd,GAAG,IAAI;SACR,CAAC,CAAC;IACL,CAAC;CACF;AAWD,MAAM,gBAAgB,GAAG,QAAQ,CAAC,IAAI,CAAC,YAAY,CAAC,gBAAgB,CAAC,CAAC;AAEtE,wCAAwC;AACxC,MAAM,CAAC,SAAS,GAAG,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,SAAS,IAAI,EAAE,EAAE;IACvD,gBAAgB,EAAE,MAAM,CAAC,SAAS,EAAE,gBAAgB,IAAI,OAAO,CAAC,sBAAsB,CAAC,KAAK,MAAM;IAClG,qEAAqE;IACrE,0EAA0E;IAC1E,4BAA4B;IAC5B,UAAU,EAAE,MAAM,CAAC,SAAS,EAAE,UAAU,IAAI,CACxC,gBAAgB,CAAC,CAAC,CAAC,CAAC,gBAAgB;QACtC,CAAC,CAAC,OAAO,CAAC,gBAAgB,CAAC,KAAK,MAAM,CACvC;IACD,IAAI,GAAG;QACL,OAAO,CAAC,CAAC,YAAY,CAAC,MAAM,CAAC;IAC/B,CAAC;IACD,IAAI,GAAG,CAAC,CAAU;QAChB,IAAI,CAAC,EAAE;YACL,YAAY,CAAC,OAAO,CAAC,QAAQ,EAAE,GAAG,IAAI,EAAE,CAAC,CAAC;SAC3C;aAAM;YACL,YAAY,CAAC,UAAU,CAAC,QAAQ,CAAC,CAAC;SACnC;IACH,CAAC;CACF,CAAC,CAAC","sourcesContent":["import type { ComplexAttributeConverter } from 'lit';\n\n/** PatternFly Elements global config object */\nexport interface PfeConfig {\n /** Set to false to disable client-side page load performance tracking */\n trackPerformance?: boolean;\n /** Set to false to disable various debug logs */\n log?: boolean;\n /** Set to false to disable automatically removing `unresolved` attr from body */\n autoReveal?: boolean;\n}\n\nconst noPref = Symbol();\n\n/** Retrieve an HTML metadata item */\nfunction getMeta(name: string): string | undefined {\n return document.head.querySelector<HTMLMetaElement>(`meta[name=\"${name}\"]`)?.content;\n}\n\n/**\n * A boolean value that indicates if the performance should be tracked.\n * For use in a JS file or script tag; can also be added in the constructor of a component during development.\n * @example trackPerformance(true);\n */\nexport function trackPerformance(preference: boolean | typeof noPref = noPref) {\n if (preference !== noPref) {\n window.PfeConfig.trackPerformance = !!preference;\n }\n return window.PfeConfig.trackPerformance;\n}\n\nfunction makeConverter<T>(f: (x: string, type?: unknown) => T): ComplexAttributeConverter<null | T[]> {\n return {\n fromAttribute(value: string) {\n if (typeof value !== 'string') {\n return null;\n } else {\n return value.split(',').map(f);\n }\n },\n toAttribute(value: T[]) {\n return value.join(',');\n },\n };\n}\n\n/**\n * A LitElement property converter which represents a list of numbers as a comma separated string\n * @see https://lit.dev/docs/components/properties/#conversion-converter\n */\nexport const NumberListConverter =\n makeConverter(x => parseInt(x?.trim(), 10));\n\n/**\n * A LitElement property converter which represents a list of strings as a comma separated string\n * @see https://lit.dev/docs/components/properties/#conversion-converter\n */\nexport const StringListConverter =\n makeConverter(x => x.trim());\n\n/**\n * A composed, bubbling event for UI interactions\n * e.g. when an accordion panel opens.\n */\nexport class ComposedEvent extends Event {\n constructor(type: string, init?: EventInit) {\n super(type, {\n bubbles: true,\n composed: true,\n ...init\n });\n }\n}\n\n// 👇 SIDE EFFECTS 👇\n\ndeclare global {\n interface Window {\n /** Global configuration settings for PatternFly Elements */\n PfeConfig: PfeConfig;\n }\n}\n\nconst bodyNoAutoReveal = document.body.hasAttribute('no-auto-reveal');\n\n/** Global patternfly elements config */\nwindow.PfeConfig = Object.assign(window.PfeConfig ?? {}, {\n trackPerformance: window.PfeConfig?.trackPerformance ?? getMeta('pf-track-performance') === 'true',\n // if the body tag has `no-auto-reveal` attribute, reveal immediately\n // if `<meta name=\"pf-auto-reveal\">` exists, and it's `content` is 'true',\n // then auto-reveal the body\n autoReveal: window.PfeConfig?.autoReveal ?? (\n bodyNoAutoReveal ? !bodyNoAutoReveal\n : getMeta('pf-auto-reveal') === 'true'\n ),\n get log() {\n return !!localStorage.pfeLog;\n },\n set log(v: boolean) {\n if (v) {\n localStorage.setItem('pfeLog', `${true}`);\n } else {\n localStorage.removeItem('pfeLog');\n }\n },\n});\n"]}