Spaces:
Sleeping
Sleeping
File size: 5,226 Bytes
886e412 e48dd40 86d32c9 886e412 e48dd40 886e412 e48dd40 886e412 e48dd40 886e412 e48dd40 886e412 e48dd40 886e412 e48dd40 886e412 e48dd40 886e412 e48dd40 886e412 e48dd40 ca79521 e48dd40 ca79521 e48dd40 886e412 |
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 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 |
import gradio as gr
import numpy as np
import cv2
from keras.models import load_model
import tensorflow as tf
from tensorflow import keras
# Cargar el modelo entrenado
model1 = load_model('./isatron_v3.h5')
# Función para encontrar la última capa convolucional
def find_last_conv_layer(model):
for layer in reversed(model.layers):
if 'conv' in layer.name:
return layer.name
raise ValueError("No se encontró una capa convolucional en el modelo.")
# Obtener el nombre de la última capa convolucional
last_conv_layer_name = find_last_conv_layer(model1)
print("Última capa convolucional:", last_conv_layer_name)
# Definir tamaño de imagen y etiquetas
img_size1 = 150
labels = ['PNEUMONIA', 'NORMAL']
def load_and_preprocess_image1(img):
# Convertir imagen de Gradio (PIL Image) a array numpy
img = np.array(img)
# Convertir de RGB a escala de grises
img = cv2.cvtColor(img, cv2.COLOR_RGB2GRAY)
# Redimensionar imagen al tamaño requerido
img = cv2.resize(img, (img_size1, img_size1))
# Reformatear imagen para entrada del modelo
img = img.reshape(-1, img_size1, img_size1, 1)
# Normalizar imagen
img = img / 255.0
return img
def make_gradcam_heatmap(img_array, model, last_conv_layer_name, pred_index=None):
# Crear un modelo que mapee la imagen de entrada a las activaciones
# de la última capa convolucional y las predicciones
grad_model = keras.models.Model(
[model.inputs], [model.get_layer(last_conv_layer_name).output, model.output]
)
# Calcular el gradiente de la clase predicha con respecto a las activaciones
with tf.GradientTape() as tape:
last_conv_layer_output, preds = grad_model(img_array)
if pred_index is None:
pred_index = np.argmax(preds[0])
class_channel = preds[:, pred_index]
# Calcular los gradientes
grads = tape.gradient(class_channel, last_conv_layer_output)
# Pooling global de los gradientes
pooled_grads = tf.reduce_mean(grads, axis=(0, 1, 2))
# Multiplicar cada canal por su importancia
last_conv_layer_output = last_conv_layer_output[0]
heatmap = last_conv_layer_output @ pooled_grads[..., tf.newaxis]
heatmap = tf.squeeze(heatmap)
# Normalizar el mapa de calor entre 0 y 1
heatmap = tf.maximum(heatmap, 0) / tf.reduce_max(heatmap)
heatmap = heatmap.numpy()
return heatmap
def overlay_heatmap(heatmap, img, alpha=0.4):
# Redimensionar mapa de calor al tamaño de la imagen
heatmap = cv2.resize(heatmap, (img.shape[1], img.shape[0]))
# Convertir mapa de calor a RGB
heatmap = np.uint8(255 * heatmap)
heatmap = cv2.applyColorMap(heatmap, cv2.COLORMAP_JET)
# Convertir imagen a BGR
img = cv2.cvtColor(img, cv2.COLOR_RGB2BGR)
# Aplicar mapa de calor a la imagen original
overlayed_img = heatmap * alpha + img
overlayed_img = np.uint8(overlayed_img)
# Convertir de nuevo a RGB
overlayed_img = cv2.cvtColor(overlayed_img, cv2.COLOR_BGR2RGB)
return overlayed_img
def image_classifier1(img):
# Mantener la imagen original para superponer
orig_img = np.array(img)
# Preprocesar la imagen
img_array = load_and_preprocess_image1(img)
# Realizar predicción usando model1
preds = model1.predict(img_array)
prediction = preds[0][0] # Suponiendo que el modelo devuelve una probabilidad
# Determinar el índice de la clase predicha
pred_index = int(prediction > 0.5)
# Generar mapa de calor
heatmap = make_gradcam_heatmap(img_array, model1, last_conv_layer_name, pred_index=pred_index)
# Superponer mapa de calor en la imagen original
overlayed_img = overlay_heatmap(heatmap, orig_img)
# Retornar la imagen superpuesta y los porcentajes de predicción
prediction_percentage = {'PNEUMONIA': float(prediction), 'NORMAL': float(1 - prediction)}
return overlayed_img, prediction_percentage
# Definir CSS personalizado
custom_css = """
body {
background-color: #e6f2ff;
}
h1 {
color: #003366;
text-align: center;
}
.gradio-container {
font-family: 'Arial', sans-serif;
max-width: 800px;
margin: auto;
padding: 20px;
background-color: #ffffff;
border-radius: 10px;
}
.footer {
text-align: center;
margin-top: 20px;
color: #003366;
font-size: 14px;
}
label {
font-weight: bold;
color: #003366;
}
button {
background-color: #0059b3;
color: white;
border: none;
padding: 10px 20px;
cursor: pointer;
}
button:hover {
background-color: #004080;
}
"""
# Crear interfaz Gradio con CSS personalizado y pie de página
demo_model1 = gr.Interface(
fn=image_classifier1,
inputs=gr.Image(type="pil", label="Sube una imagen de radiografía"),
outputs=[
gr.Image(type="numpy", label="Imagen con Mapa de Calor"),
gr.Label(num_top_classes=2, label="Resultados de Predicción")
],
title="IsaTron V2 con Mapa de Calor",
description="Esta aplicación detecta neumonía a partir de imágenes de radiografías de tórax.",
article="<div class='footer'>Jeysshon 2024</div>",
css=custom_css
)
# Ejecutar la interfaz
if __name__ == "__main__":
demo_model1.launch(share=True)
|