@esri/calcite-components
Version:
Web Components for Esri's Calcite Design System.
263 lines (257 loc) • 19.6 kB
JavaScript
import { r as registerInstance, c as createEvent, h, g as getElement, H as Host } from './index-aa8afca4.js';
import { g as getKey } from './key-ec82f942.js';
import { c as getElementProp, g as getElementDir, C as CSS_UTILITY } from './dom-466af3c7.js';
import './guid-09142681.js';
const calciteAccordionCss = "@-webkit-keyframes in{0%{opacity:0}100%{opacity:1}}@keyframes in{0%{opacity:0}100%{opacity:1}}@-webkit-keyframes in-down{0%{opacity:0;-webkit-transform:translate3D(0, -5px, 0);transform:translate3D(0, -5px, 0)}100%{opacity:1;-webkit-transform:translate3D(0, 0, 0);transform:translate3D(0, 0, 0)}}@keyframes in-down{0%{opacity:0;-webkit-transform:translate3D(0, -5px, 0);transform:translate3D(0, -5px, 0)}100%{opacity:1;-webkit-transform:translate3D(0, 0, 0);transform:translate3D(0, 0, 0)}}@-webkit-keyframes in-up{0%{opacity:0;-webkit-transform:translate3D(0, 5px, 0);transform:translate3D(0, 5px, 0)}100%{opacity:1;-webkit-transform:translate3D(0, 0, 0);transform:translate3D(0, 0, 0)}}@keyframes in-up{0%{opacity:0;-webkit-transform:translate3D(0, 5px, 0);transform:translate3D(0, 5px, 0)}100%{opacity:1;-webkit-transform:translate3D(0, 0, 0);transform:translate3D(0, 0, 0)}}@-webkit-keyframes in-scale{0%{opacity:0;-webkit-transform:scale3D(0.95, 0.95, 1);transform:scale3D(0.95, 0.95, 1)}100%{opacity:1;-webkit-transform:scale3D(1, 1, 1);transform:scale3D(1, 1, 1)}}@keyframes in-scale{0%{opacity:0;-webkit-transform:scale3D(0.95, 0.95, 1);transform:scale3D(0.95, 0.95, 1)}100%{opacity:1;-webkit-transform:scale3D(1, 1, 1);transform:scale3D(1, 1, 1)}}:root{--calcite-popper-transition:150ms ease-in-out}:host([hidden]){display:none}:host([scale=s]){--calcite-accordion-item-spacing-unit:0.25rem;--calcite-accordion-icon-margin:0.5rem;--calcite-accordion-item-padding:var(--calcite-accordion-item-spacing-unit) 0.5rem;font-size:var(--calcite-font-size--2);line-height:1rem}:host([scale=m]){--calcite-accordion-item-spacing-unit:0.5rem;--calcite-accordion-icon-margin:0.75rem;--calcite-accordion-item-padding:var(--calcite-accordion-item-spacing-unit) 0.75rem;font-size:var(--calcite-font-size--1);line-height:1rem}:host([scale=l]){--calcite-accordion-item-spacing-unit:0.75rem;--calcite-accordion-icon-margin:1rem;--calcite-accordion-item-padding:var(--calcite-accordion-item-spacing-unit) 1rem;font-size:var(--calcite-font-size-0);line-height:1.25rem}:host{display:block;position:relative;max-width:100%;border-width:1px;border-style:solid;border-color:var(--calcite-ui-border-2);border-bottom-width:0;line-height:1.5rem;--calcite-accordion-item-border:var(--calcite-ui-border-2);--calcite-accordion-item-background:var(--calcite-ui-foreground-1)}:host([appearance=minimal]){--calcite-accordion-item-padding:var(--calcite-accordion-item-spacing-unit) 0;border-color:transparent}:host([appearance=transparent]){border-color:transparent;--calcite-accordion-item-border:transparent;--calcite-accordion-item-background:transparent}";
const CalciteAccordion = class {
constructor(hostRef) {
registerInstance(this, hostRef);
this.calciteAccordionChange = createEvent(this, "calciteAccordionChange", 7);
//--------------------------------------------------------------------------
//
// Public Properties
//
//--------------------------------------------------------------------------
/** specify the appearance - default (containing border), or minimal (no containing border), defaults to default */
this.appearance = "default";
/** specify the placement of the icon in the header, defaults to end */
this.iconPosition = "end";
/** specify the type of the icon in the header, defaults to chevron */
this.iconType = "chevron";
/** specify the scale of accordion, defaults to m */
this.scale = "m";
/** specify the selection mode - multi (allow any number of open items), single (allow one open item),
* or single-persist (allow and require one open item), defaults to multi */
this.selectionMode = "multi";
//--------------------------------------------------------------------------
//
// Private State/Props
//
//--------------------------------------------------------------------------
/** created list of Accordion items */
this.items = [];
/** keep track of whether the items have been sorted so we don't re-sort */
this.sorted = false;
this.sortItems = (items) => items.sort((a, b) => a.position - b.position).map((a) => a.item);
}
//--------------------------------------------------------------------------
//
// Lifecycle
//
//--------------------------------------------------------------------------
componentDidLoad() {
if (!this.sorted) {
this.items = this.sortItems(this.items);
this.sorted = true;
}
}
render() {
return h("slot", null);
}
//--------------------------------------------------------------------------
//
// Event Listeners
//
//--------------------------------------------------------------------------
calciteAccordionItemKeyEvent(e) {
const item = e.detail.item;
const parent = e.detail.parent;
if (this.el === parent) {
const key = getKey(item.key);
const itemToFocus = e.target;
const isFirstItem = this.itemIndex(itemToFocus) === 0;
const isLastItem = this.itemIndex(itemToFocus) === this.items.length - 1;
switch (key) {
case "ArrowDown":
if (isLastItem) {
this.focusFirstItem();
}
else {
this.focusNextItem(itemToFocus);
}
break;
case "ArrowUp":
if (isFirstItem) {
this.focusLastItem();
}
else {
this.focusPrevItem(itemToFocus);
}
break;
case "Home":
this.focusFirstItem();
break;
case "End":
this.focusLastItem();
break;
}
}
}
registerCalciteAccordionItem(e) {
const item = {
item: e.target,
parent: e.detail.parent,
position: e.detail.position
};
if (this.el === item.parent) {
this.items.push(item);
}
}
updateActiveItemOnChange(event) {
this.requestedAccordionItem = event.detail.requestedAccordionItem;
this.calciteAccordionChange.emit({
requestedAccordionItem: this.requestedAccordionItem
});
}
//--------------------------------------------------------------------------
//
// Private Methods
//
//--------------------------------------------------------------------------
focusFirstItem() {
const firstItem = this.items[0];
this.focusElement(firstItem);
}
focusLastItem() {
const lastItem = this.items[this.items.length - 1];
this.focusElement(lastItem);
}
focusNextItem(e) {
const index = this.itemIndex(e);
const nextItem = this.items[index + 1] || this.items[0];
this.focusElement(nextItem);
}
focusPrevItem(e) {
const index = this.itemIndex(e);
const prevItem = this.items[index - 1] || this.items[this.items.length - 1];
this.focusElement(prevItem);
}
itemIndex(e) {
return this.items.indexOf(e);
}
focusElement(item) {
const target = item;
target.focus();
}
get el() { return getElement(this); }
};
CalciteAccordion.style = calciteAccordionCss;
const calciteAccordionItemCss = "@-webkit-keyframes in{0%{opacity:0}100%{opacity:1}}@keyframes in{0%{opacity:0}100%{opacity:1}}@-webkit-keyframes in-down{0%{opacity:0;-webkit-transform:translate3D(0, -5px, 0);transform:translate3D(0, -5px, 0)}100%{opacity:1;-webkit-transform:translate3D(0, 0, 0);transform:translate3D(0, 0, 0)}}@keyframes in-down{0%{opacity:0;-webkit-transform:translate3D(0, -5px, 0);transform:translate3D(0, -5px, 0)}100%{opacity:1;-webkit-transform:translate3D(0, 0, 0);transform:translate3D(0, 0, 0)}}@-webkit-keyframes in-up{0%{opacity:0;-webkit-transform:translate3D(0, 5px, 0);transform:translate3D(0, 5px, 0)}100%{opacity:1;-webkit-transform:translate3D(0, 0, 0);transform:translate3D(0, 0, 0)}}@keyframes in-up{0%{opacity:0;-webkit-transform:translate3D(0, 5px, 0);transform:translate3D(0, 5px, 0)}100%{opacity:1;-webkit-transform:translate3D(0, 0, 0);transform:translate3D(0, 0, 0)}}@-webkit-keyframes in-scale{0%{opacity:0;-webkit-transform:scale3D(0.95, 0.95, 1);transform:scale3D(0.95, 0.95, 1)}100%{opacity:1;-webkit-transform:scale3D(1, 1, 1);transform:scale3D(1, 1, 1)}}@keyframes in-scale{0%{opacity:0;-webkit-transform:scale3D(0.95, 0.95, 1);transform:scale3D(0.95, 0.95, 1)}100%{opacity:1;-webkit-transform:scale3D(1, 1, 1);transform:scale3D(1, 1, 1)}}:root{--calcite-popper-transition:150ms ease-in-out}:host([hidden]){display:none}.icon-position--start{--calcite-accordion-item-flex-direction:row-reverse;--calcite-accordion-item-icon-rotation:90deg;--calcite-accordion-item-active-icon-rotation:180deg;--calcite-accordion-item-icon-rotation-rtl:-90deg;--calcite-accordion-item-active-icon-rotation-rtl:-180deg;--calcite-accordion-item-icon-spacing-start:0;--calcite-accordion-item-icon-spacing-end:var(--calcite-accordion-icon-margin)}.icon-position--end{--calcite-accordion-item-flex-direction:row;--calcite-accordion-item-icon-rotation:-90deg;--calcite-accordion-item-active-icon-rotation:0;--calcite-accordion-item-icon-rotation-rtl:90deg;--calcite-accordion-item-active-icon-rotation-rtl:0;--calcite-accordion-item-icon-spacing-start:var(--calcite-accordion-icon-margin);--calcite-accordion-item-icon-spacing-end:0}.icon-position--end:not(.icon-type--plus-minus){--calcite-accordion-item-icon-rotation:0;--calcite-accordion-item-active-icon-rotation:180deg;--calcite-accordion-item-icon-rotation-rtl:0;--calcite-accordion-item-active-icon-rotation-rtl:-180deg}:host{--calcite-accordion-item-background:var(--calcite-ui-foreground-1)}:host-context([appearance=minimal]){--calcite-accordion-item-padding:var(--calcite-accordion-item-spacing-unit) 0}:host-context([appearance=transparent]){--calcite-accordion-item-border:transparent;--calcite-accordion-item-background:transparent}:host{display:-ms-flexbox;display:flex;-ms-flex-direction:column;flex-direction:column;text-decoration:none;outline:2px solid transparent;outline-offset:2px;position:relative;color:var(--calcite-ui-text-3);background-color:var(--calcite-accordion-item-background);--calcite-accordion-item-border:var(--calcite-ui-border-2)}:host .accordion-item-header{outline-offset:0;outline-color:transparent;-webkit-transition:outline-offset 100ms ease-in-out, outline-color 100ms ease-in-out;transition:outline-offset 100ms ease-in-out, outline-color 100ms ease-in-out}:host(:focus) .accordion-item-header{outline:2px solid var(--calcite-ui-brand);outline-offset:-2px}:host([active]){color:var(--calcite-ui-text-1)}:host([active]) .accordion-item-content{display:block;color:var(--calcite-ui-text-1)}:host([active]) .accordion-item-header{border-bottom-color:transparent}:host .accordion-item-header{display:-ms-flexbox;display:flex;-ms-flex-align:center;align-items:center;cursor:pointer;-ms-flex-direction:var(--calcite-accordion-item-flex-direction);flex-direction:var(--calcite-accordion-item-flex-direction)}:host .accordion-item-icon{display:-ms-inline-flexbox;display:inline-flex;position:relative;margin:0;color:var(--calcite-ui-text-3);-webkit-transition-duration:150ms;transition-duration:150ms;-webkit-transition-timing-function:cubic-bezier(0.4, 0, 0.2, 1);transition-timing-function:cubic-bezier(0.4, 0, 0.2, 1);margin-right:var(--calcite-accordion-item-icon-spacing-start);margin-left:var(--calcite-accordion-item-icon-spacing-end)}.calcite--rtl .accordion-item-icon{margin-left:var(--calcite-accordion-item-icon-spacing-start);margin-right:var(--calcite-accordion-item-icon-spacing-end)}:host .accordion-item-content,:host .accordion-item-header{padding:var(--calcite-accordion-item-padding);border-bottom:1px solid var(--calcite-accordion-item-border)}:host .accordion-item-header *{display:-ms-inline-flexbox;display:inline-flex;-ms-flex-align:center;align-items:center;-webkit-transition-duration:150ms;transition-duration:150ms;-webkit-transition-timing-function:cubic-bezier(0.4, 0, 0.2, 1);transition-timing-function:cubic-bezier(0.4, 0, 0.2, 1)}:host .accordion-item-content{display:none;color:var(--calcite-ui-text-3);padding-top:0;text-align:initial}:host .accordion-item-expand-icon{color:var(--calcite-ui-text-3);margin-left:var(--calcite-accordion-item-icon-spacing-start);margin-right:var(--calcite-accordion-item-icon-spacing-end);-webkit-transform:rotate(var(--calcite-accordion-item-icon-rotation));transform:rotate(var(--calcite-accordion-item-icon-rotation))}.calcite--rtl .accordion-item-expand-icon{margin-left:var(--calcite-accordion-item-icon-spacing-end);margin-right:var(--calcite-accordion-item-icon-spacing-start);-webkit-transform:rotate(var(--calcite-accordion-item-icon-rotation-rtl));transform:rotate(var(--calcite-accordion-item-icon-rotation-rtl))}:host([active]) .accordion-item-expand-icon{color:var(--calcite-ui-text-1);-webkit-transform:rotate(var(--calcite-accordion-item-active-icon-rotation));transform:rotate(var(--calcite-accordion-item-active-icon-rotation))}:host([active]) .calcite--rtl .accordion-item-expand-icon{-webkit-transform:rotate(var(--calcite-accordion-item-active-icon-rotation-rtl));transform:rotate(var(--calcite-accordion-item-active-icon-rotation-rtl))}:host .accordion-item-header-text{-ms-flex-direction:column;flex-direction:column;-ms-flex-positive:1;flex-grow:1;margin-top:0;margin-bottom:0;padding-top:0;padding-bottom:0;margin-right:auto;text-align:initial}.calcite--rtl .accordion-item-header-text{margin-right:0;margin-left:auto}:host .accordion-item-title,:host .accordion-item-subtitle{display:-ms-flexbox;display:flex;width:100%}:host .accordion-item-title{color:var(--calcite-ui-text-2);font-weight:var(--calcite-font-weight-medium)}:host .accordion-item-subtitle{color:var(--calcite-ui-text-3);margin-top:0.25rem}.calcite--rtl .accordion-item-title{margin-right:0;margin-left:auto}:host(:focus) .accordion-item-title,:host(:hover) .accordion-item-title{color:var(--calcite-ui-text-1)}:host(:focus) .accordion-item-icon,:host(:hover) .accordion-item-icon{color:var(--calcite-ui-text-1)}:host(:focus) .accordion-item-expand-icon,:host(:hover) .accordion-item-expand-icon{color:var(--calcite-ui-text-1)}:host(:focus) .accordion-item-subtitle,:host(:hover) .accordion-item-subtitle{color:var(--calcite-ui-text-2)}:host(:focus) .accordion-item-title,:host(:active) .accordion-item-title,:host([active]) .accordion-item-title{color:var(--calcite-ui-text-1)}:host(:focus) .accordion-item-icon,:host(:active) .accordion-item-icon,:host([active]) .accordion-item-icon{color:var(--calcite-ui-text-1)}:host(:focus) .accordion-item-expand-icon,:host(:active) .accordion-item-expand-icon,:host([active]) .accordion-item-expand-icon{color:var(--calcite-ui-text-1)}:host(:focus) .accordion-item-subtitle,:host(:active) .accordion-item-subtitle,:host([active]) .accordion-item-subtitle{color:var(--calcite-ui-text-2)}";
const CalciteAccordionItem = class {
constructor(hostRef) {
registerInstance(this, hostRef);
this.calciteAccordionItemKeyEvent = createEvent(this, "calciteAccordionItemKeyEvent", 7);
this.calciteAccordionItemSelect = createEvent(this, "calciteAccordionItemSelect", 7);
this.calciteAccordionItemClose = createEvent(this, "calciteAccordionItemClose", 7);
this.calciteAccordionItemRegister = createEvent(this, "calciteAccordionItemRegister", 7);
//--------------------------------------------------------------------------
//
// Public Properties
//
//--------------------------------------------------------------------------
this.active = false;
/** what icon position does the parent accordion specify */
this.iconPosition = "end";
/** handle clicks on item header */
this.itemHeaderClickHandler = () => this.emitRequestedItem();
}
//--------------------------------------------------------------------------
//
// Lifecycle
//
//--------------------------------------------------------------------------
connectedCallback() {
this.parent = this.el.parentElement;
this.selectionMode = getElementProp(this.el, "selection-mode", "multi");
this.iconType = getElementProp(this.el, "icon-type", "chevron");
this.iconPosition = getElementProp(this.el, "icon-position", this.iconPosition);
}
componentDidLoad() {
this.itemPosition = this.getItemPosition();
this.calciteAccordionItemRegister.emit({
parent: this.parent,
position: this.itemPosition
});
}
render() {
const dir = getElementDir(this.el);
const iconEl = h("calcite-icon", { class: "accordion-item-icon", icon: this.icon, scale: "s" });
return (h(Host, { "aria-expanded": this.active.toString(), tabindex: "0" }, h("div", { class: {
[`icon-position--${this.iconPosition}`]: true,
[`icon-type--${this.iconType}`]: true
} }, h("div", { class: { "accordion-item-header": true, [CSS_UTILITY.rtl]: dir === "rtl" }, onClick: this.itemHeaderClickHandler }, this.icon ? iconEl : null, h("div", { class: "accordion-item-header-text" }, h("span", { class: "accordion-item-title" }, this.itemTitle), this.itemSubtitle ? (h("span", { class: "accordion-item-subtitle" }, this.itemSubtitle)) : null), h("calcite-icon", { class: "accordion-item-expand-icon", icon: this.iconType === "chevron"
? "chevronUp"
: this.iconType === "caret"
? "caretUp"
: this.active
? "minus"
: "plus", scale: "s" })), h("div", { class: "accordion-item-content" }, h("slot", null)))));
}
//--------------------------------------------------------------------------
//
// Event Listeners
//
//--------------------------------------------------------------------------
keyDownHandler(e) {
if (e.target === this.el) {
switch (getKey(e.key)) {
case " ":
case "Enter":
this.emitRequestedItem();
e.preventDefault();
break;
case "ArrowUp":
case "ArrowDown":
case "Home":
case "End":
this.calciteAccordionItemKeyEvent.emit({
parent: this.parent,
item: e
});
e.preventDefault();
break;
}
}
}
updateActiveItemOnChange(event) {
this.requestedAccordionItem = event.detail
.requestedAccordionItem;
this.determineActiveItem();
}
//--------------------------------------------------------------------------
//
// Private Methods
//
//--------------------------------------------------------------------------
determineActiveItem() {
switch (this.selectionMode) {
case "multi":
if (this.el === this.requestedAccordionItem) {
this.active = !this.active;
}
break;
case "single":
if (this.el === this.requestedAccordionItem) {
this.active = !this.active;
}
else {
this.active = false;
}
break;
case "single-persist":
this.active = this.el === this.requestedAccordionItem;
break;
}
}
emitRequestedItem() {
this.calciteAccordionItemSelect.emit({
requestedAccordionItem: this.el
});
}
getItemPosition() {
return Array.prototype.indexOf.call(this.parent.querySelectorAll("calcite-accordion-item"), this.el);
}
get el() { return getElement(this); }
};
CalciteAccordionItem.style = calciteAccordionItemCss;
export { CalciteAccordion as calcite_accordion, CalciteAccordionItem as calcite_accordion_item };