From 6d3a92db329c5198d56aeed4a1944ef3d0e29f1d Mon Sep 17 00:00:00 2001 From: Tremayne Christ Date: Fri, 22 Oct 2021 16:31:31 +0100 Subject: [PATCH] feat(icon): support icon names and icon urls --- packages/elements/src/icon/index.ts | 5 +-- .../elements/src/icon/utils/IconLoader.ts | 34 ++++++++++--------- 2 files changed, 21 insertions(+), 18 deletions(-) diff --git a/packages/elements/src/icon/index.ts b/packages/elements/src/icon/index.ts index 7e6f99aa13..301a470981 100644 --- a/packages/elements/src/icon/index.ts +++ b/packages/elements/src/icon/index.ts @@ -52,8 +52,8 @@ export class Icon extends BasicElement { private _icon: string | null = null; /** - * Name of a known icon to render. - * @example heart + * Name of a known icon to render or URL of SVG icon. + * @example heart | https://cdn.io/icons/heart.svg */ @property({ type: String, reflect: true }) public get icon (): string | null { @@ -73,6 +73,7 @@ export class Icon extends BasicElement { /** * Src location of an svg icon. * @example https://cdn.io/icons/heart.svg + * @deprecated Use `icon` instead */ @property({ type: String }) public get src (): string | null { diff --git a/packages/elements/src/icon/utils/IconLoader.ts b/packages/elements/src/icon/utils/IconLoader.ts index 25ccd20b53..f6a0f4ae4b 100644 --- a/packages/elements/src/icon/utils/IconLoader.ts +++ b/packages/elements/src/icon/utils/IconLoader.ts @@ -1,5 +1,5 @@ import { CdnLoader, Deferred } from '@refinitiv-ui/utils'; -const isUrl = (str: string): boolean => (/^https?:\/\//i).test(str); +const isUrl = (str: string): boolean => (/^(https?:\/{2}|\.?\/)/i).test(str); /** * Caches and provides icon SVGs, Loaded either by name from CDN or directly by URL. @@ -54,27 +54,29 @@ class IconLoader extends CdnLoader { * @returns Promise, which will be resolved with complete source. */ public async getSrc (iconName: string): Promise { + if (isUrl(iconName)) { + return iconName; + } return iconName ? `${await this.getCdnPrefix()}${iconName}.svg` : ''; } public async loadSVG (icon: string): Promise { - if (icon) { - if (!isUrl(icon)) { - icon = await this.getSrc(icon); - } - const response = await this.load(icon); - if (response && response.status === 200 && response.getResponseHeader('content-type') === 'image/svg+xml') { - const container = document.createElement('svg'); - container.innerHTML = response.responseText; - this.stripUnsafeNodes(...container.children); - const svgRoot = container.firstElementChild as SVGElement | null; - if (svgRoot) { - svgRoot.setAttribute('focusable', 'false'); /* disable IE11 focus on SVG root element */ - } - return Promise.resolve(container.innerHTML); + if (!icon) { + return; + } + icon = await this.getSrc(icon); + const response = await this.load(icon); + if (response && response.status === 200 && response.getResponseHeader('content-type') === 'image/svg+xml') { + const container = document.createElement('svg'); + container.innerHTML = response.responseText; + this.stripUnsafeNodes(...container.children); + const svgRoot = container.firstElementChild as SVGElement | null; + if (svgRoot) { + svgRoot.setAttribute('focusable', 'false'); /* disable IE11 focus on SVG root element */ } - return Promise.resolve(''); + return container.innerHTML; } + return ''; } }