|
| 1 | +import { basename } from "path"; |
1 | 2 | import { memo, useCallback, useEffect, useMemo, useState } from "react"; |
2 | 3 | import styled from "styled-components"; |
3 | | -import { SUPPORTED_ICON_PIXEL_RATIOS } from "utils/constants"; |
| 4 | +import { |
| 5 | + MAX_RES_ICON_OVERRIDE, |
| 6 | + SUPPORTED_ICON_PIXEL_RATIOS, |
| 7 | +} from "utils/constants"; |
4 | 8 | import { |
5 | 9 | cleanUpBufferUrl, |
6 | 10 | createFallbackSrcSet, |
@@ -51,6 +55,36 @@ const StyledIcon = styled.img.attrs<StyledIconProps>( |
51 | 55 | visibility: ${({ $loaded }) => ($loaded ? "visible" : "hidden")}; |
52 | 56 | `; |
53 | 57 |
|
| 58 | +const supportedPixelRatios = new Map<string, number[]>(); |
| 59 | + |
| 60 | +const getSupportedPixelRatios = ( |
| 61 | + imagePath: string, |
| 62 | + extension: string |
| 63 | +): number[] => { |
| 64 | + if (supportedPixelRatios.has(imagePath)) { |
| 65 | + const cachedEntry = supportedPixelRatios.get(imagePath); |
| 66 | + |
| 67 | + if (cachedEntry) return cachedEntry; |
| 68 | + } |
| 69 | + |
| 70 | + let ratios = SUPPORTED_ICON_PIXEL_RATIOS; |
| 71 | + const iconOverride = MAX_RES_ICON_OVERRIDE[basename(imagePath, extension)]; |
| 72 | + |
| 73 | + if (iconOverride) { |
| 74 | + const [expectedSize, maxIconSize] = iconOverride; |
| 75 | + |
| 76 | + if (expectedSize && maxIconSize) { |
| 77 | + const maxRatio = Math.floor(maxIconSize / expectedSize); |
| 78 | + |
| 79 | + ratios = SUPPORTED_ICON_PIXEL_RATIOS.filter((ratio) => ratio <= maxRatio); |
| 80 | + } |
| 81 | + } |
| 82 | + |
| 83 | + supportedPixelRatios.set(imagePath, ratios); |
| 84 | + |
| 85 | + return ratios; |
| 86 | +}; |
| 87 | + |
54 | 88 | const Icon: FCWithRef< |
55 | 89 | HTMLImageElement, |
56 | 90 | IconProps & Omit<React.ImgHTMLAttributes<HTMLImageElement>, "src"> |
@@ -118,7 +152,7 @@ const Icon: FCWithRef< |
118 | 152 | <picture> |
119 | 153 | {!singleSrc && |
120 | 154 | isDynamic && |
121 | | - SUPPORTED_ICON_PIXEL_RATIOS.map((ratio) => { |
| 155 | + getSupportedPixelRatios(imgSrc, srcExt).map((ratio) => { |
122 | 156 | const srcSet = imageSrc(imgSrc, imgSize, ratio, srcExt); |
123 | 157 | const mediaRatio = ratio - 0.99; |
124 | 158 |
|
|
0 commit comments