@exadel/esl
Version:
Exadel Smart Library (ESL) is the lightweight custom elements library that provide a set of super-flexible components
208 lines (207 loc) • 7.28 kB
JavaScript
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var ESLShareButton_1;
import { ExportNs } from '../../esl-utils/environment/export-ns';
import { ESLBaseElement } from '../../esl-base-element/core';
import { attr, boolAttr, jsonAttr, listen, memoize, prop } from '../../esl-utils/decorators';
import { ENTER, SPACE } from '../../esl-utils/dom/keys';
import { isEqual } from '../../esl-utils/misc/object/compare';
import { toAbsoluteUrl } from '../../esl-utils/misc/url';
import { ESLShareActionRegistry } from './esl-share-action-registry';
import { ESLShareConfig } from './esl-share-config';
/**
* ESLShareButton
* @author Dmytro Shovchko
*
* ESLShareButton is a custom element to invoke a share actions, defined by {@link ESLShareBaseAction}
*/
let ESLShareButton = ESLShareButton_1 = class ESLShareButton extends ESLBaseElement {
/** Creates an instance of the ESLShareButton */
static create(buttonName) {
const $button = document.createElement(this.is);
if (buttonName) {
$button.name = buttonName;
$button.defaultIcon = true;
}
return $button;
}
/** @returns config of button specified by the name attribute */
get config() {
return ESLShareConfig.instance.getButton(this.name);
}
get(name) {
var _a, _b;
if (name === 'additional') {
// for object props
return Object.keys(this[name]).length ? this[name] : ((_a = this.config) === null || _a === void 0 ? void 0 : _a[name]) || {};
}
// for string props
return this[name] || ((_b = this.config) === null || _b === void 0 ? void 0 : _b[name]) || '';
}
/** @returns an instance of {@link ESLShareBaseAction} assigned to the button */
get actionInstance() {
return ESLShareActionRegistry.instance.get(this.shareAction);
}
/** @returns name of action assigned to the button */
get shareAction() {
return this.get('action');
}
/** @returns additional params assigned to the button */
get shareAdditional() {
return this.get('additional');
}
/** @returns link to share on social network */
get shareLink() {
return this.get('link');
}
/** @returns title to share */
get titleToShare() {
return this.getShareAttr('share-title', document.title);
}
/** @returns URL to share */
get urlToShare() {
return toAbsoluteUrl(this.getShareAttr('share-url', window.location.href));
}
attributeChangedCallback(attrName, oldVal, newVal) {
if (!this.connected || oldVal === newVal)
return;
if (attrName === 'action')
this.updateAction();
if (attrName === 'name')
this.updateName();
}
connectedCallback() {
super.connectedCallback();
this.init();
}
/** Initializes the button */
init(force) {
if (this.ready && !force)
return;
if (this.defaultIcon)
this.initIcon();
this.initA11y();
this.updateAction();
this.onReady();
}
/** Sets initial a11y attributes */
initA11y() {
if (!this.hasAttribute('role'))
this.setAttribute('role', 'button');
if (!this.hasAttribute('tabindex') && this.getAttribute('role') === 'button') {
this.tabIndex = 0;
}
}
/** Initializes the button content */
initIcon() {
if (!this.config)
return;
const { title, icon } = this.config;
this.title = title;
this.innerHTML = icon || '';
const $icon = this.firstElementChild;
if (($icon === null || $icon === void 0 ? void 0 : $icon.tagName) !== 'svg')
return;
$icon.classList.add('esl-share-icon');
}
/** Does an action to share */
share() {
var _a;
(_a = this.actionInstance) === null || _a === void 0 ? void 0 : _a.share(this);
}
/** Updates on button action change */
updateAction() {
var _a;
this.$$attr('unavailable', !((_a = this.actionInstance) === null || _a === void 0 ? void 0 : _a.isAvailable));
}
/** Updates on button name change */
updateName() {
memoize.clear(this, 'config');
this.updateAction();
}
/** Gets attribute from the element or closest parent,
* returns fallback value in the case when an element with attribute not found */
getShareAttr(name, fallback) {
const el = this.closest(`[${name}]`);
return (el && el.getAttribute(name)) || fallback;
}
_onClick(e) {
this.share();
}
_onKeydown(e) {
if ([ENTER, SPACE].includes(e.key)) {
this.click();
e.preventDefault();
}
}
_onConfigChange() {
const { config } = this;
memoize.clear(this, 'config');
if (isEqual(this.config, config))
return;
this.init(true);
this.$$fire(this.SHARE_CHANGED_EVENT, { bubbles: false });
}
/** Actions on complete init and ready component */
onReady() {
if (this.ready)
return;
this.$$attr('ready', true);
this.$$fire(this.SHARE_READY_EVENT, { bubbles: false });
}
};
ESLShareButton.is = 'esl-share-button';
ESLShareButton.observedAttributes = ['action', 'name'];
__decorate([
prop('esl:share:changed')
], ESLShareButton.prototype, "SHARE_CHANGED_EVENT", void 0);
__decorate([
prop('esl:share:ready')
], ESLShareButton.prototype, "SHARE_READY_EVENT", void 0);
__decorate([
attr()
], ESLShareButton.prototype, "action", void 0);
__decorate([
attr()
], ESLShareButton.prototype, "link", void 0);
__decorate([
attr()
], ESLShareButton.prototype, "name", void 0);
__decorate([
attr()
], ESLShareButton.prototype, "shareUrl", void 0);
__decorate([
attr()
], ESLShareButton.prototype, "shareTitle", void 0);
__decorate([
jsonAttr()
], ESLShareButton.prototype, "additional", void 0);
__decorate([
boolAttr()
], ESLShareButton.prototype, "defaultIcon", void 0);
__decorate([
boolAttr()
], ESLShareButton.prototype, "unavailable", void 0);
__decorate([
boolAttr({ readonly: true })
], ESLShareButton.prototype, "ready", void 0);
__decorate([
memoize()
], ESLShareButton.prototype, "config", null);
__decorate([
listen('click')
], ESLShareButton.prototype, "_onClick", null);
__decorate([
listen('keydown')
], ESLShareButton.prototype, "_onKeydown", null);
__decorate([
listen({ event: 'change', target: ESLShareConfig.instance })
], ESLShareButton.prototype, "_onConfigChange", null);
ESLShareButton = ESLShareButton_1 = __decorate([
ExportNs('ShareButton')
], ESLShareButton);
export { ESLShareButton };