Spaces:
Sleeping
Sleeping
File size: 5,260 Bytes
1ed9ed3 ed212f9 1189eac 1ed9ed3 1189eac 1ed9ed3 c1eacec 1ed9ed3 c1eacec 1189eac 1ed9ed3 1189eac c1eacec 1189eac 1ed9ed3 1189eac c1eacec d80b7b4 1ed9ed3 d80b7b4 1ed9ed3 d80b7b4 1ed9ed3 1189eac c1eacec 1ed9ed3 1189eac c1eacec 1ed9ed3 ed212f9 c1eacec d80b7b4 1ed9ed3 d80b7b4 1ed9ed3 d80b7b4 1ed9ed3 65cd5c5 1ed9ed3 c1eacec 1189eac 1ed9ed3 1189eac ed212f9 d80b7b4 1ed9ed3 d80b7b4 c1eacec d80b7b4 1ed9ed3 d80b7b4 1ed9ed3 d80b7b4 1ed9ed3 c1eacec 1ed9ed3 c1eacec 1189eac 1ed9ed3 1189eac ed212f9 1189eac 1ed9ed3 1189eac 1ed9ed3 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 | # -----------------------------
# app.py - Detección de objetos con DETR y Gradio (imagen + datos)
# -----------------------------
# -----------------------------
# Librerías utilizadas y justificación
# -----------------------------
# transformers: permite usar modelos preentrenados como DETR para detección de objetos.
# DetrImageProcessor: preprocesa imágenes para que DETR las interprete correctamente.
# DetrForObjectDetection: modelo DETR preentrenado para detectar objetos en imágenes.
# torch: cálculos con tensores para inferencia con PyTorch.
# PIL.Image y ImageDraw: manipulación de imágenes y dibujo de cajas y etiquetas.
# gradio: crear interfaces web interactivas de manera sencilla.
from transformers import DetrImageProcessor, DetrForObjectDetection
import torch
from PIL import Image, ImageDraw, ImageFont
import gradio as gr
# -----------------------------
# Cargar modelo preentrenado
# -----------------------------
processor = DetrImageProcessor.from_pretrained("facebook/detr-resnet-50")
model = DetrForObjectDetection.from_pretrained("facebook/detr-resnet-50")
# -----------------------------
# Función de detección
# -----------------------------
def detect_objects(image):
"""
Detecta objetos en la imagen y retorna:
- Imagen con cajas y etiquetas
- Texto con los objetos detectados y coordenadas
"""
width, height = image.size
# Preprocesamiento
inputs = processor(images=image, return_tensors="pt", padding=True)
# Inferencia
with torch.no_grad():
outputs = model(**inputs)
# Postprocesamiento
target_sizes = torch.tensor([[height, width]])
results = processor.post_process_object_detection(
outputs, target_sizes=target_sizes, threshold=0.9
)[0]
labels = results["labels"]
scores = results["scores"]
boxes = results["boxes"]
# -----------------------------
# Preparar la imagen con detecciones
# -----------------------------
image_drawn = image.copy()
draw = ImageDraw.Draw(image_drawn)
try:
font = ImageFont.truetype("arial.ttf", 16)
except:
font = ImageFont.load_default()
for score, label, box in zip(scores, labels, boxes):
box = [float(b) for b in box]
# Ajustar coordenadas dentro de la imagen
box[0] = max(0, min(box[0], width))
box[1] = max(0, min(box[1], height))
box[2] = max(0, min(box[2], width))
box[3] = max(0, min(box[3], height))
# Dibujar caja roja
draw.rectangle(box, outline="red", width=3)
# Preparar etiqueta con margen y fondo blanco
label_text = f"{label} {score:.2f}"
text_width, text_height = draw.textsize(label_text, font=font)
text_padding = 4 # margen en pixeles
# Determinar posición de la etiqueta
text_x0 = box[0]
text_y0 = max(0, box[1] - text_height - 2*text_padding)
text_x1 = text_x0 + text_width + 2*text_padding
text_y1 = text_y0 + text_height + 2*text_padding
# Fondo blanco para la etiqueta
draw.rectangle([text_x0, text_y0, text_x1, text_y1], fill="white")
# Texto en negro encima del fondo blanco
draw.text((text_x0 + text_padding, text_y0 + text_padding), label_text, fill="black", font=font)
# -----------------------------
# Preparar texto de resultados
# -----------------------------
detected_objects_text = []
for score, label, box in zip(scores, labels, boxes):
detected_objects_text.append(
f"Objeto: {label}, Score: {score:.2f}, Box: {box.tolist()}"
)
detected_objects_text = "\n".join(detected_objects_text)
# Retornar: (imagen procesada, resultados en texto)
return image_drawn, detected_objects_text
# -----------------------------
# Crear interfaz con Gradio
# -----------------------------
def create_interface():
"""
Interfaz con dos cuadros:
- Imagen con detección visual
- Texto con coordenadas y scores
"""
interface = gr.Interface(
fn=detect_objects,
inputs=gr.Image(type="pil"),
outputs=[gr.Image(type="pil", label="Imagen con Detección"),
gr.Textbox(label="Resultados (datos)")],
live=True,
title="Detección de Objetos con DETR",
description=(
"Sube una imagen y obtén la detección de objetos. "
"El primer cuadro muestra la imagen con cajas rojas y etiquetas (ahora con fondo blanco). "
"El segundo cuadro muestra los datos: objetos detectados, scores y coordenadas."
)
)
interface.launch()
# -----------------------------
# Ejecutar la aplicación
# -----------------------------
if __name__ == "__main__":
create_interface()
# -----------------------------
# Justificaciones y decisiones
# -----------------------------
# 1. Separar imagen y datos mejora la visualización y comprensión.
# 2. Fondo blanco en etiquetas evita que el texto quede recortado o sobre fondo rojo/imagen.
# 3. text_padding asegura un margen entre el borde del recuadro y el texto.
# 4. threshold=0.9 evita falsos positivos y mantiene solo predicciones confiables.
# 5. PIL.ImageDraw se usa para dibujar cajas y etiquetas sin modificar la imag
|