Desenvolvedores
src_
components_
AvatarUpload.jsx

📸 AvatarUpload - Upload e Pré-visualização de Imagem

Este componente permite que o usuário envie uma imagem e visualize a prévia antes de salvar. Ele utiliza o React com o hook useState para armazenar a imagem selecionada.


🛠 Estrutura do Componente

Começamos importando os pacotes necessários:

import React, { useState } from "react"; 
import { Avatar, AvatarImage, AvatarFallback } from "@/components/ui/avatar";
import { Input } from "@/components/ui/input";
import { Label } from "@/components/ui/label";
  • useState 📌 → Gerencia o estado da imagem carregada.
  • Avatar, AvatarImage e AvatarFallback 🖼 → Exibe a imagem carregada ou um texto de fallback caso nenhuma imagem tenha sido enviada.
  • Input 📂 → Campo para upload do arquivo.
  • Label 🏷 → Rótulo para o campo de upload.

🎨 Estado da Imagem

Criamos um estado (image) para armazenar a URL da imagem carregada:

const [image, setImage] = useState(null);

Agora, precisamos de uma função que trate a seleção do arquivo e converta a imagem em base64 para pré-visualização.


📂 Manipulação do Arquivo

A função handleFileChange é responsável por processar a imagem enviada pelo usuário:

const handleFileChange = (event) => {
  const file = event.target.files[0]; // Obtém o arquivo selecionado
  const reader = new FileReader();
 
  reader.onloadend = () => {
    setImage(reader.result); // Atualiza o estado com a imagem em base64
  };
 
  if (file) {
    reader.readAsDataURL(file); // Converte a imagem para base64
  }
};
  • FileReader 📖 → Converte a imagem em um formato que o navegador pode exibir.
  • reader.onloadend → Quando a conversão termina, atualizamos o estado image.

🏗 Renderizando o Componente

Agora, montamos a interface do componente:

return (
  <div className="flex flex-col items-center space-y-2">
    <Label htmlFor="avatar" className="mb-2">Foto de Perfil</Label>
 
    {/* 📸 Avatar com fallback caso não tenha imagem */}
    <Avatar className="w-32 h-32">
      {image ? (
        <AvatarImage src={image} alt="User Avatar" />
      ) : (
        <AvatarFallback>Sem imagem</AvatarFallback>
      )}
    </Avatar>
 
    {/* 📂 Input para upload da imagem */}
    <div className="grid w-full max-w-sm items-center gap-1.5">
      <Label htmlFor="avatar">Foto</Label>
      <Input
        type="file"
        id="avatar"
        accept="image/*"
        onChange={handleFileChange}
      />
    </div>
  </div>
);
  • Se a imagem foi carregada, exibimos a prévia (AvatarImage).
  • Caso contrário, mostramos o texto "Sem imagem" (AvatarFallback).
  • O campo de upload (Input) aceita apenas arquivos do tipo imagem (accept="image/*").

📌 Código Completo

import React, { useState } from "react"; 
import { Avatar, AvatarImage, AvatarFallback } from "@/components/ui/avatar";
import { Input } from "@/components/ui/input";
import { Label } from "@/components/ui/label";
 
const AvatarUpload = () => {
  const [image, setImage] = useState(null);
 
  const handleFileChange = (event) => {
    const file = event.target.files[0];
    const reader = new FileReader();
 
    reader.onloadend = () => {
      setImage(reader.result);
    };
 
    if (file) {
      reader.readAsDataURL(file);
    }
  };
 
  return (
    <div className="flex flex-col items-center space-y-2">
      <Label htmlFor="avatar" className="mb-2">Foto de Perfil</Label>
 
      <Avatar className="w-32 h-32">
        {image ? (
          <AvatarImage src={image} alt="User Avatar" />
        ) : (
          <AvatarFallback>Sem imagem</AvatarFallback>
        )}
      </Avatar>
 
      <div className="grid w-full max-w-sm items-center gap-1.5">
        <Label htmlFor="avatar">Foto</Label>
        <Input
          type="file"
          id="avatar"
          accept="image/*"
          onChange={handleFileChange}
        />
      </div>
    </div>
  );
};
 
export default AvatarUpload;

✅ Conclusão