@pine-ds/icons 9.5.1 → 9.6.1

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.
Files changed (34) hide show
  1. package/components/pds-icon.js +118 -108
  2. package/components/pds-icon.js.map +1 -1
  3. package/dist/cheatsheet.html +7 -5
  4. package/dist/cjs/loader.cjs.js +1 -1
  5. package/dist/cjs/pds-icon.cjs.entry.js +117 -107
  6. package/dist/cjs/pds-icon.cjs.entry.js.map +1 -1
  7. package/dist/cjs/pds-icon.entry.cjs.js.map +1 -1
  8. package/dist/cjs/pds-icons.cjs.js +1 -1
  9. package/dist/collection/components/pds-icon/pds-icon.js +104 -71
  10. package/dist/collection/components/pds-icon/pds-icon.js.map +1 -1
  11. package/dist/collection/components/pds-icon/request.js +16 -39
  12. package/dist/collection/components/pds-icon/request.js.map +1 -1
  13. package/dist/docs.json +5 -5
  14. package/dist/esm/loader.js +1 -1
  15. package/dist/esm/pds-icon.entry.js +117 -107
  16. package/dist/esm/pds-icon.entry.js.map +1 -1
  17. package/dist/esm/pds-icons.js +1 -1
  18. package/dist/pds-icons/p-23a00a5a.entry.js +2 -0
  19. package/dist/pds-icons/p-23a00a5a.entry.js.map +1 -0
  20. package/dist/pds-icons/pds-icon.entry.esm.js.map +1 -1
  21. package/dist/pds-icons/pds-icons.esm.js +1 -1
  22. package/dist/pds-icons.json +11 -1
  23. package/dist/pds-icons.symbols.svg +2 -1
  24. package/dist/svg/switch-vertical.svg +1 -0
  25. package/dist/types/components/pds-icon/pds-icon.d.ts +7 -2
  26. package/dist/types/components/pds-icon/request.d.ts +1 -1
  27. package/dist/types/components.d.ts +2 -2
  28. package/icons/index.d.ts +2 -1
  29. package/icons/index.js +2 -1
  30. package/icons/index.mjs +2 -1
  31. package/icons/package.json +1 -1
  32. package/package.json +1 -1
  33. package/dist/pds-icons/p-560fb565.entry.js +0 -2
  34. package/dist/pds-icons/p-560fb565.entry.js.map +0 -1
@@ -36,14 +36,24 @@ export class PdsIcon {
36
36
  }
37
37
  componentDidLoad() {
38
38
  this.setCSSVariables();
39
- // Always attempt to load icon, but add delay for IntersectionObserver to complete
39
+ if (!this.didLoadIcon) {
40
+ this.loadIcon();
41
+ }
42
+ // Fallback: Ensure icon loads even if IntersectionObserver doesn't fire
40
43
  setTimeout(() => {
41
- if (!this.didLoadIcon || !this.svgContent) {
42
- console.warn('Icon not loaded after component mount, forcing load attempt');
43
- this.isVisible = true; // Force visibility for fallback loading
44
+ if (!this.svgContent && !this.isVisible) {
45
+ this.isVisible = true;
44
46
  this.loadIcon();
45
47
  }
46
- }, 50);
48
+ }, 100);
49
+ // Additional fallback for client-side navigation (React Router, etc.)
50
+ // React's useLayoutEffect and rendering cycles can delay visibility detection
51
+ setTimeout(() => {
52
+ if (!this.svgContent && !this.isVisible) {
53
+ this.isVisible = true;
54
+ this.loadIcon();
55
+ }
56
+ }, 500);
47
57
  }
