Renderizando imagens — a melhor maneira

Dec 10 2022
O que eu costumava fazer Renderizar uma imagem com o elemento img e se src for nulo ou indefinido, renderizar uma imagem alternativa. O que acontece quando uma imagem falha Sempre que uma imagem falha ao carregar, um evento onError é acionado, podemos usar este evento para atualizar src para uma imagem de fallback.
Imagem de Alexandra_Koch do Pixabay

O que eu costumava fazer

Renderize uma imagem com o elemento img e, se src for nulo ou indefinido, renderize uma imagem alternativa.

import { FC } from "react";

type ImageProps = {
  src: string;
  alt: string;
};

const Image: FC<ImageProps> = ({src, alt}) => {
  return <img alt={alt} src={src || "fallback.jpg"}/>; 
}

Exemplo de imagem vazia quando src é inválido

O que acontece quando uma imagem falha

Sempre que uma imagem falha ao carregar, um evento onError é acionado, podemos usar esse evento para atualizar src para uma imagem de fallback.

Atualizações para a correção

Em vez de adicionar diretamente uma condição opcional da imagem de fallback, podemos adicionar um manipulador de eventos onError para fazer o mesmo.

useImage Hook

import { SyntheticEvent, useEffect, useState } from "react";
import { ImageProps } from "./Image";

type ImagePropsGetter = () => ImageProps & {
  onError: (e: SyntheticEvent<HTMLImageElement>) => void;
};

const useImage = ({
  src: srcFromProps,
  alt
}: ImageProps): { getImageProps: ImagePropsGetter } => {
  const [src, setSrc] = useState(srcFromProps);

  const onError = () => {
    setSrc("fallback.jpg");
  };

  useEffect(() => {
    setSrc(srcFromProps);
  }, [srcFromProps]);

  const getImageProps: ImagePropsGetter = () => {
    return { src, alt, onError };
  };

  return { getImageProps };
};

export default useImage;

import { FC } from "react";
import useImage from "./useImage";

export type ImageProps = {
  src: string;
  alt: string;
};

const Image: FC<ImageProps> = (props) => {
  const { getImageProps } = useImage(props);

  return <img {...getImageProps()} />;
};

export default Image;

Imagem de Alexandra_Koch do Pixabay

Links externos