Skip to content

Commit

Permalink
Merge pull request #6 from lbb00/feat-imagedecoder-cache
Browse files Browse the repository at this point in the history
feat: add cache for isTypeSupported
  • Loading branch information
lbb00 committed Dec 18, 2023
2 parents 96316fb + 456e823 commit 40cc368
Show file tree
Hide file tree
Showing 3 changed files with 32 additions and 21 deletions.
5 changes: 5 additions & 0 deletions .changeset/hungry-rats-itch.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"optimal-img-format": minor
---

Add cache for ImageDecoder.isTypeSupported
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
[![License](https://img.shields.io/github/license/lbb00/optimal-img-format.svg)](https://github.com/lbb00/optimal-img-format/blob/master/LICENSE)
[![Npm download](https://img.shields.io/npm/dw/optimal-img-format.svg)](https://www.npmjs.com/package/optimal-img-format)

> Get optimal image format on the browser or server.
> Get optimal image format on the browser and server.
- Support for AVIF, WebP and JPEG XL
- Zero dependency
Expand Down Expand Up @@ -43,7 +43,7 @@ const format = await getOptimalImgFormatOnBrowser(["avif", "webp"]);
const formatWebp = await isSupportWebP();
```

Detecting browser supports from:
Detecting browser supports by:

- [ImageDecoder.isTypeSupported](https://developer.mozilla.org/en-US/docs/Web/API/ImageDecoder/isTypeSupported_static)
- <https://avif.io/blog/tutorials/css/#avifsupportdetectionscript>
Expand Down
44 changes: 25 additions & 19 deletions src/browser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -27,34 +27,40 @@ function loadImage(base64Src: string, format: ImgFormat) {
return loadImagePromiseMap[format] as Promise<HTMLImageElement>
}

const cachedSupportMap: Partial<Record<ImgFormat, boolean | undefined>> = {}
const isTypeSupportedPromiseMap: Partial<
Record<ImgFormat, boolean | undefined>
> = {}
async function isTypeSupported(format: ImgFormat) {
if (isTypeSupportedPromiseMap[format] === undefined) {
isTypeSupportedPromiseMap[format] = await ImageDecoder.isTypeSupported(
`image/${format}`,
)
}
return isTypeSupportedPromiseMap[format] as boolean
}

const supportCacheMap: Partial<Record<ImgFormat, boolean | undefined>> = {}
async function isSupportWithCacheMap(
format: ImgFormat,
imgBase64: string,
{ force = false } = {},
) {
if (cachedSupportMap[format] === undefined || force) {
if (
typeof ImageDecoder !== 'undefined' &&
typeof ImageDecoder.isTypeSupported === 'function'
) {
try {
cachedSupportMap[format] = await ImageDecoder.isTypeSupported(
`image/${format}`,
)
} catch (e) {
cachedSupportMap[format] = false
}
} else {
try {
if (supportCacheMap[format] === undefined || force) {
try {
if (
typeof ImageDecoder !== 'undefined' &&
typeof ImageDecoder.isTypeSupported === 'function'
) {
supportCacheMap[format] = await isTypeSupported(format)
} else {
const img = await loadImage(imgBase64, format)
cachedSupportMap[format] = img.width > 0 && img.height > 0
} catch (e) {
cachedSupportMap[format] = false
supportCacheMap[format] = img.width > 0 && img.height > 0
}
} catch (e) {
supportCacheMap[format] = false
}
}
return cachedSupportMap[format] as boolean
return supportCacheMap[format] as boolean
}

export async function isSupportAVIF({ force = false } = {}) {
Expand Down

0 comments on commit 40cc368

Please sign in to comment.