48
58
  componentWillLoad() {
49
59
  this.inheritedAttributes = inheritAttributes(this.el, ['aria-label']);
@@ -55,20 +65,18 @@ export class PdsIcon {
55
65
  this.el.style.setProperty(`--color-icon-fill`, typeof this.color !== 'undefined' ? this.color : 'currentColor');
56
66
  }
57
67
  connectedCallback() {
58
- // Set a fallback timeout in case IntersectionObserver never fires
59
- // This prevents icons from never loading due to intersection issues
60
- const fallbackTimeout = setTimeout(() => {
61
- if (!this.isVisible) {
62
- console.warn('IntersectionObserver timeout, forcing icon visibility');
68
+ // Handle re-connection during client-side navigation
69
+ if (!this.isVisible && !this.svgContent) {
70
+ this.waitUntilVisible(this.el, '50px', () => {
63
71
  this.isVisible = true;
64
72
  this.loadIcon();
65
- }
66
- }, 100); // 100ms fallback
67
- this.waitUntilVisible(this.el, '50px', () => {
68
- clearTimeout(fallbackTimeout);
73
+ });
74
+ }
75
+ // Immediate load attempt if already visible (e.g., during React navigation)
76
+ if (this.isElementInViewport(this.el)) {
69
77
  this.isVisible = true;
70
78
  this.loadIcon();
71
- });
79
+ }
72
80
  }
73
81
  disconnectedCallback() {
74
82
  if (this.io) {
@@ -80,29 +88,27 @@ export class PdsIcon {
80
88
  this.setCSSVariables();
81
89
  }
82
90
  loadIcon() {
83
- if (Build.isBrowser) {
91
+ // Reset load state when URL changes
92
+ this.didLoadIcon = false;
93
+ // Clear existing content to prevent stale content when switching icons
94
+ this.svgContent = undefined;
95
+ if (Build.isBrowser && this.isVisible) {
84
96
  const url = getUrl(this);
85
97
  if (url) {
86
98
  if (pdsIconContent.has(url)) {
87
99
  this.svgContent = pdsIconContent.get(url);
88
100
  }
89
101
  else {
90
- // Add comprehensive error handling and timeout
91
- const timeoutPromise = new Promise((_, reject) => {
92
- setTimeout(() => reject(new Error('Icon loading timeout')), 10000); // 10 second timeout
93
- });
94
- Promise.race([getSvgContent(url), timeoutPromise])
102
+ // Fix: Ensure promise callback triggers re-render and handle errors
103
+ getSvgContent(url)
95
104
  .then(() => {
96
- this.svgContent = pdsIconContent.get(url);
97
- // Force re-render if content was loaded after initial render
98
- if (!this.svgContent) {
99
- console.warn(`Icon content not found after successful load: ${url}`);
100
- }
105
+ // Force re-render by setting state in next tick
106
+ setTimeout(() => {
107
+ this.svgContent = pdsIconContent.get(url);
108
+ }, 0);
101
109
  })
102
- .catch((error) => {
103
- console.error(`Failed to load icon: ${url}`, error);
104
- // Set empty content to prevent infinite loading state
105
- pdsIconContent.set(url, '');
110
+ .catch(() => {
111
+ // Handle fetch errors gracefully
106
112
  this.svgContent = '';
107
113
  });
108
114
  }
@@ -120,54 +126,33 @@ export class PdsIcon {
120
126
  ? shouldRtlFlipIcon(iconName, this.el) && flipRtl !== false
121
127
  : false;
122
128
  const shouldFlip = flipRtl || shouldIconAutoFlip;
123
- // Debug information when enabled
124
- this.debugIconState();
125
- return (h(Host, Object.assign({ key: '82420f9d474c932c9ed82bbf61b075cbbc67b6db', "aria-label": ariaLabel !== undefined && !this.hasAriaHidden() ? ariaLabel : null, alt: "", role: "img", class: Object.assign(Object.assign({}, createColorClasses(this.color)), { 'flip-rtl': shouldFlip, 'icon-rtl': shouldFlip && isRTL(this.el) }) }, inheritedAttributes), Build.isBrowser && this.svgContent ? (h("div", { class: "icon-inner", innerHTML: this.svgContent })) : (h("div", { class: "icon-inner" }))));
129
+ return (h(Host, Object.assign({ key: '48056743bf1a60bbf905a0779702fd366b86659d', "aria-label": ariaLabel !== undefined && !this.hasAriaHidden() ? ariaLabel : null, alt: "", role: "img", class: Object.assign(Object.assign({}, createColorClasses(this.color)), { 'flip-rtl': shouldFlip, 'icon-rtl': shouldFlip && isRTL(this.el) }) }, inheritedAttributes), Build.isBrowser && this.svgContent ? (h("div", { class: "icon-inner", innerHTML: this.svgContent })) : (h("div", { class: "icon-inner" }))));
126
130
  }
127
131
  /*****
128
132
  * Private Methods
129
133
  ****/
130
- debugIconState() {
131
- if (typeof window !== 'undefined' && window.__PDS_ICON_DEBUG__) {
132
- console.log('PDS Icon Debug:', {
133
- name: this.name,
134
- src: this.src,
135
- icon: this.icon,
136
- isVisible: this.isVisible,
137
- didLoadIcon: this.didLoadIcon,
138
- svgContent: this.svgContent ? 'loaded' : 'empty',
139
- url: getUrl(this),
140
- hasIntersectionObserver: !!this.io,
141
- element: this.el
142
- });
143
- }
144
- }
145
134
  waitUntilVisible(el, rootMargin, cb) {
146
135
  if (Build.isBrowser && typeof window !== 'undefined' && (window).IntersectionObserver) {
147
- try {
148
- const io = (this.io = new (window).IntersectionObserver((data) => {
149
- if (data[0].isIntersecting) {
150
- io.disconnect();
151
- this.io = undefined;
152
- cb();
153
- }
154
- }, { rootMargin }));
155
- io.observe(el);
156
- // Add a safety timeout for IntersectionObserver
157
- setTimeout(() => {
158
- if (this.io) {
159
- console.warn('IntersectionObserver did not trigger within 5 seconds, forcing callback');
136
+ const io = (this.io = new (window).IntersectionObserver((data) => {
137
+ if (data[0].isIntersecting) {
138
+ io.disconnect();
139
+ this.io = undefined;
140
+ cb();
141
+ }
142
+ }, { rootMargin }));
143
+ io.observe(el);
144
+ // Safety timeout for client-side navigation scenarios
145
+ // Sometimes IntersectionObserver doesn't fire during React navigation
146
+ setTimeout(() => {
147
+ if (this.io && !this.isVisible) {
148
+ // Check if element is actually visible in viewport
149
+ if (this.isElementInViewport(el)) {
160
150
  this.io.disconnect();
161
151
  this.io = undefined;
162
152
  cb();
163
153
  }
164
- }, 5000);
165
- }
166
- catch (error) {
167
- console.error('IntersectionObserver initialization failed:', error);
168
- // Fall back to immediate execution
169
- cb();
170
- }
154
+ }
155
+ }, 1000);
171
156
  }
172
157
  else {
173
158
  // browser doesn't support IntersectionObserver
@@ -175,6 +160,54 @@ export class PdsIcon {
175
160
  cb();
176
161
  }
177
162
  }
163
+ isElementInViewport(el) {
164
+ if (!el || !el.isConnected)
165
+ return false;
166
+ const rect = el.getBoundingClientRect();
167
+ const windowHeight = window.innerHeight || document.documentElement.clientHeight;
168
+ const windowWidth = window.innerWidth || document.documentElement.clientWidth;
169
+ return (rect.top >= 0 &&
170
+ rect.left >= 0 &&
171
+ rect.bottom <= windowHeight &&
172
+ rect.right <= windowWidth) || (
173
+ // Also consider partially visible elements
174
+ rect.top < windowHeight &&
175
+ rect.bottom > 0 &&
176
+ rect.left < windowWidth &&
177
+ rect.right > 0);
178
+ }
179
+ /**
180
+ * Debug method to help diagnose loading issues
181
+ * Call from browser console: document.querySelector('pds-icon').debugIconState()
182
+ */
183
+ debugIconState() {
184
+ var _a;
185
+ const url = getUrl(this);
186
+ const rect = this.el.getBoundingClientRect();
187
+ console.log('PdsIcon Debug State:', {
188
+ name: this.name,
189
+ src: this.src,
190
+ icon: this.icon,
191
+ iconName: this.iconName,
192
+ url,
193
+ isVisible: this.isVisible,
194
+ didLoadIcon: this.didLoadIcon,
195
+ hasSvgContent: !!this.svgContent,
196
+ svgContentLength: ((_a = this.svgContent) === null || _a === void 0 ? void 0 : _a.length) || 0,
197
+ isInCache: url ? pdsIconContent.has(url) : false,
198
+ cachedContent: url ? pdsIconContent.get(url) : null,
199
+ element: this.el,
200
+ // Client-side navigation specific debug info
201
+ isConnected: this.el.isConnected,
202
+ isInViewport: this.isElementInViewport(this.el),
203
+ hasIntersectionObserver: !!this.io,
204
+ boundingClientRect: rect,
205
+ windowDimensions: {
206
+ width: window.innerWidth || document.documentElement.clientWidth,
207
+ height: window.innerHeight || document.documentElement.clientHeight
208
+ }
209
+ });
210
+ }
178
211
  static get is() { return "pds-icon"; }
179
212
  static get encapsulation() { return "shadow"; }
180
213
  static get originalStyleUrls() {
@@ -229,11 +262,11 @@ export class PdsIcon {
229
262
  "reflect": false
230
263
  },
231
264
  "icon": {
232
- "type": "string",
265
+ "type": "any",
233
266
  "mutable": false,
234
267
  "complexType": {
235
- "original": "string",
236
- "resolved": "string",
268
+ "original": "any",
269
+ "resolved": "any",
237
270
  "references": {}
238
271
  },
239
272
  "required": false,
@@ -1 +1 @@
1
- {"version":3,"file":"pds-icon.js","sourceRoot":"","sources":["../../../../src/components/pds-icon/pds-icon.tsx"],"names":[],"mappings":"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","sourcesContent":["import { Build, Component, Element, Host, Prop, State, Watch, h } from '@stencil/core';\nimport { getSvgContent, pdsIconContent } from './request';\nimport { getName, getUrl, inheritAttributes, isRTL, shouldRtlFlipIcon } from './utils';\n\n@Component({\n tag: 'pds-icon',\n assetsDirs: ['svg'],\n styleUrl: 'pds-icon.scss',\n shadow: true,\n})\nexport class PdsIcon {\n private didLoadIcon = false;\n private iconName: string | null = null;\n private io?: IntersectionObserver;\n private inheritedAttributes: { [k: string]: any } = {}; // eslint-disable-line @typescript-eslint/no-explicit-any\n\n @Element() el!: HTMLPdsIconElement;\n\n @State() private ariaLabel?: string;\n @State() private isVisible = false;\n @State() private svgContent?: string;\n\n /**\n *\n * The color of the icon\n *\n */\n @Prop() color?: string;\n\n /**\n * Determines if the icon should be flipped when the `dir` is right-to-left (`\"rtl\"`).\n * This is automatically enabled for icons that are in the `ICONS_TO_FLIP` list and\n * when the `dir` is `\"rtl\"`. If `flipRtl` is set to `false`, the icon will not be flipped\n * even if the `dir` is `\"rtl\"`.\n */\n @Prop() flipRtl?: boolean;\n\n /**\n * This is a combination of both `name` and `src`. If a `src` URL is detected,\n * it will set the `src` property. Otherwise it assumes it's a built-in named\n * SVG and sets the `name` property.\n */\n @Prop() icon?: string;\n\n /**\n * The name of the icon to use from\n * the built-in set.\n */\n @Prop({ reflect: true }) name?: string;\n\n /**\n * The size of the icon. This can be\n * 'small', 'regular', 'medium', 'large', or a\n * custom value (40px, 1rem, etc)\n *\n */\n @Prop({ reflect: true }) size?:\n | 'small' // 12px\n | 'regular' // 16px\n | 'medium' // 20px\n | 'large' // 24px\n | 'auto'\n | string = 'regular'\n\n /**\n *\n * Specifies the exact `src` of an SVG file to use.\n */\n @Prop() src?: string;\n\n private iconSize() {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const sizes: { [key: string]: any } = {\n small: '12px',\n regular: '16px',\n medium: '20px',\n large: '24px',\n }\n\n if (sizes[this.size]) {\n return sizes[this.size];\n } else {\n return this.size;\n }\n }\n\n componentDidLoad() {\n this.setCSSVariables();\n\n // Always attempt to load icon, but add delay for IntersectionObserver to complete\n setTimeout(() => {\n if (!this.didLoadIcon || !this.svgContent) {\n console.warn('Icon not loaded after component mount, forcing load attempt');\n this.isVisible = true; // Force visibility for fallback loading\n this.loadIcon();\n }\n }, 50);\n }\n\n componentWillLoad() {\n this.inheritedAttributes = inheritAttributes(this.el, ['aria-label']);\n this.setCSSVariables();\n }\n\n setCSSVariables() {\n this.el.style.setProperty(`--dimension-icon-height`, this.iconSize());\n this.el.style.setProperty(`--dimension-icon-width`, this.iconSize());\n this.el.style.setProperty(`--color-icon-fill`, typeof this.color !== 'undefined' ? this.color : 'currentColor');\n }\n\n connectedCallback() {\n // Set a fallback timeout in case IntersectionObserver never fires\n // This prevents icons from never loading due to intersection issues\n const fallbackTimeout = setTimeout(() => {\n if (!this.isVisible) {\n console.warn('IntersectionObserver timeout, forcing icon visibility');\n this.isVisible = true;\n this.loadIcon();\n }\n }, 100); // 100ms fallback\n\n this.waitUntilVisible(this.el, '50px', () => {\n clearTimeout(fallbackTimeout);\n this.isVisible = true;\n this.loadIcon();\n })\n }\n\n disconnectedCallback() {\n if (this.io) {\n this.io.disconnect();\n this.io = undefined;\n }\n }\n\n @Watch('size')\n @Watch('color')\n updateStyles() {\n this.setCSSVariables();\n }\n\n @Watch('name')\n @Watch('src')\n @Watch('icon')\n loadIcon() {\n if (Build.isBrowser) {\n const url = getUrl(this);\n if (url) {\n if (pdsIconContent.has(url)) {\n this.svgContent = pdsIconContent.get(url);\n } else {\n // Add comprehensive error handling and timeout\n const timeoutPromise = new Promise((_, reject) => {\n setTimeout(() => reject(new Error('Icon loading timeout')), 10000); // 10 second timeout\n });\n\n Promise.race([getSvgContent(url), timeoutPromise])\n .then(() => {\n this.svgContent = pdsIconContent.get(url);\n // Force re-render if content was loaded after initial render\n if (!this.svgContent) {\n console.warn(`Icon content not found after successful load: ${url}`);\n }\n })\n .catch((error) => {\n console.error(`Failed to load icon: ${url}`, error);\n // Set empty content to prevent infinite loading state\n pdsIconContent.set(url, '');\n this.svgContent = '';\n });\n }\n this.didLoadIcon = true;\n }\n }\n\n this.iconName = getName(this.name, this.icon);\n\n if (this.iconName) {\n this.ariaLabel = this.iconName.replace(/\\-/g, ' ');\n }\n }\n\n render() {\n const { ariaLabel, flipRtl, iconName,inheritedAttributes } = this;\n const shouldIconAutoFlip = iconName\n ? shouldRtlFlipIcon(iconName, this.el) && flipRtl !== false\n : false;\n const shouldFlip = flipRtl || shouldIconAutoFlip;\n\n // Debug information when enabled\n this.debugIconState();\n\n return (\n\n <Host\n aria-label={ariaLabel !== undefined && !this.hasAriaHidden() ? ariaLabel : null }\n alt=\"\"\n role=\"img\"\n class={{\n ...createColorClasses(this.color),\n 'flip-rtl': shouldFlip,\n 'icon-rtl': shouldFlip && isRTL(this.el)\n }}\n {...inheritedAttributes}\n >\n {Build.isBrowser && this.svgContent ? (\n <div class=\"icon-inner\" innerHTML={this.svgContent}></div>\n ) : (\n <div class=\"icon-inner\"></div>\n )}\n </Host>\n )\n }\n\n /*****\n * Private Methods\n ****/\n\n private debugIconState() {\n if (typeof window !== 'undefined' && (window as Window & { __PDS_ICON_DEBUG__?: boolean }).__PDS_ICON_DEBUG__) {\n console.log('PDS Icon Debug:', {\n name: this.name,\n src: this.src,\n icon: this.icon,\n isVisible: this.isVisible,\n didLoadIcon: this.didLoadIcon,\n svgContent: this.svgContent ? 'loaded' : 'empty',\n url: getUrl(this),\n hasIntersectionObserver: !!this.io,\n element: this.el\n });\n }\n }\n\n private waitUntilVisible(el: HTMLElement, rootMargin: string, cb: () => void) {\n if (Build.isBrowser && typeof window !== 'undefined' && (window).IntersectionObserver) {\n try {\n const io = (this.io = new (window).IntersectionObserver(\n (data: IntersectionObserverEntry[]) => {\n if (data[0].isIntersecting) {\n io.disconnect();\n this.io = undefined;\n cb();\n }\n },\n { rootMargin },\n ));\n\n io.observe(el);\n\n // Add a safety timeout for IntersectionObserver\n setTimeout(() => {\n if (this.io) {\n console.warn('IntersectionObserver did not trigger within 5 seconds, forcing callback');\n this.io.disconnect();\n this.io = undefined;\n cb();\n }\n }, 5000);\n } catch (error) {\n console.error('IntersectionObserver initialization failed:', error);\n // Fall back to immediate execution\n cb();\n }\n } else {\n // browser doesn't support IntersectionObserver\n // so just fallback to always show it\n cb();\n }\n }\n\n private hasAriaHidden = () => {\n const { el } = this;\n\n return el.hasAttribute('aria-hidden') && el.getAttribute('aria-hidden') === 'true';\n }\n}\n\nconst createColorClasses = (color: string | undefined) => {\n return color\n ? {\n 'pds-color': true,\n [`pds-color-${color}`]: true,\n }\n : null;\n };\n"]}
1
+ {"version":3,"file":"pds-icon.js","sourceRoot":"","sources":["../../../../src/components/pds-icon/pds-icon.tsx"],"names":[],"mappings":"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","sourcesContent":["import { Build, Component, Element, Host, Prop, State, Watch, h } from '@stencil/core';\nimport { getSvgContent, pdsIconContent } from './request';\nimport { getName, getUrl, inheritAttributes, isRTL, shouldRtlFlipIcon } from './utils';\n\n@Component({\n tag: 'pds-icon',\n assetsDirs: ['svg'],\n styleUrl: 'pds-icon.scss',\n shadow: true,\n})\nexport class PdsIcon {\n private didLoadIcon = false;\n private iconName: string | null = null;\n private io?: IntersectionObserver;\n private inheritedAttributes: { [k: string]: any } = {}; // eslint-disable-line @typescript-eslint/no-explicit-any\n\n @Element() el!: HTMLPdsIconElement;\n\n @State() private ariaLabel?: string;\n @State() private isVisible = false;\n @State() private svgContent?: string;\n\n /**\n *\n * The color of the icon\n *\n */\n @Prop() color?: string;\n\n /**\n * Determines if the icon should be flipped when the `dir` is right-to-left (`\"rtl\"`).\n * This is automatically enabled for icons that are in the `ICONS_TO_FLIP` list and\n * when the `dir` is `\"rtl\"`. If `flipRtl` is set to `false`, the icon will not be flipped\n * even if the `dir` is `\"rtl\"`.\n */\n @Prop() flipRtl?: boolean;\n\n /**\n * This is a combination of both `name` and `src`. If a `src` URL is detected,\n * it will set the `src` property. Otherwise it assumes it's a built-in named\n * SVG and sets the `name` property.\n */\n @Prop() icon?: any;\n\n /**\n * The name of the icon to use from\n * the built-in set.\n */\n @Prop({ reflect: true }) name?: string;\n\n /**\n * The size of the icon. This can be\n * 'small', 'regular', 'medium', 'large', or a\n * custom value (40px, 1rem, etc)\n *\n */\n @Prop({ reflect: true }) size?:\n | 'small' // 12px\n | 'regular' // 16px\n | 'medium' // 20px\n | 'large' // 24px\n | 'auto'\n | string = 'regular'\n\n /**\n *\n * Specifies the exact `src` of an SVG file to use.\n */\n @Prop() src?: string;\n\n private iconSize() {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const sizes: { [key: string]: any } = {\n small: '12px',\n regular: '16px',\n medium: '20px',\n large: '24px',\n }\n\n if (sizes[this.size]) {\n return sizes[this.size];\n } else {\n return this.size;\n }\n }\n\n componentDidLoad() {\n this.setCSSVariables();\n\n if (!this.didLoadIcon) {\n this.loadIcon();\n }\n\n // Fallback: Ensure icon loads even if IntersectionObserver doesn't fire\n setTimeout(() => {\n if (!this.svgContent && !this.isVisible) {\n this.isVisible = true;\n this.loadIcon();\n }\n }, 100);\n\n // Additional fallback for client-side navigation (React Router, etc.)\n // React's useLayoutEffect and rendering cycles can delay visibility detection\n setTimeout(() => {\n if (!this.svgContent && !this.isVisible) {\n this.isVisible = true;\n this.loadIcon();\n }\n }, 500);\n }\n\n componentWillLoad() {\n this.inheritedAttributes = inheritAttributes(this.el, ['aria-label']);\n this.setCSSVariables();\n }\n\n setCSSVariables() {\n this.el.style.setProperty(`--dimension-icon-height`, this.iconSize());\n this.el.style.setProperty(`--dimension-icon-width`, this.iconSize());\n this.el.style.setProperty(`--color-icon-fill`, typeof this.color !== 'undefined' ? this.color : 'currentColor');\n }\n\n connectedCallback() {\n // Handle re-connection during client-side navigation\n if (!this.isVisible && !this.svgContent) {\n this.waitUntilVisible(this.el, '50px', () => {\n this.isVisible = true;\n this.loadIcon();\n });\n }\n\n // Immediate load attempt if already visible (e.g., during React navigation)\n if (this.isElementInViewport(this.el)) {\n this.isVisible = true;\n this.loadIcon();\n }\n }\n\n disconnectedCallback() {\n if (this.io) {\n this.io.disconnect();\n this.io = undefined;\n }\n }\n\n @Watch('size')\n @Watch('color')\n updateStyles() {\n this.setCSSVariables();\n }\n\n @Watch('name')\n @Watch('src')\n @Watch('icon')\n loadIcon() {\n // Reset load state when URL changes\n this.didLoadIcon = false;\n\n // Clear existing content to prevent stale content when switching icons\n this.svgContent = undefined;\n\n if (Build.isBrowser && this.isVisible) {\n const url = getUrl(this);\n if (url) {\n if (pdsIconContent.has(url)) {\n this.svgContent = pdsIconContent.get(url);\n } else {\n // Fix: Ensure promise callback triggers re-render and handle errors\n getSvgContent(url)\n .then(() => {\n // Force re-render by setting state in next tick\n setTimeout(() => {\n this.svgContent = pdsIconContent.get(url);\n }, 0);\n })\n .catch(() => {\n // Handle fetch errors gracefully\n this.svgContent = '';\n });\n }\n this.didLoadIcon = true;\n }\n }\n\n this.iconName = getName(this.name, this.icon);\n\n if (this.iconName) {\n this.ariaLabel = this.iconName.replace(/\\-/g, ' ');\n }\n }\n\n render() {\n const { ariaLabel, flipRtl, iconName,inheritedAttributes } = this;\n const shouldIconAutoFlip = iconName\n ? shouldRtlFlipIcon(iconName, this.el) && flipRtl !== false\n : false;\n const shouldFlip = flipRtl || shouldIconAutoFlip;\n\n return (\n\n <Host\n aria-label={ariaLabel !== undefined && !this.hasAriaHidden() ? ariaLabel : null }\n alt=\"\"\n role=\"img\"\n class={{\n ...createColorClasses(this.color),\n 'flip-rtl': shouldFlip,\n 'icon-rtl': shouldFlip && isRTL(this.el)\n }}\n {...inheritedAttributes}\n >\n {Build.isBrowser && this.svgContent ? (\n <div class=\"icon-inner\" innerHTML={this.svgContent}></div>\n ) : (\n <div class=\"icon-inner\"></div>\n )}\n </Host>\n )\n }\n\n /*****\n * Private Methods\n ****/\n\n private waitUntilVisible(el: HTMLElement, rootMargin: string, cb: () => void) {\n if (Build.isBrowser && typeof window !== 'undefined' && (window).IntersectionObserver) {\n const io = (this.io = new (window).IntersectionObserver(\n (data: IntersectionObserverEntry[]) => {\n if (data[0].isIntersecting) {\n io.disconnect();\n this.io = undefined;\n cb();\n }\n },\n { rootMargin },\n ));\n\n io.observe(el);\n\n // Safety timeout for client-side navigation scenarios\n // Sometimes IntersectionObserver doesn't fire during React navigation\n setTimeout(() => {\n if (this.io && !this.isVisible) {\n // Check if element is actually visible in viewport\n if (this.isElementInViewport(el)) {\n this.io.disconnect();\n this.io = undefined;\n cb();\n }\n }\n }, 1000);\n } else {\n // browser doesn't support IntersectionObserver\n // so just fallback to always show it\n cb();\n }\n }\n\n private isElementInViewport(el: HTMLElement): boolean {\n if (!el || !el.isConnected) return false;\n\n const rect = el.getBoundingClientRect();\n const windowHeight = window.innerHeight || document.documentElement.clientHeight;\n const windowWidth = window.innerWidth || document.documentElement.clientWidth;\n\n return (\n rect.top >= 0 &&\n rect.left >= 0 &&\n rect.bottom <= windowHeight &&\n rect.right <= windowWidth\n ) || (\n // Also consider partially visible elements\n rect.top < windowHeight &&\n rect.bottom > 0 &&\n rect.left < windowWidth &&\n rect.right > 0\n );\n }\n\n private hasAriaHidden = () => {\n const { el } = this;\n\n return el.hasAttribute('aria-hidden') && el.getAttribute('aria-hidden') === 'true';\n }\n\n /**\n * Debug method to help diagnose loading issues\n * Call from browser console: document.querySelector('pds-icon').debugIconState()\n */\n debugIconState() {\n const url = getUrl(this);\n const rect = this.el.getBoundingClientRect();\n\n console.log('PdsIcon Debug State:', {\n name: this.name,\n src: this.src,\n icon: this.icon,\n iconName: this.iconName,\n url,\n isVisible: this.isVisible,\n didLoadIcon: this.didLoadIcon,\n hasSvgContent: !!this.svgContent,\n svgContentLength: this.svgContent?.length || 0,\n isInCache: url ? pdsIconContent.has(url) : false,\n cachedContent: url ? pdsIconContent.get(url) : null,\n element: this.el,\n // Client-side navigation specific debug info\n isConnected: this.el.isConnected,\n isInViewport: this.isElementInViewport(this.el),\n hasIntersectionObserver: !!this.io,\n boundingClientRect: rect,\n windowDimensions: {\n width: window.innerWidth || document.documentElement.clientWidth,\n height: window.innerHeight || document.documentElement.clientHeight\n }\n });\n }\n}\n\nconst createColorClasses = (color: string | undefined) => {\n return color\n ? {\n 'pds-color': true,\n [`pds-color-${color}`]: true,\n }\n : null;\n };\n"]}
@@ -2,7 +2,7 @@ import { isEncodedDataUrl, isSvgDataUrl, validateContent } from "./validate";
2
2
  export const pdsIconContent = new Map();
3
3
  const requests = new Map(); // eslint-disable-line @typescript-eslint/no-explicit-any
4
4
  let parser;
5
- export const getSvgContent = (url, sanitize = false, retryCount = 0) => {
5
+ export const getSvgContent = (url, sanitize = false) => {
6
6
  let req = requests.get(url);
7
7
  if (!req) {
8
8
  if (typeof fetch != 'undefined' && typeof document !== 'undefined') {
@@ -17,67 +17,44 @@ export const getSvgContent = (url, sanitize = false, retryCount = 0) => {
17
17
  pdsIconContent.set(url, svg.outerHTML);
18
18
  }
19
19
  else {
20
- console.warn(`No SVG found in data URL: ${url}`);
21
20
  pdsIconContent.set(url, '');
22
21
  }
23
22
  }
24
23
  catch (error) {
25
- console.error(`Failed to parse SVG data URL: ${url}`, error);
26
24
  pdsIconContent.set(url, '');
27
25
  }
28
26
  return Promise.resolve();
29
27
  }
30
28
  else {
31
- // Add retry logic and better error handling
32
- req = fetch(url, {
33
- method: 'GET',
34
- headers: {
35
- 'Accept': 'image/svg+xml,text/plain,*/*'
36
- },
37
- cache: 'force-cache' // Aggressive caching for icons
38
- }).then((rsp) => {
29
+ // we don't have a request
30
+ req = fetch(url).then((rsp) => {
39
31
  if (rsp.ok) {
40
32
  return rsp.text().then((svgContent) => {
41
33
  if (svgContent && sanitize !== false) {
42
- svgContent = validateContent(svgContent);
43
- }
44
- if (svgContent) {
45
- pdsIconContent.set(url, svgContent);
46
- }
47
- else {
48
- console.warn(`Empty SVG content received for: ${url}`);
49
- pdsIconContent.set(url, '');
34
+ try {
35
+ svgContent = validateContent(svgContent);
36
+ }
37
+ catch (validationError) {
38
+ svgContent = '';
39
+ }
50
40
  }
41
+ pdsIconContent.set(url, svgContent || '');
51
42
  });
52
43
  }
53
44
  else {
54
- throw new Error(`HTTP ${rsp.status}: ${rsp.statusText}`);
45
+ // Handle HTTP errors
46
+ throw new Error(`Failed to load SVG: ${rsp.status} ${rsp.statusText}`);
55
47
  }
56
48
  }).catch((error) => {
57
- console.error(`Failed to fetch icon ${url}:`, error);
58
- // Retry logic - attempt up to 3 times with exponential backoff
59
- if (retryCount < 3) {
60
- const delay = Math.pow(2, retryCount) * 1000; // 1s, 2s, 4s
61
- console.log(`Retrying icon load in ${delay}ms (attempt ${retryCount + 1}/3): ${url}`);
62
- return new Promise((resolve) => {
63
- setTimeout(() => {
64
- // Clear the failed request from cache to allow retry
65
- requests.delete(url);
66
- resolve(getSvgContent(url, sanitize, retryCount + 1));
67
- }, delay);
68
- });
69
- }
70
- else {
71
- // Final failure - set empty content to prevent infinite loading
72
- pdsIconContent.set(url, '');
73
- throw error;
74
- }
49
+ // Handle all fetch errors gracefully
50
+ console.warn('Failed to load SVG:', url, error);
51
+ pdsIconContent.set(url, '');
52
+ // Don't re-throw to prevent unhandled promise rejections
75
53
  });
76
54
  requests.set(url, req);
77
55
  }
78
56
  }
79
57
  else {
80
- console.warn('Fetch or document not available, setting empty icon content');
81
58
  pdsIconContent.set(url, '');
82
59
  return Promise.resolve();
83
60
  }
@@ -1 +1 @@
1
- {"version":3,"file":"request.js","sourceRoot":"","sources":["../../../../src/components/pds-icon/request.ts"],"names":[],"mappings":"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","sourcesContent":["import { isEncodedDataUrl, isSvgDataUrl, validateContent } from './validate';\n\nexport const pdsIconContent = new Map<string, string>();\nconst requests = new Map<string, Promise<any>>(); // eslint-disable-line @typescript-eslint/no-explicit-any\n\nlet parser: DOMParser;\n\nexport const getSvgContent = (url: string, sanitize = false, retryCount = 0) => {\n let req = requests.get(url);\n\n if(!req) {\n if (typeof fetch != 'undefined' && typeof document !== 'undefined') {\n if (isSvgDataUrl(url) && isEncodedDataUrl(url)) {\n if (!parser) {\n parser = new DOMParser();\n }\n\n try {\n const doc = parser.parseFromString(url, 'text/html');\n const svg = doc.querySelector('svg');\n\n if (svg) {\n pdsIconContent.set(url, svg.outerHTML);\n } else {\n console.warn(`No SVG found in data URL: ${url}`);\n pdsIconContent.set(url, '');\n }\n } catch (error) {\n console.error(`Failed to parse SVG data URL: ${url}`, error);\n pdsIconContent.set(url, '');\n }\n\n return Promise.resolve();\n } else {\n // Add retry logic and better error handling\n req = fetch(url, {\n method: 'GET',\n headers: {\n 'Accept': 'image/svg+xml,text/plain,*/*'\n },\n cache: 'force-cache' // Aggressive caching for icons\n }).then((rsp) => {\n if (rsp.ok) {\n return rsp.text().then((svgContent) => {\n if (svgContent && sanitize !== false) {\n svgContent = validateContent(svgContent);\n }\n if (svgContent) {\n pdsIconContent.set(url, svgContent);\n } else {\n console.warn(`Empty SVG content received for: ${url}`);\n pdsIconContent.set(url, '');\n }\n });\n } else {\n throw new Error(`HTTP ${rsp.status}: ${rsp.statusText}`);\n }\n }).catch((error) => {\n console.error(`Failed to fetch icon ${url}:`, error);\n\n // Retry logic - attempt up to 3 times with exponential backoff\n if (retryCount < 3) {\n const delay = Math.pow(2, retryCount) * 1000; // 1s, 2s, 4s\n console.log(`Retrying icon load in ${delay}ms (attempt ${retryCount + 1}/3): ${url}`);\n\n return new Promise((resolve) => {\n setTimeout(() => {\n // Clear the failed request from cache to allow retry\n requests.delete(url);\n resolve(getSvgContent(url, sanitize, retryCount + 1));\n }, delay);\n });\n } else {\n // Final failure - set empty content to prevent infinite loading\n pdsIconContent.set(url, '');\n throw error;\n }\n });\n\n requests.set(url, req);\n }\n } else {\n console.warn('Fetch or document not available, setting empty icon content');\n pdsIconContent.set(url, '');\n return Promise.resolve();\n }\n }\n\n return req;\n}\n"]}
1
+ {"version":3,"file":"request.js","sourceRoot":"","sources":["../../../../src/components/pds-icon/request.ts"],"names":[],"mappings":"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","sourcesContent":["import { isEncodedDataUrl, isSvgDataUrl, validateContent } from './validate';\n\nexport const pdsIconContent = new Map<string, string>();\nconst requests = new Map<string, Promise<any>>(); // eslint-disable-line @typescript-eslint/no-explicit-any\n\nlet parser: DOMParser;\n\nexport const getSvgContent = (url: string, sanitize = false) => {\n let req = requests.get(url);\n\n if(!req) {\n if (typeof fetch != 'undefined' && typeof document !== 'undefined') {\n if (isSvgDataUrl(url) && isEncodedDataUrl(url)) {\n if (!parser) {\n parser = new DOMParser();\n }\n\n try {\n const doc = parser.parseFromString(url, 'text/html');\n const svg = doc.querySelector('svg');\n\n if (svg) {\n pdsIconContent.set(url, svg.outerHTML);\n } else {\n pdsIconContent.set(url, '');\n }\n } catch (error) {\n pdsIconContent.set(url, '');\n }\n\n return Promise.resolve();\n } else {\n // we don't have a request\n req = fetch(url).then((rsp) => {\n if (rsp.ok) {\n return rsp.text().then((svgContent) => {\n if (svgContent && sanitize !== false) {\n try {\n svgContent = validateContent(svgContent);\n } catch (validationError) {\n svgContent = '';\n }\n }\n pdsIconContent.set(url, svgContent || '');\n });\n } else {\n // Handle HTTP errors\n throw new Error(`Failed to load SVG: ${rsp.status} ${rsp.statusText}`);\n }\n }).catch((error) => {\n // Handle all fetch errors gracefully\n console.warn('Failed to load SVG:', url, error);\n pdsIconContent.set(url, '');\n // Don't re-throw to prevent unhandled promise rejections\n });\n\n requests.set(url, req);\n }\n } else {\n pdsIconContent.set(url, '');\n return Promise.resolve();\n }\n }\n\n return req;\n}\n"]}
package/dist/docs.json CHANGED
@@ -1,5 +1,5 @@
1
1
  {
2
- "timestamp": "2025-06-27T18:20:18",
2
+ "timestamp": "2025-07-10T20:35:35",
3
3
  "compiler": {
4
4
  "name": "@stencil/core",
5
5
  "version": "4.28.2",
@@ -63,10 +63,10 @@
63
63
  },
64
64
  {
65
65
  "name": "icon",
66
- "type": "string",
66
+ "type": "any",
67
67
  "complexType": {
68
- "original": "string",
69
- "resolved": "string",
68
+ "original": "any",
69
+ "resolved": "any",
70
70
  "references": {}
71
71
  },
72
72
  "mutable": false,
@@ -76,7 +76,7 @@
76
76
  "docsTags": [],
77
77
  "values": [
78
78
  {
79
- "type": "string"
79
+ "type": "any"
80
80
  }
81
81
  ],
82
82
  "optional": true,
@@ -5,7 +5,7 @@ import { g as globalScripts } from './app-globals-DQuL1Twl.js';
5
5
  const defineCustomElements = async (win, options) => {
6
6
  if (typeof window === 'undefined') return undefined;
7
7
  await globalScripts();
8
- return bootstrapLazy([["pds-icon",[[1,"pds-icon",{"color":[1],"flipRtl":[4,"flip-rtl"],"icon":[1],"name":[513],"size":[513],"src":[1],"ariaLabel":[32],"isVisible":[32],"svgContent":[32]},null,{"size":["updateStyles"],"color":["updateStyles"],"name":["loadIcon"],"src":["loadIcon"],"icon":["loadIcon"]}]]]], options);
8
+ return bootstrapLazy([["pds-icon",[[1,"pds-icon",{"color":[1],"flipRtl":[4,"flip-rtl"],"icon":[8],"name":[513],"size":[513],"src":[1],"ariaLabel":[32],"isVisible":[32],"svgContent":[32]},null,{"size":["updateStyles"],"color":["updateStyles"],"name":["loadIcon"],"src":["loadIcon"],"icon":["loadIcon"]}]]]], options);
9
9
  };
10
10
 
11
11
  export { defineCustomElements };