UNPKG

@synergy-design-system/components

Version:

This package provides the base of the Synergy Design System as native web components. It uses [lit](https://www.lit.dev) and parts of [shoelace](https://shoelace.style/). Synergy officially supports the latest two versions of all major browsers (as define

279 lines (275 loc) 8.01 kB
import { tooltip_custom_styles_default } from "./chunk.YT5SHGUK.js"; import { tooltip_styles_default } from "./chunk.O644HRW3.js"; import { SynPopup } from "./chunk.6CC5CH2P.js"; import { waitForEvent } from "./chunk.C2ENQBPM.js"; import { animateTo, parseDuration, stopAnimations } from "./chunk.G6ITZTTW.js"; import { getAnimation, setDefaultAnimation } from "./chunk.7JGKUB4A.js"; import { LocalizeController } from "./chunk.OAQRCZOO.js"; import { watch } from "./chunk.BVZQ6QSY.js"; import { component_styles_default } from "./chunk.NLYVOJGK.js"; import { SynergyElement } from "./chunk.3AZFEB6D.js"; import { __decorateClass } from "./chunk.Z4XV3SMG.js"; // src/components/tooltip/tooltip.component.ts import { classMap } from "lit/directives/class-map.js"; import { html } from "lit"; import { property, query } from "lit/decorators.js"; var SynTooltip = class extends SynergyElement { constructor() { super(); this.localize = new LocalizeController(this); this.content = ""; this.placement = "top"; this.disabled = false; this.distance = 13; this.open = false; this.skidding = 0; this.trigger = "hover focus"; this.hoist = false; this.handleBlur = () => { if (this.hasTrigger("focus")) { this.hide(); } }; this.handleClick = () => { if (this.hasTrigger("click")) { if (this.open) { this.hide(); } else { this.show(); } } }; this.handleFocus = () => { if (this.hasTrigger("focus")) { this.show(); } }; this.handleDocumentKeyDown = (event) => { if (event.key === "Escape") { event.stopPropagation(); this.hide(); } }; this.handleMouseOver = () => { if (this.hasTrigger("hover")) { const delay = parseDuration(getComputedStyle(this).getPropertyValue("--show-delay")); clearTimeout(this.hoverTimeout); this.hoverTimeout = window.setTimeout(() => this.show(), delay); } }; this.handleMouseOut = () => { if (this.hasTrigger("hover")) { const delay = parseDuration(getComputedStyle(this).getPropertyValue("--hide-delay")); clearTimeout(this.hoverTimeout); this.hoverTimeout = window.setTimeout(() => this.hide(), delay); } }; this.addEventListener("blur", this.handleBlur, true); this.addEventListener("focus", this.handleFocus, true); this.addEventListener("click", this.handleClick); this.addEventListener("mouseover", this.handleMouseOver); this.addEventListener("mouseout", this.handleMouseOut); } disconnectedCallback() { var _a; super.disconnectedCallback(); (_a = this.closeWatcher) == null ? void 0 : _a.destroy(); document.removeEventListener("keydown", this.handleDocumentKeyDown); } firstUpdated() { this.body.hidden = !this.open; if (this.open) { this.popup.active = true; this.popup.reposition(); } } hasTrigger(triggerType) { const triggers = this.trigger.split(" "); return triggers.includes(triggerType); } async handleOpenChange() { var _a, _b; if (this.open) { if (this.disabled) { return; } this.emit("syn-show"); if ("CloseWatcher" in window) { (_a = this.closeWatcher) == null ? void 0 : _a.destroy(); this.closeWatcher = new CloseWatcher(); this.closeWatcher.onclose = () => { this.hide(); }; } else { document.addEventListener("keydown", this.handleDocumentKeyDown); } await stopAnimations(this.body); this.body.hidden = false; this.popup.active = true; const { keyframes, options } = getAnimation(this, "tooltip.show", { dir: this.localize.dir() }); await animateTo(this.popup.popup, keyframes, options); this.popup.reposition(); this.emit("syn-after-show"); } else { this.emit("syn-hide"); (_b = this.closeWatcher) == null ? void 0 : _b.destroy(); document.removeEventListener("keydown", this.handleDocumentKeyDown); await stopAnimations(this.body); const { keyframes, options } = getAnimation(this, "tooltip.hide", { dir: this.localize.dir() }); await animateTo(this.popup.popup, keyframes, options); this.popup.active = false; this.body.hidden = true; this.emit("syn-after-hide"); } } async handleOptionsChange() { if (this.hasUpdated) { await this.updateComplete; this.popup.reposition(); } } handleDisabledChange() { if (this.disabled && this.open) { this.hide(); } } /** Shows the tooltip. */ async show() { if (this.open) { return void 0; } this.open = true; return waitForEvent(this, "syn-after-show"); } /** Hides the tooltip */ async hide() { if (!this.open) { return void 0; } this.open = false; return waitForEvent(this, "syn-after-hide"); } // // NOTE: Tooltip is a bit unique in that we're using aria-live instead of aria-labelledby to trick screen readers into // announcing the content. It works really well, but it violates an accessibility rule. We're also adding the // aria-describedby attribute to a slot, which is required by <syn-popup> to correctly locate the first assigned // element, otherwise positioning is incorrect. // render() { return html` <syn-popup part="base" exportparts=" popup:base__popup, arrow:base__arrow " class=${classMap({ tooltip: true, "tooltip--open": this.open })} placement=${this.placement} distance=${this.distance} skidding=${this.skidding} strategy=${this.hoist ? "fixed" : "absolute"} flip shift arrow hover-bridge > ${""} <slot slot="anchor" aria-describedby="tooltip"></slot> ${""} <div part="body" id="tooltip" class="tooltip__body" role="tooltip" aria-live=${this.open ? "polite" : "off"}> <slot name="content">${this.content}</slot> </div> </syn-popup> `; } }; SynTooltip.styles = [component_styles_default, tooltip_styles_default, tooltip_custom_styles_default]; SynTooltip.dependencies = { "syn-popup": SynPopup }; __decorateClass([ query("slot:not([name])") ], SynTooltip.prototype, "defaultSlot", 2); __decorateClass([ query(".tooltip__body") ], SynTooltip.prototype, "body", 2); __decorateClass([ query("syn-popup") ], SynTooltip.prototype, "popup", 2); __decorateClass([ property() ], SynTooltip.prototype, "content", 2); __decorateClass([ property() ], SynTooltip.prototype, "placement", 2); __decorateClass([ property({ type: Boolean, reflect: true }) ], SynTooltip.prototype, "disabled", 2); __decorateClass([ property({ type: Number }) ], SynTooltip.prototype, "distance", 2); __decorateClass([ property({ type: Boolean, reflect: true }) ], SynTooltip.prototype, "open", 2); __decorateClass([ property({ type: Number }) ], SynTooltip.prototype, "skidding", 2); __decorateClass([ property() ], SynTooltip.prototype, "trigger", 2); __decorateClass([ property({ type: Boolean }) ], SynTooltip.prototype, "hoist", 2); __decorateClass([ watch("open", { waitUntilFirstUpdate: true }) ], SynTooltip.prototype, "handleOpenChange", 1); __decorateClass([ watch(["content", "distance", "hoist", "placement", "skidding"]) ], SynTooltip.prototype, "handleOptionsChange", 1); __decorateClass([ watch("disabled") ], SynTooltip.prototype, "handleDisabledChange", 1); setDefaultAnimation("tooltip.show", { keyframes: [ { opacity: 0, scale: 0.8 }, { opacity: 1, scale: 1 } ], options: { duration: 150, easing: "ease" } }); setDefaultAnimation("tooltip.hide", { keyframes: [ { opacity: 1, scale: 1 }, { opacity: 0, scale: 0.8 } ], options: { duration: 150, easing: "ease" } }); export { SynTooltip }; //# sourceMappingURL=chunk.LK6UOSII.js.map