react-inlinesvg 4.0.6 → 4.1.0
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.
- package/dist/index.d.mts +6 -3
- package/dist/index.d.ts +6 -3
- package/dist/index.js +263 -228
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +271 -228
- package/dist/index.mjs.map +1 -1
- package/dist/provider.js +2 -1
- package/dist/provider.js.map +1 -1
- package/dist/provider.mjs +3 -1
- package/dist/provider.mjs.map +1 -1
- package/package.json +12 -12
- package/src/index.tsx +195 -270
- package/src/{cache.ts → modules/cache.ts} +3 -2
- package/src/{helpers.ts → modules/helpers.ts} +1 -1
- package/src/modules/hooks.tsx +11 -0
- package/src/modules/utils.ts +122 -0
- package/src/provider.tsx +1 -1
- package/src/types.ts +20 -16
package/dist/index.d.mts
CHANGED
|
@@ -14,7 +14,7 @@ type ErrorCallback = (error: Error | FetchError) => void;
|
|
|
14
14
|
type LoadCallback = (src: string, isCached: boolean) => void;
|
|
15
15
|
type PlainObject<T = unknown> = Record<string, T>;
|
|
16
16
|
type PreProcessorCallback = (code: string) => string;
|
|
17
|
-
|
|
17
|
+
type Props = Simplify<Omit<React.SVGProps<SVGElement>, 'onLoad' | 'onError' | 'ref'> & {
|
|
18
18
|
baseURL?: string;
|
|
19
19
|
cacheRequests?: boolean;
|
|
20
20
|
children?: React.ReactNode;
|
|
@@ -29,7 +29,7 @@ interface Props extends Omit<React.SVGProps<SVGElement>, 'onLoad' | 'onError' |
|
|
|
29
29
|
title?: string | null;
|
|
30
30
|
uniqueHash?: string;
|
|
31
31
|
uniquifyIDs?: boolean;
|
|
32
|
-
}
|
|
32
|
+
}>;
|
|
33
33
|
interface State {
|
|
34
34
|
content: string;
|
|
35
35
|
element: React.ReactNode;
|
|
@@ -42,6 +42,9 @@ interface FetchError extends Error {
|
|
|
42
42
|
message: string;
|
|
43
43
|
type: string;
|
|
44
44
|
}
|
|
45
|
+
type Simplify<T> = {
|
|
46
|
+
[KeyType in keyof T]: T[KeyType];
|
|
47
|
+
} & {};
|
|
45
48
|
type Status = (typeof STATUS)[keyof typeof STATUS];
|
|
46
49
|
interface StorageItem {
|
|
47
50
|
content: string;
|
|
@@ -70,4 +73,4 @@ declare class CacheStore {
|
|
|
70
73
|
declare let cacheStore: CacheStore;
|
|
71
74
|
declare function InlineSVG(props: Props): string | number | boolean | Iterable<React.ReactNode> | react_jsx_runtime.JSX.Element | null | undefined;
|
|
72
75
|
|
|
73
|
-
export { ErrorCallback, FetchError, LoadCallback, PlainObject, PreProcessorCallback, Props, State, Status, StorageItem, cacheStore, InlineSVG as default };
|
|
76
|
+
export { ErrorCallback, FetchError, LoadCallback, PlainObject, PreProcessorCallback, Props, Simplify, State, Status, StorageItem, cacheStore, InlineSVG as default };
|
package/dist/index.d.ts
CHANGED
|
@@ -14,7 +14,7 @@ type ErrorCallback = (error: Error | FetchError) => void;
|
|
|
14
14
|
type LoadCallback = (src: string, isCached: boolean) => void;
|
|
15
15
|
type PlainObject<T = unknown> = Record<string, T>;
|
|
16
16
|
type PreProcessorCallback = (code: string) => string;
|
|
17
|
-
|
|
17
|
+
type Props = Simplify<Omit<React.SVGProps<SVGElement>, 'onLoad' | 'onError' | 'ref'> & {
|
|
18
18
|
baseURL?: string;
|
|
19
19
|
cacheRequests?: boolean;
|
|
20
20
|
children?: React.ReactNode;
|
|
@@ -29,7 +29,7 @@ interface Props extends Omit<React.SVGProps<SVGElement>, 'onLoad' | 'onError' |
|
|
|
29
29
|
title?: string | null;
|
|
30
30
|
uniqueHash?: string;
|
|
31
31
|
uniquifyIDs?: boolean;
|
|
32
|
-
}
|
|
32
|
+
}>;
|
|
33
33
|
interface State {
|
|
34
34
|
content: string;
|
|
35
35
|
element: React.ReactNode;
|
|
@@ -42,6 +42,9 @@ interface FetchError extends Error {
|
|
|
42
42
|
message: string;
|
|
43
43
|
type: string;
|
|
44
44
|
}
|
|
45
|
+
type Simplify<T> = {
|
|
46
|
+
[KeyType in keyof T]: T[KeyType];
|
|
47
|
+
} & {};
|
|
45
48
|
type Status = (typeof STATUS)[keyof typeof STATUS];
|
|
46
49
|
interface StorageItem {
|
|
47
50
|
content: string;
|
|
@@ -70,5 +73,5 @@ declare class CacheStore {
|
|
|
70
73
|
declare let cacheStore: CacheStore;
|
|
71
74
|
declare function InlineSVG(props: Props): string | number | boolean | Iterable<React.ReactNode> | react_jsx_runtime.JSX.Element | null | undefined;
|
|
72
75
|
|
|
73
|
-
export { ErrorCallback, FetchError, LoadCallback, PlainObject, PreProcessorCallback, Props, State, Status, StorageItem, cacheStore, InlineSVG as default };
|
|
76
|
+
export { ErrorCallback, FetchError, LoadCallback, PlainObject, PreProcessorCallback, Props, Simplify, State, Status, StorageItem, cacheStore, InlineSVG as default };
|
|
74
77
|
export = InlineSVG
|
package/dist/index.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
"use client";
|
|
1
2
|
"use strict";
|
|
2
3
|
var __create = Object.create;
|
|
3
4
|
var __defProp = Object.defineProperty;
|
|
@@ -39,8 +40,8 @@ __export(src_exports, {
|
|
|
39
40
|
default: () => InlineSVG
|
|
40
41
|
});
|
|
41
42
|
module.exports = __toCommonJS(src_exports);
|
|
42
|
-
var
|
|
43
|
-
var
|
|
43
|
+
var import_react2 = require("react");
|
|
44
|
+
var import_react_from_dom2 = __toESM(require("react-from-dom"));
|
|
44
45
|
|
|
45
46
|
// src/config.ts
|
|
46
47
|
var CACHE_NAME = "react-inlinesvg";
|
|
@@ -54,7 +55,7 @@ var STATUS = {
|
|
|
54
55
|
UNSUPPORTED: "unsupported"
|
|
55
56
|
};
|
|
56
57
|
|
|
57
|
-
// src/helpers.ts
|
|
58
|
+
// src/modules/helpers.ts
|
|
58
59
|
function canUseDOM() {
|
|
59
60
|
return !!(typeof window !== "undefined" && window.document && window.document.createElement);
|
|
60
61
|
}
|
|
@@ -112,7 +113,7 @@ function omit(input, ...filter) {
|
|
|
112
113
|
return output;
|
|
113
114
|
}
|
|
114
115
|
|
|
115
|
-
// src/cache.ts
|
|
116
|
+
// src/modules/cache.ts
|
|
116
117
|
var CacheStore = class {
|
|
117
118
|
constructor() {
|
|
118
119
|
__publicField(this, "cacheApi");
|
|
@@ -238,267 +239,301 @@ var CacheStore = class {
|
|
|
238
239
|
}
|
|
239
240
|
};
|
|
240
241
|
|
|
241
|
-
// src/
|
|
242
|
-
var
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
242
|
+
// src/modules/hooks.tsx
|
|
243
|
+
var import_react = require("react");
|
|
244
|
+
function usePrevious(state) {
|
|
245
|
+
const ref = (0, import_react.useRef)();
|
|
246
|
+
(0, import_react.useEffect)(() => {
|
|
247
|
+
ref.current = state;
|
|
248
|
+
});
|
|
249
|
+
return ref.current;
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
// src/modules/utils.ts
|
|
253
|
+
var import_react_from_dom = __toESM(require("react-from-dom"));
|
|
254
|
+
function getNode(options) {
|
|
255
|
+
const {
|
|
256
|
+
baseURL,
|
|
257
|
+
content,
|
|
258
|
+
description,
|
|
259
|
+
handleError,
|
|
260
|
+
hash,
|
|
261
|
+
preProcessor,
|
|
262
|
+
title,
|
|
263
|
+
uniquifyIDs = false
|
|
264
|
+
} = options;
|
|
265
|
+
try {
|
|
266
|
+
const svgText = processSVG(content, preProcessor);
|
|
267
|
+
const node = (0, import_react_from_dom.default)(svgText, { nodeOnly: true });
|
|
268
|
+
if (!node || !(node instanceof SVGSVGElement)) {
|
|
269
|
+
throw new Error("Could not convert the src to a DOM Node");
|
|
270
|
+
}
|
|
271
|
+
const svg = updateSVGAttributes(node, { baseURL, hash, uniquifyIDs });
|
|
272
|
+
if (description) {
|
|
273
|
+
const originalDesc = svg.querySelector("desc");
|
|
274
|
+
if (originalDesc?.parentNode) {
|
|
275
|
+
originalDesc.parentNode.removeChild(originalDesc);
|
|
276
|
+
}
|
|
277
|
+
const descElement = document.createElementNS("http://www.w3.org/2000/svg", "desc");
|
|
278
|
+
descElement.innerHTML = description;
|
|
279
|
+
svg.prepend(descElement);
|
|
280
|
+
}
|
|
281
|
+
if (typeof title !== "undefined") {
|
|
282
|
+
const originalTitle = svg.querySelector("title");
|
|
283
|
+
if (originalTitle?.parentNode) {
|
|
284
|
+
originalTitle.parentNode.removeChild(originalTitle);
|
|
264
285
|
}
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
{
|
|
270
|
-
content,
|
|
271
|
-
isCached: hasCache,
|
|
272
|
-
status: STATUS.LOADED
|
|
273
|
-
},
|
|
274
|
-
this.getElement
|
|
275
|
-
);
|
|
286
|
+
if (title) {
|
|
287
|
+
const titleElement = document.createElementNS("http://www.w3.org/2000/svg", "title");
|
|
288
|
+
titleElement.innerHTML = title;
|
|
289
|
+
svg.prepend(titleElement);
|
|
276
290
|
}
|
|
277
|
-
});
|
|
278
|
-
this.state = {
|
|
279
|
-
content: "",
|
|
280
|
-
element: null,
|
|
281
|
-
isCached: !!props.cacheRequests && cacheStore.isCached(props.src),
|
|
282
|
-
status: STATUS.IDLE
|
|
283
|
-
};
|
|
284
|
-
this.hash = props.uniqueHash ?? randomString(8);
|
|
285
|
-
}
|
|
286
|
-
componentDidMount() {
|
|
287
|
-
this.isActive = true;
|
|
288
|
-
if (!canUseDOM() || this.isInitialized) {
|
|
289
|
-
return;
|
|
290
291
|
}
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
292
|
+
return svg;
|
|
293
|
+
} catch (error) {
|
|
294
|
+
return handleError(error);
|
|
295
|
+
}
|
|
296
|
+
}
|
|
297
|
+
function processSVG(content, preProcessor) {
|
|
298
|
+
if (preProcessor) {
|
|
299
|
+
return preProcessor(content);
|
|
300
|
+
}
|
|
301
|
+
return content;
|
|
302
|
+
}
|
|
303
|
+
function updateSVGAttributes(node, options) {
|
|
304
|
+
const { baseURL = "", hash, uniquifyIDs } = options;
|
|
305
|
+
const replaceableAttributes = ["id", "href", "xlink:href", "xlink:role", "xlink:arcrole"];
|
|
306
|
+
const linkAttributes = ["href", "xlink:href"];
|
|
307
|
+
const isDataValue = (name, value) => linkAttributes.includes(name) && (value ? !value.includes("#") : false);
|
|
308
|
+
if (!uniquifyIDs) {
|
|
309
|
+
return node;
|
|
310
|
+
}
|
|
311
|
+
[...node.children].forEach((d) => {
|
|
312
|
+
if (d.attributes?.length) {
|
|
313
|
+
const attributes = Object.values(d.attributes).map((a) => {
|
|
314
|
+
const attribute = a;
|
|
315
|
+
const match = /url\((.*?)\)/.exec(a.value);
|
|
316
|
+
if (match?.[1]) {
|
|
317
|
+
attribute.value = a.value.replace(match[0], `url(${baseURL}${match[1]}__${hash})`);
|
|
297
318
|
}
|
|
298
|
-
|
|
299
|
-
|
|
319
|
+
return attribute;
|
|
320
|
+
});
|
|
321
|
+
replaceableAttributes.forEach((r) => {
|
|
322
|
+
const attribute = attributes.find((a) => a.name === r);
|
|
323
|
+
if (attribute && !isDataValue(r, attribute.value)) {
|
|
324
|
+
attribute.value = `${attribute.value}__${hash}`;
|
|
300
325
|
}
|
|
301
|
-
|
|
302
|
-
}
|
|
303
|
-
} catch (error) {
|
|
304
|
-
this.handleError(error);
|
|
326
|
+
});
|
|
305
327
|
}
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
componentDidUpdate(previousProps, previousState) {
|
|
309
|
-
if (!canUseDOM()) {
|
|
310
|
-
return;
|
|
328
|
+
if (d.children.length) {
|
|
329
|
+
return updateSVGAttributes(d, options);
|
|
311
330
|
}
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
331
|
+
return d;
|
|
332
|
+
});
|
|
333
|
+
return node;
|
|
334
|
+
}
|
|
335
|
+
|
|
336
|
+
// src/index.tsx
|
|
337
|
+
var import_jsx_runtime = require("react/jsx-runtime");
|
|
338
|
+
var cacheStore;
|
|
339
|
+
function ReactInlineSVG(props) {
|
|
340
|
+
const {
|
|
341
|
+
cacheRequests = true,
|
|
342
|
+
children = null,
|
|
343
|
+
description,
|
|
344
|
+
fetchOptions,
|
|
345
|
+
innerRef,
|
|
346
|
+
loader = null,
|
|
347
|
+
onError,
|
|
348
|
+
onLoad,
|
|
349
|
+
src,
|
|
350
|
+
title,
|
|
351
|
+
uniqueHash
|
|
352
|
+
} = props;
|
|
353
|
+
const [state, setState] = (0, import_react2.useReducer)(
|
|
354
|
+
(previousState2, nextState) => ({
|
|
355
|
+
...previousState2,
|
|
356
|
+
...nextState
|
|
357
|
+
}),
|
|
358
|
+
{
|
|
359
|
+
content: "",
|
|
360
|
+
element: null,
|
|
361
|
+
isCached: cacheRequests && cacheStore.isCached(props.src),
|
|
362
|
+
status: STATUS.IDLE
|
|
318
363
|
}
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
364
|
+
);
|
|
365
|
+
const { content, element, isCached, status } = state;
|
|
366
|
+
const previousProps = usePrevious(props);
|
|
367
|
+
const previousState = usePrevious(state);
|
|
368
|
+
const hash = (0, import_react2.useRef)(uniqueHash ?? randomString(8));
|
|
369
|
+
const isActive = (0, import_react2.useRef)(false);
|
|
370
|
+
const isInitialized = (0, import_react2.useRef)(false);
|
|
371
|
+
const handleError = (0, import_react2.useCallback)(
|
|
372
|
+
(error) => {
|
|
373
|
+
if (isActive.current) {
|
|
374
|
+
setState({
|
|
375
|
+
status: error.message === "Browser does not support SVG" ? STATUS.UNSUPPORTED : STATUS.FAILED
|
|
376
|
+
});
|
|
377
|
+
onError?.(error);
|
|
323
378
|
}
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
379
|
+
},
|
|
380
|
+
[onError]
|
|
381
|
+
);
|
|
382
|
+
const handleLoad = (0, import_react2.useCallback)((loadedContent, hasCache = false) => {
|
|
383
|
+
if (isActive.current) {
|
|
384
|
+
setState({
|
|
385
|
+
content: loadedContent,
|
|
386
|
+
isCached: hasCache,
|
|
387
|
+
status: STATUS.LOADED
|
|
388
|
+
});
|
|
328
389
|
}
|
|
329
|
-
}
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
390
|
+
}, []);
|
|
391
|
+
const fetchContent = (0, import_react2.useCallback)(async () => {
|
|
392
|
+
const responseContent = await request(src, fetchOptions);
|
|
393
|
+
handleLoad(responseContent);
|
|
394
|
+
}, [fetchOptions, handleLoad, src]);
|
|
395
|
+
const getElement = (0, import_react2.useCallback)(() => {
|
|
334
396
|
try {
|
|
335
|
-
const node =
|
|
336
|
-
const
|
|
337
|
-
if (!
|
|
397
|
+
const node = getNode({ ...props, handleError, hash: hash.current, content });
|
|
398
|
+
const convertedElement = (0, import_react_from_dom2.default)(node);
|
|
399
|
+
if (!convertedElement || !(0, import_react2.isValidElement)(convertedElement)) {
|
|
338
400
|
throw new Error("Could not convert the src to a React element");
|
|
339
401
|
}
|
|
340
|
-
|
|
341
|
-
element,
|
|
402
|
+
setState({
|
|
403
|
+
element: convertedElement,
|
|
342
404
|
status: STATUS.READY
|
|
343
405
|
});
|
|
344
406
|
} catch (error) {
|
|
345
|
-
|
|
407
|
+
handleError(new Error(error.message));
|
|
408
|
+
}
|
|
409
|
+
}, [content, handleError, props]);
|
|
410
|
+
const getContent = (0, import_react2.useCallback)(async () => {
|
|
411
|
+
const dataURI = /^data:image\/svg[^,]*?(;base64)?,(.*)/u.exec(src);
|
|
412
|
+
let inlineSrc;
|
|
413
|
+
if (dataURI) {
|
|
414
|
+
inlineSrc = dataURI[1] ? window.atob(dataURI[2]) : decodeURIComponent(dataURI[2]);
|
|
415
|
+
} else if (src.includes("<svg")) {
|
|
416
|
+
inlineSrc = src;
|
|
417
|
+
}
|
|
418
|
+
if (inlineSrc) {
|
|
419
|
+
handleLoad(inlineSrc);
|
|
420
|
+
return;
|
|
346
421
|
}
|
|
347
|
-
}
|
|
348
|
-
getNode() {
|
|
349
|
-
const { description, title } = this.props;
|
|
350
422
|
try {
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
const svg = this.updateSVGAttributes(node);
|
|
357
|
-
if (description) {
|
|
358
|
-
const originalDesc = svg.querySelector("desc");
|
|
359
|
-
if (originalDesc?.parentNode) {
|
|
360
|
-
originalDesc.parentNode.removeChild(originalDesc);
|
|
361
|
-
}
|
|
362
|
-
const descElement = document.createElementNS("http://www.w3.org/2000/svg", "desc");
|
|
363
|
-
descElement.innerHTML = description;
|
|
364
|
-
svg.prepend(descElement);
|
|
365
|
-
}
|
|
366
|
-
if (typeof title !== "undefined") {
|
|
367
|
-
const originalTitle = svg.querySelector("title");
|
|
368
|
-
if (originalTitle?.parentNode) {
|
|
369
|
-
originalTitle.parentNode.removeChild(originalTitle);
|
|
370
|
-
}
|
|
371
|
-
if (title) {
|
|
372
|
-
const titleElement = document.createElementNS("http://www.w3.org/2000/svg", "title");
|
|
373
|
-
titleElement.innerHTML = title;
|
|
374
|
-
svg.prepend(titleElement);
|
|
375
|
-
}
|
|
423
|
+
if (cacheRequests) {
|
|
424
|
+
const cachedContent = await cacheStore.get(src, fetchOptions);
|
|
425
|
+
handleLoad(cachedContent, true);
|
|
426
|
+
} else {
|
|
427
|
+
await fetchContent();
|
|
376
428
|
}
|
|
377
|
-
return svg;
|
|
378
429
|
} catch (error) {
|
|
379
|
-
|
|
430
|
+
handleError(error);
|
|
380
431
|
}
|
|
381
|
-
}
|
|
382
|
-
load() {
|
|
383
|
-
if (
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
if (
|
|
401
|
-
|
|
402
|
-
return;
|
|
432
|
+
}, [cacheRequests, fetchContent, fetchOptions, handleError, handleLoad, src]);
|
|
433
|
+
const load = (0, import_react2.useCallback)(async () => {
|
|
434
|
+
if (isActive.current) {
|
|
435
|
+
setState({
|
|
436
|
+
content: "",
|
|
437
|
+
element: null,
|
|
438
|
+
isCached: false,
|
|
439
|
+
status: STATUS.LOADING
|
|
440
|
+
});
|
|
441
|
+
}
|
|
442
|
+
}, []);
|
|
443
|
+
(0, import_react2.useEffect)(
|
|
444
|
+
() => {
|
|
445
|
+
isActive.current = true;
|
|
446
|
+
if (!canUseDOM() || isInitialized.current) {
|
|
447
|
+
return () => void 0;
|
|
448
|
+
}
|
|
449
|
+
try {
|
|
450
|
+
if (status === STATUS.IDLE) {
|
|
451
|
+
if (!isSupportedEnvironment()) {
|
|
452
|
+
throw new Error("Browser does not support SVG");
|
|
403
453
|
}
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
const content = await cacheStore.get(src, fetchOptions);
|
|
407
|
-
this.handleLoad(content, true);
|
|
408
|
-
} else {
|
|
409
|
-
await this.fetchContent();
|
|
410
|
-
}
|
|
411
|
-
} catch (error) {
|
|
412
|
-
this.handleError(error);
|
|
454
|
+
if (!src) {
|
|
455
|
+
throw new Error("Missing src");
|
|
413
456
|
}
|
|
457
|
+
load();
|
|
414
458
|
}
|
|
415
|
-
)
|
|
459
|
+
} catch (error) {
|
|
460
|
+
handleError(error);
|
|
461
|
+
}
|
|
462
|
+
isInitialized.current = true;
|
|
463
|
+
return () => {
|
|
464
|
+
isActive.current = false;
|
|
465
|
+
};
|
|
466
|
+
},
|
|
467
|
+
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
468
|
+
[]
|
|
469
|
+
);
|
|
470
|
+
(0, import_react2.useEffect)(() => {
|
|
471
|
+
if (!canUseDOM()) {
|
|
472
|
+
return;
|
|
416
473
|
}
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
const { content } = this.state;
|
|
420
|
-
const { preProcessor } = this.props;
|
|
421
|
-
if (preProcessor) {
|
|
422
|
-
return preProcessor(content);
|
|
474
|
+
if (!previousProps) {
|
|
475
|
+
return;
|
|
423
476
|
}
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
const replaceableAttributes = ["id", "href", "xlink:href", "xlink:role", "xlink:arcrole"];
|
|
429
|
-
const linkAttributes = ["href", "xlink:href"];
|
|
430
|
-
const isDataValue = (name, value) => linkAttributes.includes(name) && (value ? !value.includes("#") : false);
|
|
431
|
-
if (!uniquifyIDs) {
|
|
432
|
-
return node;
|
|
433
|
-
}
|
|
434
|
-
[...node.children].forEach((d) => {
|
|
435
|
-
if (d.attributes?.length) {
|
|
436
|
-
const attributes = Object.values(d.attributes).map((a) => {
|
|
437
|
-
const attribute = a;
|
|
438
|
-
const match = /url\((.*?)\)/.exec(a.value);
|
|
439
|
-
if (match?.[1]) {
|
|
440
|
-
attribute.value = a.value.replace(match[0], `url(${baseURL}${match[1]}__${this.hash})`);
|
|
441
|
-
}
|
|
442
|
-
return attribute;
|
|
443
|
-
});
|
|
444
|
-
replaceableAttributes.forEach((r) => {
|
|
445
|
-
const attribute = attributes.find((a) => a.name === r);
|
|
446
|
-
if (attribute && !isDataValue(r, attribute.value)) {
|
|
447
|
-
attribute.value = `${attribute.value}__${this.hash}`;
|
|
448
|
-
}
|
|
449
|
-
});
|
|
450
|
-
}
|
|
451
|
-
if (d.children.length) {
|
|
452
|
-
return this.updateSVGAttributes(d);
|
|
477
|
+
if (previousProps.src !== src) {
|
|
478
|
+
if (!src) {
|
|
479
|
+
handleError(new Error("Missing src"));
|
|
480
|
+
return;
|
|
453
481
|
}
|
|
454
|
-
|
|
455
|
-
})
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
"children",
|
|
466
|
-
"description",
|
|
467
|
-
"fetchOptions",
|
|
468
|
-
"innerRef",
|
|
469
|
-
"loader",
|
|
470
|
-
"onError",
|
|
471
|
-
"onLoad",
|
|
472
|
-
"preProcessor",
|
|
473
|
-
"src",
|
|
474
|
-
"title",
|
|
475
|
-
"uniqueHash",
|
|
476
|
-
"uniquifyIDs"
|
|
477
|
-
);
|
|
478
|
-
if (!canUseDOM()) {
|
|
479
|
-
return loader;
|
|
482
|
+
load();
|
|
483
|
+
} else if (previousProps.title !== title || previousProps.description !== description) {
|
|
484
|
+
getElement();
|
|
485
|
+
}
|
|
486
|
+
}, [description, getElement, handleError, load, previousProps, src, title]);
|
|
487
|
+
(0, import_react2.useEffect)(() => {
|
|
488
|
+
if (!previousState) {
|
|
489
|
+
return;
|
|
490
|
+
}
|
|
491
|
+
if (previousState.status !== STATUS.LOADING && status === STATUS.LOADING) {
|
|
492
|
+
getContent();
|
|
480
493
|
}
|
|
481
|
-
if (
|
|
482
|
-
|
|
494
|
+
if (previousState.status !== STATUS.LOADED && status === STATUS.LOADED) {
|
|
495
|
+
getElement();
|
|
483
496
|
}
|
|
484
|
-
if (
|
|
485
|
-
|
|
497
|
+
if (previousState.status !== STATUS.READY && status === STATUS.READY) {
|
|
498
|
+
onLoad?.(src, isCached);
|
|
486
499
|
}
|
|
500
|
+
}, [getContent, getElement, isCached, onLoad, previousState, src, status]);
|
|
501
|
+
const elementProps = omit(
|
|
502
|
+
props,
|
|
503
|
+
"baseURL",
|
|
504
|
+
"cacheRequests",
|
|
505
|
+
"children",
|
|
506
|
+
"description",
|
|
507
|
+
"fetchOptions",
|
|
508
|
+
"innerRef",
|
|
509
|
+
"loader",
|
|
510
|
+
"onError",
|
|
511
|
+
"onLoad",
|
|
512
|
+
"preProcessor",
|
|
513
|
+
"src",
|
|
514
|
+
"title",
|
|
515
|
+
"uniqueHash",
|
|
516
|
+
"uniquifyIDs"
|
|
517
|
+
);
|
|
518
|
+
if (!canUseDOM()) {
|
|
487
519
|
return loader;
|
|
488
520
|
}
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
|
|
493
|
-
|
|
521
|
+
if (element) {
|
|
522
|
+
return (0, import_react2.cloneElement)(element, { ref: innerRef, ...elementProps });
|
|
523
|
+
}
|
|
524
|
+
if ([STATUS.UNSUPPORTED, STATUS.FAILED].includes(status)) {
|
|
525
|
+
return children;
|
|
526
|
+
}
|
|
527
|
+
return loader;
|
|
528
|
+
}
|
|
494
529
|
function InlineSVG(props) {
|
|
495
530
|
if (!cacheStore) {
|
|
496
531
|
cacheStore = new CacheStore();
|
|
497
532
|
}
|
|
498
533
|
const { loader } = props;
|
|
499
|
-
const hasCallback =
|
|
500
|
-
const [isReady, setReady] =
|
|
501
|
-
|
|
534
|
+
const hasCallback = (0, import_react2.useRef)(false);
|
|
535
|
+
const [isReady, setReady] = (0, import_react2.useState)(cacheStore.isReady);
|
|
536
|
+
(0, import_react2.useEffect)(() => {
|
|
502
537
|
if (!hasCallback.current) {
|
|
503
538
|
cacheStore.onReady(() => {
|
|
504
539
|
setReady(true);
|