// @ts-check

import { decode } from 'blurhash';
import React, { useRef, useEffect } from 'react';
import PropTypes from 'prop-types';

/**
 * @typedef BlurhashPropsBase
 * @property {string} hash Hash to render
 * @property {number} width
 * Width of the blurred region in pixels. Defaults to 32
 * @property {number} [height]
 * Height of the blurred region in pixels. Defaults to width
 * @property {boolean} [dummy]
 * Whether dummy mode is enabled. If enabled, nothing is rendered
 * and canvas left untouched
 */

/** @typedef {JSX.IntrinsicElements['canvas'] & BlurhashPropsBase} BlurhashProps */

/**
 * Component that is used to render blurred of blurhash string
 *
 * @param {BlurhashProps} param1 Props of the component
 * @returns Canvas which will render blurred region element to embed
 */
function Blurhash({
  hash,
  width = 32,
  height = width,
  dummy = false,
  ...canvasProps
}) {
  const canvasRef = /** @type {import('react').MutableRefObject<HTMLCanvasElement>} */ (useRef());

  useEffect(() => {
    const { current: canvas } = canvasRef;
    canvas.width = canvas.width; // resets canvas

    if (dummy) return;

    const pixels = decode(hash, width, height);
    const ctx = canvas.getContext('2d');
    const imageData = new ImageData(pixels, width, height);

    ctx.putImageData(imageData, 0, 0);
  }, [dummy, hash, width, height]);

  return (
    <canvas {...canvasProps} ref={canvasRef} width={width} height={height} />
  );
}

Blurhash.propTypes = {
  hash: PropTypes.string.isRequired,
  width: PropTypes.number,
  height: PropTypes.number,
  dummy: PropTypes.bool,
};

export default React.memo(Blurhash);

@@ -183,16 +183,17 @@
  %7Bstring
+?
 %7D hash H
@@ -1124,16 +1124,25 @@
 f (dummy
+ %7C%7C !hash
 ) return
@@ -1144,16 +1144,28 @@
 eturn;%0A%0A
+    try %7B%0A  
     cons
@@ -1204,16 +1204,18 @@
 eight);%0A
+  
     cons
@@ -1247,24 +1247,26 @@
 ('2d');%0A    
+  
 const imageD
@@ -1314,16 +1314,18 @@
 );%0A%0A    
+  
 ctx.putI
@@ -1351,16 +1351,107 @@
  0, 0);%0A
+    %7D catch (err) %7B%0A      console.error('Blurhash decoding failure', %7B err, hash %7D);%0A    %7D%0A
   %7D, %5Bdu

Improve safety of Blurhash component (#14278)